在javascript中干掉承诺

时间:2016-07-29 01:49:35

标签: javascript node.js promise generator

我在运行在api上的节点v6.3.0中有以下代码,该api运行两个单独的promise,具体取决于POST请求中是否存在param的条件。

if (paramExists) {
    // call database with this query
    User.filter(/* do something with param */)
        .then(function (user) {
            Data.filter(/* same in both conditions */)
                .then(function (data) {
                    // join data and user
                    res.send(joinedData);
                })  // omit catch for clarity
        })  // omit catch for clarity
} else {
    // call database with this query
    User.filter(/* do something with header */)
        .then(function (user) {
            Data.filter(/* same in both conditions */)
                .then(function (data) {
                    // join data and user
                    res.send(joinedData);
                })  // omit catch for clarity
        })  // omit catch for clarity
}

我确信有一种方法可以干掉这段代码,这样两种情况下的第一个承诺都会将用户传递给第二个承诺,但我无法弄清楚如何。我应该使用发电机,还是有办法用我没有得到的承诺?

3 个答案:

答案 0 :(得分:2)

您可以执行以下操作。我假设Data.filter也会返回一个承诺。

if (paramExists) {
    // call database with this query
    User.filter(/* do something with param */)
        .then(sameCondition);  // omit catch for clarity
} else {
    // call database with this query
    User.filter(/* do something with header */)
        .then(sameCondition);  // omit catch for clarity
}

function sameCondition(user) {
  return Data.filter(/* same in both conditions */)
    .then(function (data) {
      // join data and user
      res.send(joinedData);
  });  // omit catch for clarity
}

答案 1 :(得分:2)

由于两个分支之间似乎不同的唯一部分是传递给User.filter()的部分,因此可以将该值放入条件中的局部变量中,然后使用变量运行一个版本的代码。

您也可以简化链接方法以删除不必要的嵌套:

var arg; 
if (paramExists) {
    arg = ...     // some logic
} else {
    arg = ...     // some different logic
}
// call database with this query
User.filter(arg).then(function (user) {
    return Data.filter(...);
}).then(function (data) {
    // join data and user
    res.send(joinedData);
});  // omit catch for clarity

你也可以使用三元:

var arg = paramExists ? someLogic : someOtherLogic;
// call database with this query
User.filter(arg).then(function (user) {
    return Data.filter(...);
}).then(function (data) {
    // join data and user
    res.send(joinedData);
});  // omit catch for clarity

如果您需要同时访问userdata来发送回复(在您的伪代码中有点难以辨别),那么您可以保留您的嵌套:

var arg = paramExists ? someLogic : someOtherLogic;
// call database with this query
User.filter(arg).then(function (user) {
    return Data.filter(...).then(function(data) {
        // join data and user
        res.send(joinedData);
    });
});  // omit catch for clarity

答案 2 :(得分:1)

做这样的事......

var task1 = paramExists ? 
   User.filter(/* do something with param */) :
   User.filter(/* do something with header */)

var doFilter = task1.then(function () {
   return Data.filter(/* same in both conditions */)
})

doFilter.then(function (joinedData) {
   res.send(joinedData);
});