简体   繁体   English

如何在中间突破承诺链

[英]How to break out of the promise chain in the middle

Here is my sample code. 这是我的示例代码。

Orchestrator calls the worker with couple of inputs first, upon getting the response, it has to validate whether the response was satisfactory or not. Orchestrator首先用几个输入呼叫工作人员,获得响应后,必须验证响应是否令人满意。

If satisfactory, just return to the caller. 如果满意,请返回给呼叫者。

If not, again, call the same worker or may be different worker with slightly different input and follow the flow. 如果不是,请再次致电相同的工作人员,也可以是其他工作人员,输入稍有不同,然后按照流程进行操作。

Here, although, my code calls cb() after the first worker call, it's also going to the second then and errors out "response" is undefined etc.. 在这里,尽管我的代码在第一个工作程序调用之后调用cb(),但也将在第二个工作程序调用之后调用,并且未定义“响应”错误。

I could add an extra condition to check whether the 1st response was satisfactory, like need2ndworkercall && validate(response) in 2nd then and get away with it. 我可以添加一个额外的条件来检查第一个响应是否令人满意,例如第二个中的need2ndworkercall && validate(response)并摆脱它。 But wondering what is the right way of dealing with this problem. 但是想知道什么是解决这个问题的正确方法。 Appreciate any feedback. 感谢任何反馈。

  function orchestrateSomething(input, cb){
    doSomething(input.a, input.b)
      .then(response=>{
        if(validate(response)){
          cb(buildResultObj(response));
        }
        else{
          return doSomething(input.a)
        }
      })
      .then(response=>{
        if(validate(response)){
          cb(buildResultObj(response));
        }
        else{
          cb(null,{});
        }
      })
      .catch(error=>cb(error));
  }

return value from function and .then() . 从函数和.then() return值。 Also cb function should call passed function which returns value or evaluate parameters and return value passed 此外, cb函数应调用传递的函数,该函数返回值或评估参数并返回传递的值

  function orchestrateSomething(input, cb){
    return doSomething(input.a, input.b)
      .then(response=>{
        if(validate(response)){
          return cb(buildResultObj(response));
        }
        else{
          return doSomething(input.a)
        }
      })
      .then(response=>{
        if(validate(response)){
          return cb(buildResultObj(response));
        }
        else{
          return cb(null,{});
        }
      })
      .catch(error=>cb(error));
  }

  orchestrateSomething(input, cb) // where `cb` calls function or values passed
  .then(function(results) {
    console.log(results)
  })
  .catch(function(err) {
    console.log(err)
  });

It is possible break the promise chain via simple throw . 可以通过简单的throw打破承诺链。 The trick is to handle it properly on the catch call: 诀窍是在catch调用中正确处理它:

doPromise(...)
  .then(...)
  .then(result => {
    if(condition) {
      throw result
    }
    else {
      return doPromise()
    }
  })
  .then(...)
  .catch(result => {
    if(result instanceof Error) {
      // handle error result
    }
    else {
      // handle desired result
    }
  })

Here's the simpliest demo of such approach: http://plnkr.co/edit/H7K5UsZIueUY5LdTZH2S?p=preview 这是这种方法的最简单演示: http ://plnkr.co/edit/H7K5UsZIueUY5LdTZH2S?p=preview

By the way, if you can generalize then processing function, it becomes possible to make a recursive call: 顺便说一句,如果你能概括then处理功能,可以进行递归调用:

processCB = (result) => {
  if(condition) {
    throw result
  }
  else {
    return doPromise()
  }
}

catchCB = (result) => {
  if(result instanceof Error) {
    // handle error result
  }
  else {
    // handle desired result
  }
}

doProcess = () => doPromise()
  .then(processCB)
  .catch(catchCB)

And here's the demo for the second piece: http://plnkr.co/edit/DF28KgBOHnjopPaQtjPl?p=preview 这是第二部分的演示: http : //plnkr.co/edit/DF28KgBOHnjopPaQtjPl?p=preview

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM