saving and retrieving from chrome.storage.sync
Asked Answered
H

8

65

I am trying to save a data object in chrome sync storage and then retrieve it, however the get() function always returns an empty object. The code I am using is,

function storeUserPrefs() {
  var key='myKey', testPrefs = {'val': 10};
  chrome.storage.sync.set({key: testPrefs}, function() {
    console.log('Saved', key, testPrefs);
  });
}

function getUserPrefs() {
  chrome.storage.sync.get('myKey', function (obj) {
    console.log('myKey', obj);
  });
}

Could someone please tell me what I am doing wrong here?

Heterophony answered 25/1, 2013 at 22:7 Comment(1)
correct me if I am wrong, but with {key: "something"} JS creates an object with a property named 'key', not the value of the key variable declared before. You can only use a variable on the right side of the colon. See section 'Creating a Direct Instance' hereSmoothbore
P
88

The problem is with chrome.storage.sync.set({key: testPrefs}

Your data is stored as

{
    key: "{"val":10}"
}

So, your code chrome.storage.sync.get('myKey') return undefined\empty object.

Solution I

Use string "key" as your key

chrome.storage.sync.get("key", function (obj) {
    console.log(obj);
});

or

Solution II

Set data through "myKey" Key.

chrome.storage.sync.set({"myKey": testPrefs})

P.S : Don't forget chrome.storage.sync is permanent storage API, Use chrome.storage.sync.clear before any further testing to see changes

References

EDIT 1

Use this code to set variable value in Chrome.storage

function storeUserPrefs() {
    var key = "myKey",
        testPrefs = JSON.stringify({
            'val': 10
        });
    var jsonfile = {};
    jsonfile[key] = testPrefs;
    chrome.storage.sync.set(jsonfile, function () {
        console.log('Saved', key, testPrefs);
    });

}

It generates following Output

Object{
    myKey: "{"val":10}"
}
Patnode answered 26/1, 2013 at 3:6 Comment(3)
Thanks this works. So is there any way to use a string variable as a key in the set/get functions?Heterophony
@source.rar:Check My EDIT #1, in the listed way it is possible, hope this helps :Patnode
None of these answers test for failure... quoting developer.chrome.com/extensions/storage: "Callback on success, or on failure (in which case runtime.lastError will be set)."Doloritas
H
32

A more fancy way to do it, and it handles errors as well:

const getStorageData = key =>
  new Promise((resolve, reject) =>
    chrome.storage.sync.get(key, result =>
      chrome.runtime.lastError
        ? reject(Error(chrome.runtime.lastError.message))
        : resolve(result)
    )
  )

const { data } = await getStorageData('data')


const setStorageData = data =>
  new Promise((resolve, reject) =>
    chrome.storage.sync.set(data, () =>
      chrome.runtime.lastError
        ? reject(Error(chrome.runtime.lastError.message))
        : resolve()
    )
  )

await setStorageData({ data: [someData] })
Houseclean answered 18/1, 2019 at 21:20 Comment(2)
wow, much better than the others solutions, and the error handling is great !Kaleidoscopic
Great solution, thanks ! It's worth noting that to save an item in the list with key data and value someData, you'll want to use the above code as follows: await setStorageData({ [data]: someData }) instead of what's written in the answer, which will create an array with someData in the first element. Also, getting an item like this did not work for me. I needed to add an additional level getStorageData('data')['data'] worked as expected. I did use chain the get and set functions with .then and .catch instead of using await, so the issues I had might be related to this.Rexanna
S
13
function storeUserPrefs() {
    var key='myKey', testPrefs = {'val': 10};
    chrome.storage.sync.set({[key]: testPrefs}, function() {
      console.log('Saved', key, testPrefs);
    });
}

You could just force to evaluate the variable key using [key] when saving. That way is easy to set your keys dynamically. Hope that helps.

Supervision answered 16/5, 2017 at 14:24 Comment(2)
how to use chrome.storage.sync.get ?Proper
@swapnilgandhi something like that will help you read the value: chrome.storage.sync.get("myKey", function(data) { console.log(Object.values(data)[0].val); });Expedite
K
2

As chrome.storage.sync can storage JS objects, you can just do this:

var save = {};
save["myKey"] = testPrefs;

chrome.storage.sync.set(save, function() {
    console.log('Settings saved');
});
Knocker answered 28/6, 2013 at 12:35 Comment(0)
B
0
testPrefs = JSON.stringify({
            'val': 10
        });
    var jsonfile = {};
    jsonfile[key] = testPrefs;
    chrome.storage.sync.set(jsonfile, function () {
        console.log('Saved', key, testPrefs)
Buzz answered 21/11, 2013 at 18:36 Comment(0)
P
0

By using WebExtension browser API Polyfill you can use promises and also use TS and code like below for set sync of chrome and get sync

function getStore() {
    return chrome.storage.sync.get("myKey").then(function (value) {
        return value["myKey"];
    });
}

function setStore() {
    return chrome.storage.sync.set("myKey","value").then(function (value) {
        return "Success!";
    });
}
Presnell answered 12/7, 2022 at 8:38 Comment(0)
W
0

as of then ECMA now got new syntac to simplify Your example

    function storeUserPrefs() {
    var key='myKey', testPrefs = {'val': 10};
        chrome.storage.sync.set({key: testPrefs}, function() {console.log('Saved', key, testPrefs);});
}

function getUserPrefs() {
    chrome.storage.sync.get('myKey', function ({myKey}) {
        console.log('myKey', obj);
    });
}

So now to get rid of object name You just need to destruct argument object and it will unwrap it. Hennce look this syntax:

let ob={a:"me",b:"and" ,c:"myself",d:"and", e:"eye", f:"o_O"}

function someFunction( {c,d,f} ){
 console.log( c,d,f)  //output:   myself and o_O
}
Wideeyed answered 21/5, 2023 at 15:12 Comment(0)
P
0

Although this question is very old, there is a simple syntax in ES 6 that solves the problem. Refer to solution 2.

Problem

In your code,

{ key: testPrefs }

creates an object with a key key instead of myKey. It does not refer to the content of the variable key.

Here are two solutions to set myKey (or any string that is known in runtime only) to testPrefs in an object.

Solution 1:

Create an object first, then use the obj[key] syntax.

function storeUserPrefs() {
  var key = 'myKey', testPrefs = {'val': 10};

  var obj = {};
  obj[key] = testPrefs; // The key name is resolved dynamically to 'myKey'

  chrome.storage.sync.set(obj, function() {
    console.log('Saved', key, testPrefs);
  });
}

Solution 2 (ES 6):

Use the { [key]: testPrefs } syntax.

function storeUserPrefs() {
  var key = 'myKey', testPrefs = {'val': 10};

  chrome.storage.sync.set({ [key]: testPrefs }, function() {
    console.log('Saved', key, testPrefs);
  });
}

Note when getting from storage:

Your code

  chrome.storage.sync.get('myKey', function (obj) {
    console.log('myKey', obj);
  });

returns { myKey: { 'val': 10 } } instead of { 'val': 10 }. So for me, I will print obj[key] instead of obj.

Photovoltaic answered 19/6 at 4:59 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.