I have a Cordova mobile app that stores offline data in localStorage. Recently users started getting QUOTA_EXCEEDED_ERR error because localStorage has 5MB limit. I decided to use "localForage" framework, but I noticed that it works asynchronously. Since I don't want to rewrite all my plex app wrapping into callback functions I wanted to know if there is some way to use "localForage" synchronously (wait till getItem function returns value).
Here is a code example what I am trying to do:
localforage.setItem('testKey', 'testValue', function() {
var value = getValue('testKey');
console.log(value); // here I get undefined, but I want to get a value
});
function getValue(key) { // I want this function to return value
var result;
localforage.getItem(key, function(value) {
result = value;
});
return result;
}
I want getValue() to return a value without changing any other code
I have a Cordova mobile app that stores offline data in localStorage. Recently users started getting QUOTA_EXCEEDED_ERR error because localStorage has 5MB limit. I decided to use "localForage" framework, but I noticed that it works asynchronously. Since I don't want to rewrite all my plex app wrapping into callback functions I wanted to know if there is some way to use "localForage" synchronously (wait till getItem function returns value).
Here is a code example what I am trying to do:
localforage.setItem('testKey', 'testValue', function() {
var value = getValue('testKey');
console.log(value); // here I get undefined, but I want to get a value
});
function getValue(key) { // I want this function to return value
var result;
localforage.getItem(key, function(value) {
result = value;
});
return result;
}
I want getValue() to return a value without changing any other code
Share Improve this question asked Feb 7, 2019 at 8:35 user2412672user2412672 1,4794 gold badges22 silver badges38 bronze badges4 Answers
Reset to default 1According to this link
localForage has a dual API that allows you to either use Node-style callbacks or Promises. If you are unsure which one is right for you, it's remended to use Promises.
So you can use any of them if you like. if using promises you can use async/await
to wait for the result
localforage.setItem('testKey', 'testValue', async function() {
var value = await getValue('testKey')
console.log(value); // here I get undefined, but I want to get a value
});
async function getValue(key) {
var result = await localforage.getItem(key);
return result;
}
jsfiddle
https://localforage.github.io/localForage/#data-api-getitem, use async
/await
:
try {
const value = await localforage.getItem('somekey');
// This code runs once the value has been loaded
// from the offline store.
console.log(value);
} catch (err) {
// This code runs if there were any errors.
console.log(err);
}
As you mentioned, your issue is not related to localforage. Localforage is asynchronous because it runs in the browser, and you don't want the UX to be frozen while you do back-end like calls to persistence.
There is already a discussion about calling synchronously async function: Call An Asynchronous Javascript Function Synchronously
Solution 1 - Make your functions async
if you can have your function async, this is probably the best way.
localforage.setItem('testKey', 'testValue', async function() {
console.log(await getValue('testKey'));
})
getValue = async function(key) => await localforage.getItem(key);
Solution 2 - Use setTimeout()
localforage.setItem('testKey', 'testValue', function() {
console.log(getValue('testKey'));
});
function getValue(key) {
let result;
localforage.getItem(key, value => {
result = value);
});
const update = () => {
if("undefined" === typeof result) setTimeout(update, 100)
}
update();
return result;
}
localforage.setItem('testKey', 'testValue', async function() {//declare function as async
var value = await getValue('testKey'); //wait for the value
console.log(value); // "testValue" value should show in console
});
//declare function as async
async function getValue(key) {
var result = await localforage.getItem(key); //wait for the localforage item
return result;
}
JSFiddle here: https://jsfiddle/mvdgxorL/