I used events in nodejs to implement my logic. And "nextParams" is an event that make function "extractVideo" executed again. I know I used recursive event loop. I tried to used setTimeout(function, 0) and setTimeout(function, 1) in my code, but the error "Maximum call stack size exceeded" still appear, I wonder does anybody know how to fix this problem, I am appreciated very much!
videoCrawler.prototype.extractVideo=function(queryStr){
self.on("videoIdArray",function(){
if(videoIdArray.length){
self.getVideoInfo(videoIdArray.pop());
}else{
self.videomonitor.emit("nextParams");
}
});
self.on("getVideoIdArray",function(videoidarray){
if(!(videoidarray || videoidarray.length)){
self.videomonitor.emit("nextParams");
}
videoIdArray=videoidarray;
self.getVideoInfo(videoIdArray.pop());
});
self.on("save",function(videodetailinfo){
if(!videodetailinfo){
if(videoIdArray.length){
self.getVideoInfo(videoIdArray.pop());
}else{
self.videomonitor.emit("nextParams");
}
}
self.saveVideoInfo(videodetailinfo);
});
self.on("errorCapture",function(errInfo){
if(errInfo.message=="queryStr is not exits"){
setTimeout(self.videomonitor.emit("nextParams"),1);
}else if(errInfo.message=="videodetailsinfo is not exits"){
self.getVideoInfo(videoIdArray.pop());
}else if(errInfo.message=="videoId is empty"){
self.getVideoInfo(videoIdArray.pop());
}else if(errInfo.message=="save fails"){
self.getVideoInfo(videoIdArray.pop());
}
});
self.getVideoId(queryStr);
}
below are functions
videoCrawler.prototype.getVideoId=function(queryStr){
if(!queryStr) this.emit("errorCapture",errInfo);
//dosomething
this.emit("getVideoIdArray",videoArray);
}
videoCrawler.prototype.getVideoInfo=function(videoId){
if(!queryStr) this.emit("errorCapture",errInfo);
//dosomething
self.emit("save",videodetails);
}
videoCrawler.prototype.saveVideoInfo=function(videodetailsinfo){
if(!queryStr) this.emit("errorCapture",errInfo);
//dosomething
self.emit("videoIdArray");
}
For certain problems that involve tail calls, you can turn on the tail call optimization in some versions of Node (since 6.5 but not any more since 8.0!).
See this for compatibility:
For info on proper tail calls, see:
For other cases where you don't have tails calls you should use
setImmediate()
orprocess.nextTick()
depending on when you want your code to run, instead of usingsetTimeout()
because those are better optimized butsetTimeout()
would still avoid the call stack from growing. But here you don't usesetTimeout()
for every call and that is probably the problem.