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

用可读的函数名展平promise链

杜海
2023-03-14

我在处理promise链中的多个捕获中看到了promise实现,它产生了一个非常可读的链

return validateInput
                 .then(checkLoginPermission)
                 .then(checkDisableUser)
                 .then(changePassword);

但是,为了做到这一点,每个函数都需要返回一个值,而不是Promise?因为Promise可以解析为值或Promise,所以这不是问题。我的目标是让每个函数都具有可读的清晰逻辑。

尝试解除嵌套的promise函数时会出现问题

return validateInput
       .then(function(resultA) {
            return checkLoginPermission
               .then (function(resultB) {
                   // Do something with resultA
               })
       });

想象一下,原始实现涉及访问先前promise中的值。有了嵌套的promise,它很容易实现。但如果是扁平链,我需要像这样分解每个功能

function validateInput = function (resultA ) {
        return Promise.resolve({resultA : resultA, resultB : 
}
function checkLoginPermission = function (mix ) {
        let resultA = mix.resultA;
        let resultB = mix.resultB
        //Do something with resultA
        ... 
}

当链中的最后一个函数从一开始就依赖某个东西时,情况会更糟。这意味着即使未使用该值,也必须从链的开头向下传递该值。

那么,我是否无意中踩到了某种可能影响性能的反模式?否则,我怎样才能在没有这些麻烦的情况下获得良好的可读性?

共有3个答案

宦飞
2023-03-14

内部。然后(/*…*/)回调可以返回原语值或解析为某个值的promise。如果这是另一个promise,那么下一个promise将不会开始,直到内心的promise得到解决。本质上,promise总是解析为非promise类型。如果您解决或返回另一个promise,它将自动取消包装。

单于轶
2023-03-14

Promises是一种模式,与函数式编程相关,直接将数据从一个函数传递到另一个函数是基本的(它被称为compose,这里的例子是:http://scott.sauyet.com/Javascript/Talk/Compose/2013-05-22/)。所以这绝不是反模式

我看不出这种模式有什么问题。您可以将任何想要的数据传递给下一个promise,并在嵌套的promise中获取它们需要的数据。它非常透明和清晰:

function validateInput() {
    return Promise.resolve({resultA: 1});
}

function checkLoginPermission(result) {
    return new Promise(function(resolve, reject) {
        // ...
        // code
        // ...
        result.resultB = 2;
        return resolve(result);
    });
}

function checkDisableUser(result) {
    return new Promise(function(resolve, reject) {
        // grab some data from previous function
        let resultB = result.resultB;
        // ...
        // code
        // ...
        result.resultC = 3;
        return resolve(result);
    });
}

function changePassword(result) {
    return new Promise(function(resolve, reject) {
        // grab some data from previous functions
        let resultB = result.resultB;
        let resultC = result.resultC;
        // ...
        // code
        // ...
        result.resultD = resultB * resultC;
        return resolve(result);
    });
}

validateInput()
    .then(checkLoginPermission)
    .then(checkDisableUser)
    .then(changePassword);

此外,您还可以在promise之前声明的某个变量中收集数据,这样您就不必传递结果。但这将破坏promise的功能性。

桑坚
2023-03-14

这实际上就是asyncwait的作用所在。当您需要跨多个异步调用/promise的结果在范围内时,这很好。如果你能用,我会说试试看。

async function foo () {
    const input = await validateInput()
    const hasPermission = await checkLoginPermission(input)
    const result = await checkDisableUser(hasPermission)
    return await changePassword(result)
}

只要将变量按需要传递到函数中即可。只是举个例子。我也有点不确定您是如何设置validateInput的,我认为您需要将wait放在函数调用本身的前面。

如果你不能使用async/wait,我通常会使用你的第二个代码片段,或者在上面定义更高的范围变量:

let resultA
return validateInput
   .then(function(result) {
        resultA = result
        return checkLoginPermission
           .then (function(resultB) {
               // Do something with resultA
           })
   });
 类似资料:
  • 以下是例外的结果: null

  • 我正在使用Q promise库的Node.js应用程序中工作。我有两组promise链,一个用于控制流,另一个用于调用服务方法,我从中检索数据,我的问题是,我需要获取promise链对另一个promise链的返回值。 MyExample.js 在上面的代码中,我调用bookService.getBookById(bookId)并获取书籍。然后我调用bookDetals函数,它是一个promise链

  • 函数参数的默认值 基本用法 在ES6之前,不能直接为函数的参数指定默认值,只能采用变通的方法。 function log(x, y) { y = y || 'World'; console.log(x, y); } log('Hello') // Hello World log('Hello', 'China') // Hello China log('Hello', '') // He

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

  • 我有一个JavaScript数组,如: 如何将单独的内部数组合并为一个: