我目前在 nodejs 中有一些 js 文件,它们作为模块加载并扩充应用程序对象(使用 express)。
所以他们的签名看起来像:
module.exports = function(app, callback) {
// ...
callback();
}
所以目前我有大约 5 个,我的代码如下所示:
require("./setup/a")(app, function() {
require("./setup/b")(app, function(){
require("./setup/c")(app, function(){
require("./setup/d")(app, function(){
require("./setup/e")(app, function(){
startApp();
})
})
})
})
});
现在它看起来像“厄运金字塔”一样难看,但是我不完全确定我需要如何更改此模式才能使用 Q,因为我假设我会使用 Q.fcall(... a).then(...b).etc.done()
.但是,我不确定如何将应用程序传递给它,以及是否需要返回回调以使其作为 promise 进行处理。
理想情况下,我不想在我的代码中开始重击 Q 我只想在我想删除金字塔用例的地方使用它,所以在上面的示例中,我如何使用带有 promise 的 Q 将应用程序传递到每个必需的模块,然后在最后启动应用程序?
最佳答案
假设您的模块还没有使用 promises,您可以这样做:
module.exports = function(app) {
// do some stuff with app
return new Promise(function(resolve,reject){
// when ready to resolve after some actions on app
resolve(); // you can also return a value here as a cb param
});
};
Promise.all(["./setup/a","./setup/b","./setup/c"].map(require.bind(null,app)))
.then(startApp);
然而,您应该尽可能在最低级别使用 promise,这意味着您可以简单地返回您在该过程中使用的 promise:
module.exports = function(app){
return something(app).then(function(){
return somethingElseAsyncWithApp(app);
});
};
因此不需要 promise 构造函数。请注意,此答案使用 native promise ,但也适用于使用该语法的库,如 Bluebird。对于 Q,将 new Promise
更改为 new Q.Promise
并将 Promise.all
更改为 Q.all
。
或者,您可以将每个 require(x)
更改为 Q.fcall(require,x)
并在其上使用 Q.all
直接,但这既慢(尽管 Q 无论如何也很慢)并且比直接 promise 模块更容易出错。最好 promise 尽可能低级别的 API。
关于javascript - 与 nodejs 中的 q 和 promises 有点混淆,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24982209/