admin管理员组文章数量:1393065
i use the following code to send an ajax-request every 3 seconds:
var refreshId = setInterval(function() {
$.ajax({
async: true,
url: 'gohere',
dataType: 'text',
cache: false,
timeout: 5000,
success: function(result, textStatus, XMLHttpRequest) {
alert('textStatus: ' + textStatus + ",\nXHR.readyState: " + XMLHttpRequest.readyState + ",\nXHT.status: " + XMLHttpRequest.status);
},
error: function(XMLHttpRequest, textStatus, errorThrown) {
alert('textStatus: ' + textStatus + ",\nXHR.readyState: " + XMLHttpRequest.readyState + ",\nXHT.status: " + XMLHttpRequest.status);
}
});
}, 3000);
The problem is, that even if the home-server is not accessible (eg not connected to the LAN) the success-function will be called instead of the error-function with a "timeout"-status (tested on Ubuntu 10.04 with FireFox 3.6.7).
(Without periodic requests it will work fine: On timeouts the error-function is called with the correct 'timeout'-statusText.)
The success-alert-function will show the following text on timeouts:
textStatus: success, XHR.readyState: 4, XHR.status: 0So i need to use the XHR.status-value, which should be 200 on success, to determine errors. Is this the normal behaviour or did i something wrong?
i use the following code to send an ajax-request every 3 seconds:
var refreshId = setInterval(function() {
$.ajax({
async: true,
url: 'gohere',
dataType: 'text',
cache: false,
timeout: 5000,
success: function(result, textStatus, XMLHttpRequest) {
alert('textStatus: ' + textStatus + ",\nXHR.readyState: " + XMLHttpRequest.readyState + ",\nXHT.status: " + XMLHttpRequest.status);
},
error: function(XMLHttpRequest, textStatus, errorThrown) {
alert('textStatus: ' + textStatus + ",\nXHR.readyState: " + XMLHttpRequest.readyState + ",\nXHT.status: " + XMLHttpRequest.status);
}
});
}, 3000);
The problem is, that even if the home-server is not accessible (eg not connected to the LAN) the success-function will be called instead of the error-function with a "timeout"-status (tested on Ubuntu 10.04 with FireFox 3.6.7).
(Without periodic requests it will work fine: On timeouts the error-function is called with the correct 'timeout'-statusText.)
The success-alert-function will show the following text on timeouts:
textStatus: success, XHR.readyState: 4, XHR.status: 0So i need to use the XHR.status-value, which should be 200 on success, to determine errors. Is this the normal behaviour or did i something wrong? Share Improve this question asked Jul 30, 2010 at 10:27 BiggieBiggie 7,06710 gold badges35 silver badges43 bronze badges
4 Answers
Reset to default 3ponder on moving the setTimeout in the success and error handlers instead and make it asynchronously recursive.
var refreshId = function() {
$.ajax({
async: true,
url: 'gohere',
dataType: 'text',
cache: false,
timeout: 5000,
success: function(result, textStatus, XMLHttpRequest) {
alert('textStatus: ' + textStatus + ",\nXHR.readyState: " + XMLHttpRequest.readyState + ",\nXHT.status: " + XMLHttpRequest.status);
setTimeout(refreshId, 3000);
},
error: function(XMLHttpRequest, textStatus, errorThrown) {
alert('textStatus: ' + textStatus + ",\nXHR.readyState: " + XMLHttpRequest.readyState + ",\nXHT.status: " + XMLHttpRequest.status);
setTimeout(refreshId, 3000);
}
});
};
Thing is, setTimeout and setInterval time is not reliable, especially with alerts. An alert call stalls javascript as long as the alert dialog remains open. Furthermore, setTimeout and setInterval do not interrupt currently running code to guarantee perfect timing, they will wait till the javascript thread has an opening and jump between code executions.
With your previous code setup, you also had a chance that the response of refreshId call 1 will arrive after refreshId call 2 due to the http roundtrip taking an undetermined ammount of time.
By making your setTimeout depend on the response ming in, you get a more stable and transparent result.
Well, messing around with asyncronous function callbacks can get messy :). setInterval()
is one of those, so is .ajax()
.
You should try to use setTimeout()
and just fire the next .ajax()
call when the last has pleted.
(function repeat(){
$.ajax({
async: true,
url: 'gohere',
dataType: 'text',
cache: false,
timeout: 5000,
success: function(result, textStatus, XMLHttpRequest) {
alert('textStatus: ' + textStatus + ",\nXHR.readyState: " + XMLHttpRequest.readyState + ",\nXHT.status: " + XMLHttpRequest.status);
},
error: function(XMLHttpRequest, textStatus, errorThrown) {
alert('textStatus: ' + textStatus + ",\nXHR.readyState: " + XMLHttpRequest.readyState + ",\nXHT.status: " + XMLHttpRequest.status);
},
plete: function(XMLHttpRequest){
setTimeout(repeat, 3000);
}
});
}());
If you are insistent to have an .ajax()
as close as possible to 3
seconds, you can abort your last (possibly running) ajax request before fireing the new one.
Therefore, assign a variable to the return of .ajax()
like
var currentxhr = $.ajax({});
and add a beforeSend
callback into your .ajax()
call. Within that handler call
currentxhr.abort();
That will abort a possibly running request.
Instead of looking at textStatus
use this test: xhr.statusText.toUpperCase() === 'OK'
I ran into a problem with FF 3.6.8 having a xhr.status === 0
on 301 pages. I added the above to my jQuery 1.4.2 in the httpSuccess
function:
return !xhr.status && location.protocol === "file:" ||
// Opera returns 0 when status is 304
( xhr.status >= 200 && xhr.status < 300 ) ||
xhr.status === 304 || xhr.status === 1223 ||
( xhr.status === 0 && xhr.statusText.toUpperCase() === 'OK');
I believe you should look into http://plugins.jquery./project/ajaxqueue which is designed to manage ajax race conditions.
本文标签: javascriptTimeouts on periodic ajax requests with jQueryStack Overflow
版权声明:本文标题:javascript - Timeouts on periodic ajax requests with jQuery - Stack Overflow 内容由网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:http://www.betaflare.com/web/1744773678a2624496.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论