Search code examples
node.jsasynchronousrecursionnode-async

Error on callback when running a recursion function using async


I try to execute a recursion through a tree, in order to exec node_func for each node in the tree. node_func also returns the next values in the tree under [values].

I use async.eachSeries which get a list of the nodes in the next level of the tree. The function runs successfully over the first branch of the tree, but at the leaf where I have the stop condition, I try to call the callback but it's undefined.

The code:

function clone(a) {
   return JSON.parse(JSON.stringify(a));
}
var searchNext = function(params, callbackSN){
    var seParams = clone(params);
    node_func(seParams,function(searchRes){
        //Stop Condition - return
        if (searchRes["nextFeature"] != 1){
            return callbackSN(); //Stop Condition
        }
        var values = searchRes["values"]
        var paramsArr = []
        for (var i = 0; i < values.length; i++) {
            var seParams2 = clone(seParams);
            seParams2["value"].push(values[i]["value"])
            paramsArr.push(seParams2)               
        };

        async.eachSeries(paramsArr, searchNext, function(err){
            return callbackSN(err)
        });         
    })
}

//init search
var params = {"value" :[]}
searchNext(params,console.log)

When I run it, it runs over the first branch, and when it gets to the "Stop Condition" I get the following error:

TypeError: undefined is not a function

Pointing to the line:

return callbackSN(); //Stop Condition

At the Stop Condition


Solution

  • I had an error in the original code :

    function clone(a) {
       return JSON.parse(JSON.stringify(a));
    }
    var searchNext = function(params,db, callbackSN){
        var seParams = clone(params);
        node_func(seParams,db,function(searchRes){
            //Stop Condition - return
            if (searchRes["nextFeature"] != 1){
                return callbackSN(); //Stop Condition
            }
            var values = searchRes["values"]
            var paramsArr = []
            for (var i = 0; i < values.length; i++) {
                var seParams2 = clone(seParams);
                seParams2["value"].push(values[i]["value"])
                paramsArr.push(seParams2)               
            };
    
            async.eachSeries(paramsArr, searchNext, function(err){
                return callbackSN(err)
            });         
        })
    }
    
    //init search
    var params = {"value" :[]}
    searchNext(params,console.log)
    

    The second variable "db" at node_func cannot be called from the async, so it made the confusion.

    I added the "db" variable at the parent function as a local variable.