应该由Promise调用同步代码.然后创建一个新的Promise

Should synchronous code called by Promise .then create a new Promise

本文关键字:Promise 一个 然后 调用 同步 代码 创建      更新时间:2023-09-26

我已经实现了一些代码,其中异步代码后面跟着一些同步函数。例如:

function processSomeAsyncData() {
  asyncFuncCall()
    .then(syncFunction)
    .catch(error);
}

如果我理解正确的话,then也是一个承诺。那么,我是否也应该在同步代码中创建promise?

function syncFunction() {
  const p = new Promise (function (resolve, reject) {
    //Do some sync stuff
    ...
    resolve(data);
  }
  return p;
}

如果没有必要,如果发生错误,如何拒绝同步代码中的promise?

您不需要显式创建新的promise。有一个更简单的方法。

这个例子是人为的,因为它永远不会失败,但关键是你不必创建一个承诺,也不必返回一个决心(val(。

function syncFunction() {
  var j = "hi"
  if(j){
    return j;
  }
  return new Error('i am an error');
}

这将起作用:

asyncFunction()
  .then(syncFunction);

但如果你反过来做:

syncFunction()
  .then(asyncFunction);

您必须将syncFunction定义为:

function syncFunction() {
  var j = "hi"
  return new Promise((resolve, reject) => {
    if(j){
      return resolve(j);
    }
    return reject('error');
  })  
}

编辑:为了向所有不相信的人证明,在你的电脑上给这个家伙一个本地的机会。证明你有这么多选择。:(

var Promise = require('bluebird');

function b(h) {
    if(h){
        return h;
    }
    return Promise.resolve('hello from b');
}
function a(z) {
    return new Promise((resolve, reject)=> {
        if(z){return resolve(z)};
        return resolve('hello from a');
    })
}
a().then(b).then(x => console.log(x)).catch(e => console.log(e));
b().then(a).then(x => console.log(x)).catch(e => console.log(e));

否。同步函数可以从同步代码中调用,并且应该始终同步失败!它们不需要以任何方式遵循异步调用程序。如果发生错误,只需抛出一个错误。试试看:

var asyncFuncCall = () => Promise.resolve();
function syncFunction() {
  throw new Error("Fail");
}
asyncFuncCall()
  .then(syncFunction)
  .catch(e => console.log("Caught: " + e.message));

这是因为传递给.then的函数引发的异常被转换为拒绝它应该返回的承诺。

此外,传递给.then的函数返回的任何值都将转换为使用该值解析的promise。调用函数的promise代码负责处理这一问题。

这使您可以毫无问题地混合同步和异步代码:

asyncFuncCallOne()
  .then(() => {
    var x = syncFunction();
    return asyncFuncCallTwo(x);
  })
  .catch(e => console.log(e.message));

它是可选的。

如果从syncFunction返回promise,则只有在新promise解析后,原始promise才会解析,并且新promise返回的任何值都将传递给链中的下一个then

如果返回非Promise值,则该值将传递给链中的下一个then

要从syncFunction中拒绝,只需抛出一个异常即可。