admin管理员组

文章数量:1332889

I am trying to call an asynchronous function recursively using javascript promises but haven't found a pattern that works.

This is what I imagine would work:

var doAsyncThing = function(lastId){
  new Promise(function(resolve, reject){
    // async request with lastId
    return resolve(response)
  }
}

var recursivelyDoAsyncThing = function(lastId){
  doAsyncThing(lastId).then(function(response){
    return new Promise(function(resolve, reject){
      //do something with response
      if(response.hasMore){
        //get newlastId
        return resolve(recursivelyDoAsyncThing(newLastId));
      }else{
        resolve();
      }
    });
  });
}

recursivelyDoAsyncThing().then( function(){
  console.log('done');
});

Why doesn't this work? What have I misunderstood?

Is there a better pattern to solve this problem?

I am trying to call an asynchronous function recursively using javascript promises but haven't found a pattern that works.

This is what I imagine would work:

var doAsyncThing = function(lastId){
  new Promise(function(resolve, reject){
    // async request with lastId
    return resolve(response)
  }
}

var recursivelyDoAsyncThing = function(lastId){
  doAsyncThing(lastId).then(function(response){
    return new Promise(function(resolve, reject){
      //do something with response
      if(response.hasMore){
        //get newlastId
        return resolve(recursivelyDoAsyncThing(newLastId));
      }else{
        resolve();
      }
    });
  });
}

recursivelyDoAsyncThing().then( function(){
  console.log('done');
});

Why doesn't this work? What have I misunderstood?

Is there a better pattern to solve this problem?

Share Improve this question asked Feb 15, 2016 at 18:46 benjaminjosephwbenjaminjosephw 4,4173 gold badges22 silver badges41 bronze badges
Add a ment  | 

3 Answers 3

Reset to default 3

recursivelyDoAsyncThing needs to return a Promise in order to continue the chain. In your case, all you need to do is have doAsyncThing return its Promise:

var doAsyncThing = function(lastId){
  // Notice the return here:
  return new Promise(function(resolve, reject){

Then add return to your doAsyncThing call like so:

var recursivelyDoAsyncThing = function(lastId){
  // Notice the return here:
  return doAsyncThing(lastId).then(function(response){

You're missing a return in the recursivelyDoAsyncThing function. Also you should avoid the Promise constructor antipattern:

function recursivelyDoAsyncThing(lastId) {
  return doAsyncThing(lastId).then(function(response) {
//^^^^^^
    //do something with response
    if (response.hasMore) {
      //get newlastId
      return recursivelyDoAsyncThing(newLastId);
    } else {
      return; // undefined? Always return a useful value
    }
  });
}

I have a simple example of recursive promise. The example is based on calculation factorial of number.

let code = (function(){
	let getFactorial = n =>{
		return new Promise((resolve,reject)=>{
			if(n<=1){
				resolve(1);
			}
			resolve(
				getFactorial(n-1).then(fact => {
					return fact * n;
				})
			)
		});
	}
	return {
		factorial: function(number){
			getFactorial(number).then(
				response => console.log(response)
			)
		}
	}
})();
code.factorial(5);
code.factorial(6);
code.factorial(7);

本文标签: javascriptHow to call promise function recursivelyStack Overflow