Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

chrome.storage.local get returns 'undefined'

I want to get 2 values from chrome storage via chrome.storage.local.get() but if I try to return the values from the callback function, I get 'undefined'. If I console.log() them, they are actually logged. Why is that? I've read in some other posts, that I need to use a callback - but as far as my basic JS understanding goes, I already return the value from the callback frunction of get().

// this should load 2 keys from an object stored in chrome storage
function loadJiraUrlElements(){
    chrome.storage.local.get({companyName: '', jiraBaseUrl: ''}, function(items) {
        return (items.companyName + items.jiraBaseUrl);
     })
}

// I want to use this function to call the return value and populate a DOM element
function populateUrlFieldsWithUrlElements(){
    companyInput.value = loadJiraUrlElements()
}
like image 967
Hannes Avatar asked Dec 24 '22 01:12

Hannes


2 Answers

You're getting undefined because you're returning to the callback function (ie the inner function), not the outer function, which you are trying to get the return value from.

You can use a promise with resolve so you can use a .then callback in your populateUrlFieldsWithUrlElements function to get the value you want:

function loadJiraUrlElements() {
  return new Promise(resolve => {
    chrome.storage.local.get({companyName: '', jiraBaseUrl: ''}, function(items) {
      resolve(items.companyName + items.jiraBaseUrl);
    })
  })
}

// I want to use this function to call the return value and populate a DOM element
function populateUrlFieldsWithUrlElements() {
  loadJiraUrlElements().then(result => {
    companyInput.value = result;
  })
}

Or you can use async/await in your second function if you don't wish to use the .then callback:

// I want to use this function to call the return value and populate a DOM element
async function populateUrlFieldsWithUrlElements() {
  companyInput.value = await loadJiraUrlElements();
}
like image 76
Nick Parsons Avatar answered Dec 25 '22 14:12

Nick Parsons


It's an async function, you can either wrap it under a Promise object or continue using the callback mechanism.

1.) Promise:

function loadJiraUrlElements() {
    return new Promise(function(resolve, reject) {
        chrome.storage.local.get({companyName: '', jiraBaseUrl: ''}, function(items) {
            resolve(items.companyName + items.jiraBaseUrl);
         })
    });
}

// And caller function changes to 
function populateUrlFieldsWithUrlElements(){
    loadJiraUrlElements().then(function(value) {
        companyInput.value = value;
    })
}

2.) Callback:

function loadJiraUrlElements(cb){
    chrome.storage.local.get({companyName: '', jiraBaseUrl: ''}, function(items) {
        cb && cb(items.companyName + items.jiraBaseUrl);
     })
}

function populateUrlFieldsWithUrlElements(){
    loadJiraUrlElements(function(value) {
        companyInput.value = value;
    })

}
like image 41
varun agarwal Avatar answered Dec 25 '22 15:12

varun agarwal