I'm new to Promises and trying to load lots of results from localstorage first and if that fails, fall back on getting the data from a server. I don't want to use jquery - ignore that I'm currently using $.getJSON :-/
function loader1() {
return new Promise(function (resolve, reject) {
localforage.getItem("data1").then(function (value) {
if (value !== null) {
resolve(value);
} else {
$.getJSON("/myapp/data1.json").then(function (data) {
if (data !== null) {
resolve(data);
}
}).catch(function (err) {
reject(err);
});
}
});
});
}
which is fine for one file. So then I'd
loader1().then(function(result) {
// we have a result
doSomethingElse();
}).catch(function (err) {
// problem
});
But I want to do this for multiple files, some of which are in localstorage and some of which load json from a remote source. I want to load everything, and when it's finished, perform the next step of my app.
Promise.all
appears to be the thing, but I can't see how to get the results of each of the loaders; I was thinking it would be like:
Promise
.all([loader1, loader2, loader3])
.then(function(result1,result2,result3)) {
...
but this isn't how it works ... so I tried
Promise
.all([loader1, loader2, loader3])
.then(function(result)) {
// var result1 = result[0];
// var result2 = result[1];
// var result3 = result[1];
but the results of the second are the functions not the returned values ...
Searching many sites indicated that promise systems like Q and bluebird have a spread
method which looks like what I want. can I do this in plain old javascript (how?) or should I look at using a library like Q or RSVP instead?
but the results of the second are the functions not the returned values ...
You are not resolving any value form the Promise
you construct. You are also not returning any values form the succeeding .then
's in the chain.
You need to do the following for each of your loader functions:
function loader1() {
var data = localforage.getItem("data1");
data.then(function (data) {
if (data !== null) {
return data;
} else {
data = $.getJSON("/myapp/data1.json")
if (data !== null) {
return data;
} else {
return Error;
}
data.catch(function (err) {
return (err);
}
This ensures that a call to function loader1() will either return a resolved Promise
or a rejected Promise
. You can then use the solution suggested by guest271314:
Promise
.all([loader1(), loader2(), loader3()])
.then(function(result) {
// var result1 = result[0];
// var result2 = result[1];
// var result3 = result[1];
})
.catch(function (err) {
// problem
});
However please be aware that a Promise
executes synchronously. This means that it does not automatically wait on any asynchronous action to complete inside the Promise
. You have to take care of this yourself by only resolving it once the asynchronous action has completed (typically by resolving in a callback passed to an asynchronous function).
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With