蓝鸟相当于 Q promise.post

Bluebird equivalent of Q promise.post

我目前正在从 Q 迁移到 Bluebird。

我有以下内容来包装对 MongoDB 的调用:

DB.prototype.find = function(collectionName /*, query, projection, opt*/){
    if (arguments.length < 1) {
        return Promise.reject(new _Error("argumentsError", "DB:find expected collection name"));
    }

    var args = new Array(arguments.length);
    args[0] = 'findAsync';
    for (var i=1, l=arguments.length; i<l; i++) {
        args[i] = arguments[i];
    }

    var promise = this.getCollection(collectionName);
    return promise.call.apply(promise, args);
}

我的问题是,对于 Q,我可以简单地使用 .post('findAsync', args) 而不是 promise.call 上的 apply。即使这段代码有效,它也有很多 LOC 只是为了这个。 bluebird 有更好的方法吗?

Even if this code works, its a lot of LOC just for this.

我不认为许多 LOC 来自 .apply() 声明。它将参数复制到非常麻烦的数组,事实上,如果您使用 Q 的 .post() 方法,您将拥有完全相同的 3 行。

如果您真的很在意,可以可以将其缩短为

DB.prototype.find = function(collectionName /*, query, projection, opt*/) {
    if (!arguments.length)
        return Promise.reject(new _Error("argumentsError", "DB:find expected collection name"));

    var args = Array.prototype.slice.call(arguments);
    args[0] = 'findAsync';
    return Promise.prototype.call.apply(this.getCollection(collectionName), args);
}

(虽然这可能有 performance implications)。您可能还想尝试一个简单的

    arguments[0] = 'findAsync';
    return Promise.prototype.call.apply(this.getCollection(collectionName), arguments);

(当然假设是严格模式)。

Is there a better approach with bluebird?

我不这么认为。您的代码注释似乎表明您无论如何都期待三个参数,您可能只想将它们命名为参数并将它们显式传递给 .call().

如果您正在寻找一种真正卓越的方法,请使用带有剩余参数和扩展参数的 ES6:

DB.prototype.find = function(collectionName, ...args) {
    if (!arguments.length)
        return Promise.reject(new _Error("argumentsError", "DB:find expected collection name"));

    return this.getCollection(collectionName).call('findAsync', ...args);
}