蓝鸟相当于Q promise.post

时间:2015-09-15 17:46:13

标签: javascript promise bluebird

我目前正在从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)上使用apply而不是promise.call。即使这个代码有效,它的很多LOC也只是为了这个。 蓝鸟有更好的方法吗?

1 个答案:

答案 0 :(得分:1)

  

即使这段代码有效,它也只是为了这个。

我不认为很多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);

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

  

蓝鸟有更好的方法吗?

我不这么认为。您的代码注释似乎表明您无论如何都期望正好有三个参数,您可能只想让它们成为命名参数并将它们明确地传递给.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);
}