Javascript 使用$q串行执行多个任务

Javascript 使用$q串行执行多个任务,javascript,angularjs,angular-promise,Javascript,Angularjs,Angular Promise,现在我在玩超级英雄安格拉斯的$q。我有三个异步任务。让我们称它们为taskA,taskB和taskC。我想一个接一个地执行。目前我正在使用$q的all()方法。我正在做以下工作: var taskA = function() { var d = $q.defer(); $timeout(function() { $log.log('Task A'); d.resolve('A is done'); }, Math.random() * 5000);

现在我在玩超级英雄安格拉斯的
$q
。我有三个
异步
任务。让我们称它们为
taskA
taskB
taskC
。我想一个接一个地执行。目前我正在使用
$q
all()
方法。我正在做以下工作:

var taskA = function() {
    var d = $q.defer();
    $timeout(function() {
      $log.log('Task A');
      d.resolve('A is done');
    }, Math.random() * 5000);
    return d.promise;
  };


  var taskB = function() {
    var d = $q.defer();
    $timeout(function() {
      $log.log('Task B');
      // d.resolve('B is done');
      d.reject('B is rejected');
    }, Math.random() * 5000);
    return d.promise;
  };


  var taskC = function() {
    var d = $q.defer();
    $timeout(function() {
      $log.log('Task C');
      //d.resolve('C is done');
      d.reject('C is rejected');
    }, Math.random() * 5000);
    return d.promise;
  };

  $scope.startWithAll = function() {
    $log.log('With all started');
    var promises = [taskA(), taskB(), taskC()];
    $q.all(promises).then(
      //success callback...
      function(result) {
        $log.log(result);
      },
      //error callback
      function(error) {
        $log.log(error);
      },
      //progress callback
      function() {
        //todo implement it
      }
    ).finally(function() {
      $log.log('I am from finally');
    });
  };
这种方法的问题是我的所有任务都是并行执行的。在
success
中,我在
数组中得到每个任务的结果。如果任何任务被拒绝,则其余任务继续执行,但执行错误
回调
,我在回调中得到错误
对象
。我想做的是,首先只执行
taskA
,然后执行
taskB
,然后执行
taskC
,如果其中任何一个被拒绝或失败,则不应执行任务的其余部分。执行不应该是并行的,而应该是串行的。要连续执行它们,我将执行以下操作:

$scope.startSerial = function() {
    $log.log('Serially started');
    $q.when().then(function(result) {
      $log.log(result);
      return taskA();
    }).then(function(result) {
      $log.log(result);
      return taskB();
    }).then(function(result) {
      $log.log(result);
      return taskC();
    }).finally(function() {
      $log.log('I am from finally');
    });
  };

这就解决了我的问题。但问题是,在第一次
回调中
我得到了
未定义的
,我对此没有任何问题,所以我们可以省略这一部分。但目前我只有三个任务,所以这种方法很好,但如果明天我有三个以上的任务,那么这将不是一个好的实施方式。有没有其他方法可以这样做,因为我无法继续添加多个
,然后在另一个
的下方添加。我已经创造了这个世界。我想的是创建一个
服务
,它将创建这个任务执行层次结构,但我不知道如何做到这一点。

您可以按照希望任务执行的顺序将任务放入一个数组中,然后循环执行任务,如果任务失败,则退出循环。它不是很性感,但它能完成任务

您可以按照希望任务执行的顺序将任务放入数组中,然后循环执行任务,如果任务失败,则退出循环。它不是很性感,但它能完成任务

您可以创建一个连接所有承诺的循环:

  function each(arr, func) {
    for (var i = 0; i < arr.length; i++) {
      func(arr[i], i);
    }
  }

  $scope.startSerial = function() {
      var funcs = [taskA, taskB, taskC];
      $log.log('Serially started');
      var s = $q.when();
      each(funcs, function (func) {
          s = s.then(function (result) {
            $log.log(result);
            return func();
          });
      });
      s.finally(function () {
        $log.log('I am from finally');
      });
  }
每个函数(arr、func){
对于(变量i=0;i

这将导致与原始脚本相同的行为,但您可以简单地调整数组
funcs
,而不是为每个承诺添加额外的代码块。

您可以创建一个循环,连接所有承诺:

  function each(arr, func) {
    for (var i = 0; i < arr.length; i++) {
      func(arr[i], i);
    }
  }

  $scope.startSerial = function() {
      var funcs = [taskA, taskB, taskC];
      $log.log('Serially started');
      var s = $q.when();
      each(funcs, function (func) {
          s = s.then(function (result) {
            $log.log(result);
            return func();
          });
      });
      s.finally(function () {
        $log.log('I am from finally');
      });
  }
每个函数(arr、func){
对于(变量i=0;i
这将导致与原始脚本相同的行为,但是您可以简单地调整数组
funcs
,而不是为每个承诺添加额外的代码块