当前位置: 首页 > 知识库问答 >
问题:

在调用promise链后调用Qpromise函数

欧阳博文
2023-03-14

我正在使用Q promise库的Node.js应用程序中工作。我有两组promise链,一个用于控制流,另一个用于调用服务方法,我从中检索数据,我的问题是,我需要获取promise链对另一个promise链的返回值。

MyExample.js

bookService.getBookById(bookId)
  .then(bookDetals)
  .then(function(returnValue) { // <- (A)
    res.send(200, returnValue); // <- (C)
    return returnValue;
  }).catch(function(error) {
    logger.error('Error getting values');
    res.send(500, error);
  });


bookDetals = function(book) {
  myService.retrieveATypeData(book, bookId)
    .then(function(bookData) {
      myService.retrieveBTypeData(bookId)
        .then(function(bdata) {
          bookData[bTypeData] = bdata;
          myService.retrieveCTypeData(bookId)
            .then(function(cdata) {
              bookData[cTypeData] = cdata;
            }).done(function() {
              return bookData; // <- (B)
            })
        });
    });
};

在上面的代码中,我调用bookService.getBookById(bookId)并获取书籍。然后我调用bookDetals函数,它是一个promise链。但我的问题是它在promise链结束之前返回returnValue。如何获取promise链(在第(B)行)的返回值以就地返回(C)。目前它返回之前。所以在C中,它表示未定义。

共有2个答案

秦斌
2023-03-14

你需要回报一个promise:

bookDetals = function(book) {
  return Q.Promise(function(resolve, reject, notify) {
    myService.retrieveATypeData(book, bookId)
        .then(function(bookData) {
          myService.retrieveBTypeData(bookId)
            .then(function(bdata) {
              bookData[bTypeData] = bdata;
              myService.retrieveCTypeData(bookId)
                .then(function(cdata) {
                  bookData[cTypeData] = cdata;
                }).done(function() {
                  resolve(bookData); // <- (B)
                })
            });
        });
  }  
}

延迟是这里讨论的一种反模式。老实说,最好使用polyfill,因为Promise在es6规范中。

柳威
2023-03-14

因为您使用的是Node,所以我将转向ES6promise。如果您当前的版本还不支持ES6promise,我建议您切换到一个库(ES6promise)来为您填充它。使用ES6,您可以执行以下操作:

// mock async promise
const getThing = id => (
  new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve({
        id
      });
    }, 250);
  })
);

// mock async promise
const getDetailsA = thing => {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve(Object.assign({}, thing, {
        a: 'purple'
      }));
    }, 250);
  })
};

// mock async promise
const getDetailsB = thing => (
  new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve(Object.assign({}, thing, {
        b: 'monkey'
      }));
    }, 250);
  })
);

// mock async promise
const getDetailsC = thing => (
  new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve(Object.assign({}, thing, {
        c: 'dishwasher'
      }));
    }, 250);
  })
);

getThing('123')
  .then(getDetailsA)
  .then(getDetailsB)
  .then(getDetailsC)
  .then(console.log)
  .catch(console.error);
 类似资料:
  • 问题内容: 我目前正在尝试诺言,并且有一个非常基本的问题! 在一个Promise链中,调用同步函数是否是错误的做法?例如: 还是应该将我的同步功能重构为也返回承诺? 问题答案: 在一个Promise链中,调用同步函数是否是错误的做法? 不,这根本不是一个坏习惯。这是许多预期和有用的实践之一。 您可以完全自由地(在处理程序中)调用promise链中的同步函数或异步函数,然后再返回新的promise。

  • 知识点 理解 Promise 概念,为什么需要 promise 学习 q 的 API,利用 q 来替代回调函数(https://github.com/kriskowal/q ) 课程内容 第五课(https://github.com/alsotang/node-lessons/tree/master/lesson5 )讲述了如何使用 async 来控制并发。async 的本质是一个流程控制。其实在

  • 我在玩弄promise和回调,想知道如果没有回调被传递,写一个返回promise的函数的正确方法是什么。 我的结果看起来是这样的,但我不确定这是否正确(反模式的意思) 它很简单:创建一个函数,并将“工作”代码包装在一个promise中。如果没有回调传递给我的函数,我返回包装的promise。如果一个回调被传递,我从和 这样可以吗,还是我错过了一些不起作用的特殊情况?

  • 链式调用异步函数。 循环遍历包含异步事件的函数数组,每次异步事件完成后调用 next 。 const chainAsync = fns => { let curr = 0; const next = () => fns[curr++](next); next(); }; chainAsync([ next => { console.log('0 seconds');

  • 我试图用Mocha、Chai和Sinon为我的代码添加更多的测试,但是我很难理解为什么第二个存根函数没有被识别为被调用。 我有一个向用户发送电子邮件的功能(稍后我将测试电子邮件功能-现在我只想处理我控制的存根依赖项) 和测试文件: 我可以用Sinon存根User.findOne()方法,但是当我尝试存根emailLogger.log()方法时,我遇到了麻烦。它似乎调用了存根,而不是真正的方法,而是

  • 我想在一个HTML页面上做一个值,每5秒更新一次,这样就不会让服务器不堪重负。结果表明,我的函数中的setTimeout()没有适当延迟,而是立即被调用。有人能帮我找个线索吗?我真的不想给我的服务器太多的工作,因为我必须实现更多的Ajax。 代码如下: