I have an object with certain keys which need to be updated. The updates are through a function (gets info from a database) and returns a promise. The original object has many keys and only some will need updating.
// mocked response for demonstration
// the call01 function returns an array that make_obj function uses.
// the make_obj function returns an object like var obj.
// the get_data expects an array of ints and returns an array of strings like ['cat', 'dog', 'boat']
var obj = {'key1': {'a': [1,2,3], 'b': [2,3,4], 'c': [5,6,7]}, 'key2': {'a': [5,4,5], 'b': [9,8,9], 'c': [1,9,5]}}
var _ = require('lodash');
function updater(obj) {
var deferred = Q.defer();
_.forIn(obj, function(v,k) {
get_data(v.a)
.then(function(words) {
v.a = words;
});
get_data(v.b)
.then(function(words) {
v.b = words;
});
deferred.resolve(obj);
});
return deferred.promise;
// call01 returns a promise
call01(some_val)
.then(make_obj)
.then(updater)
.then(console.log)
I am expecting to see the something like this (granted i'm making up the values here):
{'key1': {'a': ['cat', 'dog', 'boat'], 'b': ['dog', 'boat', 'chair'] , 'c': [5,7,8]}, 'key2': {'a': ['spoon', 'chair', 'spoon'], 'b': ['tree', 'bird', 'tree'], 'c': [1,9,5]}}
I know that I may need to have a Q.all or Q.allSettled to aggregate the promises but I cannot get it to work.
This is what I tried with Q.all. What isn't working is that the I could not figure out how to map the results from var promises back to the obj to update the values.
function updater(obj) {
var deferred = Q.defer();
// this is only making an array of get_data from el.a
var promise_arr1 = _.map(obj, function(el){
return get_data(el.a);
});
// this is only making an array of get_data from el.b
var promise_arr2 = _.map(obj, function(el){
return get_data(el.b);
});
// I know this is not the right way to do it. the result flattened arr has no mapping back to the original obj. I wasn't sure how to make the update to obj.
Q.all(_.flatten(promise_arr1, promise_arr2))
.then(deferred.resolve)
return deferred.promise;
I even thought about using async instead of q. I saw that async has a async.eachSeries but I didn't give it a full try yet. Any suggestions?