jQuery $.ajax, error handler doesn't work
Hello I noticed that this simple code doesn't work the way it is supposed to work...
function test() {
$.ajax( {
'url' : 'test/GameConfiguration.json',
'dataType' : 'json',
data : {
a : 'aaa'
},
cache : false,
method : 'get',
timeout : 10000, //10 secs of timeout
success : function(data, textStatus, XMLHttpRequest) {
console.log("success");
if (data == null)
console.log("it's not a real success");
},
error : function(XMLHttpRequest, textStatus, errorThrown) {
console.log("error: " + textStatus);
}
});
}
The test has been run on localhost, I mean: I load the page, I shut down the local webserver, then I fire the request (via a simple button with onclick pointing to this function). Error doesn't ever get called, what I get is to have the success handler called and it has textStatus = "success" and data = null. I even notice that the request times out long before 10 seconds. This happens on Firefox (last version), Chrome (last version) and Safari 5. Why this? Is it due to the fact I'm working on localhost?
I forgot to tell: THE Request isn't cached. In fact both firebug and Chrome dev tools show the request to fail.
Big update
This behaviour is related to the use of localhost. In fact if I load this page from another collegue PC and before triggering the request I disconnect my PC from the network, I correctly get the error handler fired with timeout as status. I think this is a bug of jQuery. It will make me hard to test the timeout errors :(
Guys from jQuery forums say this is due to the way the network stack aborts the connection, given that the host is loca开发者_开发技巧lhost. I tested this on Windows 7 only. If you feel like testing this on other systems and you can work out some jQuery internals, report to this post at the jQuery forums:
http://forum.jquery.com/topic/strange-and-unexpected-behaviour-of-ajax-error-and-localhost#14737000001331961
UPDATED: Try to replace the test (data == null)
to the (XMLHttpRequest.readyState === 4 && XMLHttpRequest.status === 0)
.
In W3C Candidate Recommendation about XMLHttpRequest
standard is described that it must exist so named "error flag" which should be used to indicates some type of network error or abortion. In case of such kind of errors the status in the XMLHttpRequest
will be 0 instead of 200 ("OK"), 201 ("Created"), 304 ("Not Modified") and so on. To be exactly corresponds to http://www.w3.org/TR/XMLHttpRequest/#the-status-attribute the XMLHttpRequest.status
can be 0 in case of XMLHttpRequest.readyState
equal to 0 or 1 ("UNSENT" or "OPENED"). Another case is XMLHttpRequest.readyState
equal to 4 ("DONE") and "error flag" is true. If we have no from these two cases the XMLHttpRequest.status
must be a HTTP status code. Under http://www.w3.org/Protocols/rfc2616/rfc2616-sec10.html or http://www.w3.org/Protocols/HTTP/1.0/spec.html#Status-Codes there are no HTTP status code equal to 0. So it seems to my that you can do following
jQuery(document).ready(function () {
$.ajax({
type: 'GET',
url: 'test/GameConfiguration.json',
dataType: 'json',
cache : false,
success: function(data, textStatus, xhr){
if (xhr.readyState === 4 && xhr.status === 0) {
// if readyState is DONE (numeric value 4) then corresponds to
// http://www.w3.org/TR/XMLHttpRequest/#dom-xmlhttprequest-done
// "The DONE state has an associated error flag that indicates
// some type of network error or abortion."
// Corresponds to http://www.w3.org/TR/XMLHttpRequest/#the-status-attribute
// If error flag it true, xhr.status is 0.
alert('"error flag\" is true. It means that we have a network error"+
" or abortion (for example because of Same Origin Policy restrictions)');
}
else {
alert(textStatus);
alert(data);
}
},
error: function(xhr, textStatus, errorThrown) {
if (textStatus !== null) {
alert("error: " + textStatus);
} else if (errorThrown !== null) {
alert("exception: " + errorThrown.message);
}
else {
alert ("error");
}
}
});
});
If there's a network error the success
callback will be called and not the error
even if it doesn't make much sense. Checkout this blog post for details. So basically what you've done by checking data == null
is correct.
Even if you shut down the local server, it should still be able to see the json file.. try to remove the file temporarily and see if that works.
精彩评论