【发布时间】:2017-12-12 20:18:36
【问题描述】:
jQuery.Deferred.prototype.then 我遇到了麻烦,
所以我决定看看 jQuery 的测试套件来检查我是否
正确理解此方法的行为。
与我的问题最相关的测试如下,来自
发布 3.2.1:
https://github.com/jquery/jquery/blob/3.2.1/test/unit/deferred.js#L133-L168
注意:
-
Deferred对象在第 153 行被拒绝。 -
done在第 144 和 164 行被调用。 我对 QUnit 不是很熟悉,但很清楚 我认为测试将失败,除非 传递给done的回调实际上会被执行。 - 当且仅当
Deferred对象时,才应该执行传递给done的回调 已解决,未拒绝。 (这是我对Deferred的理解 documentation, 无论如何。)
但以上3点不可能全对!
对done 的两次调用都是在由返回的对象上进行的
jQuery.Deferred.prototype.then。我可以解释
代码如果我假设,在then返回的Promise对象中,
最终状态与原状态不同
Deferred。但是,我在 jQuery 中找不到任何提示
文档。
让我的问题尽可能简短:何时
我上面链接的代码被执行,是回调
传递给done 执行的,如果是,为什么?
更新
这是我在上面链接的代码(添加了一些 cmets 来指示行号):
QUnit.test( "jQuery.Deferred.then - filtering (fail)", function( assert ) {
assert.expect( 4 );
var value1, value2, value3,
defer = jQuery.Deferred(),
piped = defer.then( null, function( a, b ) {
return a * b;
} ),
done = jQuery.map( new Array( 3 ), function() { return assert.async(); } );
piped.done( function( result ) { // Line 144
value3 = result;
} );
defer.fail( function( a, b ) {
value1 = a;
value2 = b;
} );
defer.reject( 2, 3 ).then( null, function() { // Line 153
assert.strictEqual( value1, 2, "first reject value ok" );
assert.strictEqual( value2, 3, "second reject value ok" );
assert.strictEqual( value3, 6, "result of filter ok" );
done.pop().call();
} );
jQuery.Deferred().resolve().then( null, function() {
assert.ok( false, "then should not be called on resolve" );
} ).then( done.pop() );
jQuery.Deferred().reject().then( null, jQuery.noop ).done( // Line 164
function( value ) {
assert.strictEqual( value, undefined, "then fail callback can return undefined/null" );
done.pop().call();
} );
} );
更新 2
事实证明,then 的行为随着 2016 年 6 月 jQuery 3 的发布而改变。根据一个
post
在 jQuery 博客上,宣布新版本:
.then() 创建的 Deferred 的解析状态现在由 它的回调——异常变成拒绝值和不可返回的返回 成为履行价值。以前,从拒绝处理程序返回 变成了拒绝值。
then 的 documentation 尚未更新。
标签: javascript jquery jquery-deferred