mirror of
https://github.com/jquery/jquery.git
synced 2026-02-01 06:04:57 -05:00
Ajax: trigger error callback on native abort
- IE9 does not have onabort. Use onreadystatechange instead. Fixes gh-2079 Close gh-2684
This commit is contained in:
@@ -25,7 +25,7 @@ support.cors = !!xhrSupported && ( "withCredentials" in xhrSupported );
|
||||
support.ajax = xhrSupported = !!xhrSupported;
|
||||
|
||||
jQuery.ajaxTransport( function( options ) {
|
||||
var callback;
|
||||
var callback, errorCallback;
|
||||
|
||||
// Cross domain only allowed if supported through XMLHttpRequest
|
||||
if ( support.cors || xhrSupported && !options.crossDomain ) {
|
||||
@@ -72,17 +72,26 @@ jQuery.ajaxTransport( function( options ) {
|
||||
callback = function( type ) {
|
||||
return function() {
|
||||
if ( callback ) {
|
||||
callback = xhr.onload = xhr.onerror = null;
|
||||
callback = errorCallback = xhr.onload =
|
||||
xhr.onerror = xhr.onabort = xhr.onreadystatechange = null;
|
||||
|
||||
if ( type === "abort" ) {
|
||||
xhr.abort();
|
||||
} else if ( type === "error" ) {
|
||||
complete(
|
||||
|
||||
// File: protocol always yields status 0; see #8605, #14207
|
||||
xhr.status,
|
||||
xhr.statusText
|
||||
);
|
||||
// Support: IE9
|
||||
// On a manual native abort, IE9 throws
|
||||
// errors on any property access that is not readyState
|
||||
if ( typeof xhr.status !== "number" ) {
|
||||
complete( 0, "error" );
|
||||
} else {
|
||||
complete(
|
||||
|
||||
// File: protocol always yields status 0; see #8605, #14207
|
||||
xhr.status,
|
||||
xhr.statusText
|
||||
);
|
||||
}
|
||||
} else {
|
||||
complete(
|
||||
xhrSuccessStatus[ xhr.status ] || xhr.status,
|
||||
@@ -103,7 +112,31 @@ jQuery.ajaxTransport( function( options ) {
|
||||
|
||||
// Listen to events
|
||||
xhr.onload = callback();
|
||||
xhr.onerror = callback( "error" );
|
||||
errorCallback = xhr.onerror = callback( "error" );
|
||||
|
||||
// Support: IE9
|
||||
// Use onreadystatechange to replace onabort
|
||||
// to handle uncaught aborts
|
||||
if ( xhr.onabort !== undefined ) {
|
||||
xhr.onabort = errorCallback;
|
||||
} else {
|
||||
xhr.onreadystatechange = function() {
|
||||
|
||||
// Check readyState before timeout as it changes
|
||||
if ( xhr.readyState === 4 ) {
|
||||
|
||||
// Allow onerror to be called first,
|
||||
// but that will not handle a native abort
|
||||
// Also, save errorCallback to a variable
|
||||
// as xhr.onerror cannot be accessed
|
||||
window.setTimeout( function() {
|
||||
if ( callback ) {
|
||||
errorCallback();
|
||||
}
|
||||
} );
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
// Create the abort callback
|
||||
callback = callback( "abort" );
|
||||
|
||||
@@ -38,7 +38,7 @@ QUnit.module( "ajax", {
|
||||
);
|
||||
|
||||
ajaxTest( "jQuery.ajax() - success callbacks", 8, function( assert ) {
|
||||
return {
|
||||
return {
|
||||
setup: addGlobalEvents( "ajaxStart ajaxStop ajaxSend ajaxComplete ajaxSuccess", assert ),
|
||||
url: url( "data/name.html" ),
|
||||
beforeSend: function() {
|
||||
@@ -437,6 +437,25 @@ QUnit.module( "ajax", {
|
||||
};
|
||||
} );
|
||||
|
||||
ajaxTest( "jQuery.ajax() - native abort", 2, function( assert ) {
|
||||
return {
|
||||
url: url( "data/name.php?wait=1" ),
|
||||
xhr: function() {
|
||||
var xhr = new window.XMLHttpRequest();
|
||||
setTimeout( function() {
|
||||
xhr.abort();
|
||||
}, 100 );
|
||||
return xhr;
|
||||
},
|
||||
error: function( xhr, msg ) {
|
||||
assert.strictEqual( msg, "error", "Native abort triggers error callback" );
|
||||
},
|
||||
complete: function() {
|
||||
assert.ok( true, "complete" );
|
||||
}
|
||||
};
|
||||
} );
|
||||
|
||||
ajaxTest( "jQuery.ajax() - events with context", 12, function( assert ) {
|
||||
var context = document.createElement( "div" );
|
||||
|
||||
|
||||
Reference in New Issue
Block a user