I have an async.series() calling a function from another javascript object:
main.js
var object1 = require('./object1');
var object1 = require('./object2');
async.series([
object1.myFunction1,
object2.anotherFunction
]);
object1.js
module.exports = {
function1: function(callback){
async.each(someArray, function(item, cb) {
function2(item);
}, function(err){
if(err) return callback(err);
callback();
});
},
function2:function(item, callback){
//Do something
}
};
This code does not work because function2 is undefined inside the callback. I tried to put
var refToFunction2 = this.function2
at the beginning of function1. It works if we call directly function1, but here function1 is called by async and for some reasons: this = undefined.
Is there a clean way to do that ?
You could setup your object1.js file in the following way:
var async = require('async');
function function1(callback){
async.each(someArray, function(item, cb) {
function2(item);
}, function(err){
if(err) return callback(err);
callback();
});
}
function function2(item, callback){
//Do something
}
module.exports.function1 = function1;
module.exports.function2 = function2;
You should now notice that function1 and function2 are defined globally in the file. This means they can be called inside of each other freely.
Related
var robject=[];
async.waterfall([
function (callback) {
for(var i in serial){
Router.find({},{r_serial_no:serial[i]},function (err,routerData) {
robject = robject.concat(routerData);
});
}
console.log('Robject= '+robject); //THIS RETURNS NULL
callback(null, robject);
},
function (blogs, callback) {
res.render('index', {dispatched_data:dispatched_data });
callback(null, 'Ended..' );
}
], function (err, result) {
console.log(result);
});
this is my waterfall model, here i need to access the robject from schema.find method to outside of that method. but it always return null..
how to access that??
You have the syntax error:
for(var i in serial){
Router.find({},{r_serial_no: i},function (err,routerData) {
robject = robject.concat(routerData);
});
}
the "for" loop defines "i" as next item in the array each iteration
The problem I see here is in for...in loop. Your callback will be fired even if your process i.e. Router.find is not completed. You can try below code, It might help.
Unlike your serial object please create a array called serials.
var robject=[];
async.waterfall([
function (callback) {
async.each(serials,
function(serial, localCb){
Router.find({},{r_serial_no:serial},function (err,routerData) {
robject = robject.concat(routerData);
localCb()
});
},
function(err){
console.log('Robject= '+robject);
callback(null, robject);
}
);
},
function (blogs, callback) {
res.render('index', {dispatched_data:dispatched_data });
callback(null, 'Ended..' );
}
], function (err, result) {
console.log(result);
});
I want to store all the data fetched from the database in arr_obj, then use this variable int async.forEachLimit function. For this reason i used async.series function, everything works fine except sleep(1000), code sleeps as soon as second function of async.series is called and then gives all the result together.Being a beginner in NodeJs i don't have much idea about all this.
var sleep = require('system-sleep');
//
//
var arr_obj = [];
async.series([
function (callback) {
Service.listAllUser(req.body, function (err, data) {
if(err) return callback(err);
arr_obj = data.toJSON();
callback();
});
},
function (callback1) {
console.log(arr_obj);
async.forEachLimit(arr_obj, 1, function (item, callback) {
Quality_Service.qualityService(item, function (err, data) {
if (err) return next(err);
console.log(data);
});
sleep(1000);
callback();
});
callback1();
}
], function (err) { //This function gets called after the two tasks have called their "task callbacks"
if (err) return next(err);
res.send("okay");
});
Try to use callback inside the foreach, with setTimeout
async.forEachLimit(arr_obj, function (item, callback) {
Quality_Service.qualityService(item, function (err, data) {
if (err) return next(err);
setTimeout(callback, 1000, err);
});
});
I am having a weird problem with calling a callback inside another callback from mongoose.
Setup : MEAN Stack.
myFunc = function (cb) {
var projection = {
'_id': 0,
'var1': 1,
'var2': 1
}
var order = {
'var1': 1
}
User.find({})
.select(projection).sort(order)
.exec(function(err, docs){
if(err){
console.log(err);
cb(err,docs);
} else {
console.log(docs);
cb(err,docs);
}
});
};
going to the lines where cb(err,docs) will result in
"ReferenceError: cb is not defined"
the weird part is
I have functions with even deeper nested callbacks that can invoke the "cb" normaly.
myFunc = function(cb){
model1.count({var1:'test'}, function (err, count) {
if(count) {
model2.findOne({dat1:'hoho'}, function (err, doc){
if (err) {
console.error(err);
cb(err,doc);
} else {
cb(err,doc);
}
});
} else {
cb({message: "No items found"}, null);
}
})
}
The code above will be invoked like so...
function init(something){
myfunc(function(err, doc) {
if (err){
console.log(err.message);
} else {
//do something about doc
}
});
}
ugh, it seems that the calling function did not properly follow the rules.
it called
myFunc(json, function(err,doc){
//do something
})
wrong param count...
In node js, i am using async function to get the result from another function and store it as array and return the result. But here i am getting empty json as output {}. See the comments inside code block. May i know where i am doing mistake ?
collectSearchResult: function (searchConfig, callback) {
var searchResult = {};
async.each(searchConfig.scope, function (scope, callback) {
var query = {
"query": {
"match": {
"_all": searchConfig.q
}
},
operationPath = scope.url;
this.doSearch(operationPath, query, function (err, results) {
var type = scope.type;
searchResult[type] = results;
// Here i am able to get correct output async
console.log(searchResult);
});
callback();
}.bind(this), function (err) {
// Here it is just returning empty json like {}. this function is called before this.doSearch complete its task
console.log(searchResult);
callback(err, searchResult);
});
}
collectSearchResult: function (searchConfig, callback) {
var searchResult = {};
async.each(searchConfig.scope, function (scope, callback) {
var query = {
"query": {
"match": {
"_all": searchConfig.q
}
},
operationPath = scope.url;
this.doSearch(operationPath, query, function (err, results) {
var type = scope.type;
searchResult[type] = results;
// Here i am able to get correct output async
console.log(searchResult);
//<><><><><><><>
callback(); //you need to place the callback for asynch.each
//within the callback chain of your query, else async.each
//immediately finishes before your data has arrived.
//<><><><><><><>
});
}.bind(this), function (err) {
// Here it is just returning empty json like {}. this function is called before this.doSearch complete its task
console.log(searchResult);
callback(err, searchResult);
});
}
var foo = function (callback_foo) {
async.series([func1, func2, func3], function (err) {
if (err) {
return callback_foo(err)
}
async.series([func4, func5], function(err){
if (err) {
return callback_foo(err)
}
return callback_foo(); //1
});
return callback_foo(); //2
});
}
do I need to return callback_foo() two times? the first callback_foo() is to tell async.series func4, fun5 is done. And the second callback_foo() is to tell the outer async.series func1,func2, func3 are done. is that right?
you could do it like below.
var foo = function (callback_foo) {
async.series([
func1(callback) {
//func1 processing
callback(); //this will call func2 after func1 is done
},
func2(callback) {
//func2 processing
callback(); //this will call func 3 after func 2 is done
},
func3(callback) {
//do your func3 processing here,then call async.series for 4 and 5.
async.series([
func4(callback) {
//do func 4 processing here
callback(); //This will call func5 after func4 is done
},
func5(callback) {
//do func5 processing here
callback(); //this will call the final callback of the nested async.series()
}], function (err) {
//this is the final callback of the nested(2nd) async.series call
callback(); //this is the iterator callback of func3,this will now call the final callback of the original async.series
});
}], function (err) {
//final callback after all the functions are executed.
return callback_foo();//call your foo's callback.
});
}
Note:callback used in func1,2,3,4,5 need not be defined,its async.series's iterator callback,thats helps us to move to the next function.
However i don't see the point of nested async.series calls.you could do it with 1 async.series call.
var foo = function (callback_foo) {
async.series([func1, func2, func3,func4,func5], function (err) {
if (err) {
return callback_foo(err)
}
});
};