问题描述:

What is the most concise way to run a dynamically generated sequence of functions, where each function returns a Promise which must be resolved before the next should run?

For example:

// Assume the following 'process' functions are generated elsewhere

function process_1 (input) {

return new Promise(function (resolve, reject) {

resolve(input + '_1');

});

}

function process_2 (input) {

return new Promise(function (resolve, reject) {

resolve(input + '_2');

});

}

function process_3 (input) {

return new Promise(function (resolve, reject) {

resolve(input + '_3');

});

}

// We can construct a sequence of these functions,

// but each one still needs to be 'configured' with a value

// before it can return it's promise.

var process = [process_1, process_2, process_3]

The collection methods available on Bluebirds Promise (eg all, each etc) seems to deal with collections of values, rather than collections of promise generating functions.

If I try and map or reduce the sequence into a sequence of promises rather than functions, then I lose the ability of passing the result of one promise into the next?

网友答案:

You can use reduce for this:

bluebird.reduce( [process_1, process_2, process_3], function ( input, next ) {                                                                                                                                     
    return next( input );
}, 'INPUT' ).then( function ( result ) { 
    console.log( result );
} );

Note: You're also missing an input argument for process_2 and process_3 that must be added for this to work.

function process_1 (input) {
    return new Promise(function (resolve, reject) {
        resolve(input + '_1');
    });
}

function process_2 ( input ) {
    return new Promise(function (resolve, reject) {
        resolve(input + '_2');
    });
}

function process_3 ( input ) {
    return new Promise(function (resolve, reject) {
        resolve(input + '_3');
    });
}

bluebird.reduce( [process_1, process_2, process_3], function ( input, next ) {
    return next( input );                                                                                                                                                                                          
}, 'INPUT' ).then( function ( result ) {
    console.log( result );
} );

// INPUT_1_2_3
网友答案:

Here is an alternative non-bluebird-specific way:

var p = arrayOfFns.reduce((p, c) => p.then(c), Promise.resolve('INPUT'));
p.then(console.log);
相关阅读:
Top