Dengan menggunakan jQuery, bagaimana saya bisa cancel/batalkan permintaan Ajax bahwa saya belum menerima respon dari?
Sebagian besar jQuery Ajax metode kembali XMLHttpRequest (atau setara) objek, sehingga anda hanya dapat menggunakan abort()
.
Lihat dokumentasi:
var xhr = $.ajax({
type: "POST",
url: "some.php",
data: "name=John&location=Boston",
success: function(msg){
alert( "Data Saved: " + msg );
}
});
//kill the request
xhr.abort()
UPDATE: Sebagai jQuery 1.5 kembali objek pembungkus asli object XMLHttpRequest yang disebut jqXHR. Objek ini muncul untuk mengekspos semua pribumi properti dan metode sehingga contoh di atas masih bekerja. Melihat The jqXHR Objek (jQuery dokumentasi API).
UPDATE 2:
Sebagai jQuery 3, metode ajax sekarang kembali janji dengan metode ekstra (seperti abort), sehingga kode di atas masih bekerja, meskipun objek yang dikembalikan tidak xhr
lagi. Lihat 3.0 blog here.
PERBARUI 3: xhr.abort()
masih bekerja pada jQuery 3.x. Don't mengasumsikan update 2 adalah benar. Info lebih lanjut tentang jQuery repositori Github.
Anda dapat't mengingat permintaan tetapi anda dapat menetapkan nilai timeout setelah respon akan diabaikan. Melihat ini halaman untuk jquery AJAX pilihan. Saya percaya bahwa kesalahan anda callback yang akan dipanggil jika batas waktu telah terlampaui. Sudah ada default timeout pada setiap permintaan AJAX.
Anda juga dapat menggunakan abort() metode pada objek permintaan tetapi, sementara itu akan menyebabkan klien untuk berhenti mendengarkan untuk acara, <menyerang>mungkin</strike> mungkin tidak akan menghentikan server dari pemrosesan itu.
It's asynchronous permintaan, yang berarti setelah itu's yang dikirim itu's di luar sana.
Dalam kasus server anda mulai operasi yang sangat mahal karena permintaan AJAX, yang terbaik yang dapat anda lakukan adalah membuka server anda untuk mendengarkan untuk membatalkan permintaan, dan mengirim terpisah AJAX permintaan memberitahukan server untuk menghentikan apapun itu's lakukan.
Jika tidak, mengabaikan AJAX respon.
Menyimpan panggilan yang anda buat dalam array, kemudian memanggil xhr.abort() pada masing-masing.
BESAR PERINGATAN: Anda dapat membatalkan permintaan, tapi yang's hanya sisi klien. Sisi server masih bisa memproses permintaan. Jika anda menggunakan sesuatu seperti PHP atau ASP dengan data sesi, sesi data terkunci sampai ajax telah selesai. Jadi, untuk memungkinkan pengguna untuk melanjutkan browsing web, anda harus menghubungi session_write_close(). Ini menghemat sesi dan membuka sehingga halaman-halaman lain yang menunggu untuk terus akan dilanjutkan. Tanpa ini, beberapa halaman dapat menunggu kunci untuk dihapus.
Permintaan AJAX mungkin tidak lengkap dalam urutan mereka mulai. Bukan membatalkan, anda dapat memilih untuk ignore semua AJAX tanggapan kecuali untuk yang terakhir:
Garis besar kode:
var xhrCount = 0;
function sendXHR() {
// sequence number for the current invocation of function
var seqNumber = ++xhrCount;
$.post("/echo/json/", { delay: Math.floor(Math.random() * 5) }, function() {
// this works because of the way closures work
if (seqNumber === xhrCount) {
console.log("Process the response");
} else {
console.log("Ignore the response");
}
});
}
sendXHR();
sendXHR();
sendXHR();
// AJAX requests complete in any order but only the last
// one will trigger "Process the response" message
[Demo jsFiddle][1]
Kami hanya harus bekerja di sekitar masalah ini dan diuji tiga pendekatan yang berbeda.
var Ajax1 = {
call: function() {
if (typeof this.xhr !== 'undefined')
this.xhr.abort();
this.xhr = $.ajax({
url: 'your/long/running/request/path',
type: 'GET',
success: function(data) {
//process response
}
});
}
};
var Ajax2 = {
counter: 0,
call: function() {
var self = this,
seq = ++this.counter;
$.ajax({
url: 'your/long/running/request/path',
type: 'GET',
success: function(data) {
if (seq === self.counter) {
//process response
}
}
});
}
};
var Ajax3 = {
active: false,
call: function() {
if (this.active === false) {
this.active = true;
var self = this;
$.ajax({
url: 'your/long/running/request/path',
type: 'GET',
success: function(data) {
//process response
},
complete: function() {
self.active = false;
}
});
}
}
};
$(function() {
$('#button').click(function(e) {
Ajax3.call();
});
})
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<input id="button" type="button" value="click" />
Dalam kasus kami, kami memutuskan untuk menggunakan pendekatan #3 karena menghasilkan lebih sedikit beban bagi server. Tapi saya tidak 100% yakin jika jQuery adalah panggilan .lengkap()-metode ini bisa menghasilkan kebuntuan situasi. Dalam pengujian kami, kami tidak bisa mereproduksi situasi seperti ini.
Yang terbaik adalah selalu berlatih untuk melakukan sesuatu seperti ini.
var $request;
if ($request != null){
$request.abort();
$request = null;
}
$request = $.ajax({
type : "POST", //TODO: Must be changed to POST
url : "yourfile.php",
data : "data"
}).done(function(msg) {
alert(msg);
});
Tapi itu jauh lebih baik jika anda memeriksa jika pernyataan untuk memeriksa apakah permintaan ajax adalah null atau tidak.
meouw's solusi adalah benar, tetapi jika anda're tertarik pada kontrol lebih besar maka anda bisa mencoba Manajer Ajax plugin untuk jQuery.
Sebut saja xhr.abort() apakah itu's jquery ajax objek atau asli object XMLHTTPRequest.
contoh:
//jQuery ajax
$(document).ready(function(){
var xhr = $.get('/server');
setTimeout(function(){xhr.abort();}, 2000);
});
//native XMLHTTPRequest
var xhr = new XMLHttpRequest();
xhr.open('GET','/server',true);
xhr.send();
setTimeout(function(){xhr.abort();}, 2000);
Saya melakukan live mencari solusi dan dibutuhkan untuk membatalkan permintaan tertunda yang mungkin telah mengambil lebih lama dari yang terbaru/paling permintaan saat ini.
Dalam kasus saya saya menggunakan sesuatu seperti ini:
//On document ready
var ajax_inprocess = false;
$(document).ajaxStart(function() {
ajax_inprocess = true;
});
$(document).ajaxStop(function() {
ajax_inprocess = false;
});
//Snippet from live search function
if (ajax_inprocess == true)
{
request.abort();
}
//Call for new request
Banyak orang-orang di thread telah mencatat, hanya karena permintaan dibatalkan pada sisi client, server masih akan memproses permintaan. Hal ini menciptakan beban yang tidak perlu pada server karena itu's melakukan pekerjaan yang kita've berhenti mendengarkan pada front-end.
Masalah saya mencoba untuk memecahkan (yang lain dapat menjalankan ke dalam serta) adalah bahwa ketika pengguna memasukkan informasi dalam bidang masukan, saya ingin api dari permintaan untuk Google Instan tipe merasa.
Untuk menghindari menembak permintaan yang tidak perlu dan untuk menjaga snappiness dari front-end, yang saya lakukan sebagai berikut:
var xhrQueue = [];
var xhrCount = 0;
$('#search_q').keyup(function(){
xhrQueue.push(xhrCount);
setTimeout(function(){
xhrCount = ++xhrCount;
if (xhrCount === xhrQueue.length) {
// Fire Your XHR //
}
}, 150);
});
Ini pada dasarnya akan mengirim satu permintaan setiap 150ms (variabel yang bisa anda sesuaikan untuk kebutuhan anda sendiri). Jika anda're memiliki kesulitan memahami apa yang sebenarnya terjadi di sini, log xhrCount
dan xhrQueue
untuk konsol sebelum jika blok.
Hanya menggunakan ajax.abort() sebagai contoh anda bisa batalkan pending permintaan ajax sebelum mengirim satu sama lain seperti ini
//check for existing ajax request
if(ajax){
ajax.abort();
}
//then you make another ajax request
$.ajax(
//your code here
);
tidak ada cara yang dapat diandalkan untuk melakukan hal itu, dan saya bahkan tidak akan mencoba itu, setelah permintaan pada pergi; hanya cara untuk bereaksi cukup untuk abaikan respon.
dalam kebanyakan kasus, hal itu mungkin terjadi dalam situasi seperti: pengguna mengeklik terlalu sering pada tombol yang memicu banyak berturut-turut XHR, di sini anda memiliki banyak pilihan, baik blok tombol sampai XHR dikembalikan, atau bahkan tidak memicu baru XHR sementara yang lain berjalan mengisyaratkan pengguna untuk bersandar kembali atau membuang apapun yang tertunda XHR respon tapi baru-baru ini.
Anda dapat membatalkan setiap terus menerus ajax call dengan menggunakan ini
<input id="searchbox" name="searchbox" type="text" />
<script src="http://code.jquery.com/jquery-1.11.0.min.js"></script>
<script type="text/javascript">
var request = null;
$('#searchbox').keyup(function () {
var id = $(this).val();
request = $.ajax({
type: "POST", //TODO: Must be changed to POST
url: "index.php",
data: {'id':id},
success: function () {
},
beforeSend: function () {
if (request !== null) {
request.abort();
}
}
});
});
</script>
Kode berikut menunjukkan memulai serta membatalkan permintaan Ajax:
function libAjax(){
var req;
function start(){
req = $.ajax({
url: '1.php',
success: function(data){
console.log(data)
}
});
}
function stop(){
req.abort();
}
return {start:start,stop:stop}
}
var obj = libAjax();
$(".go").click(function(){
obj.start();
})
$(".stop").click(function(){
obj.stop();
})
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<input type="button" class="go" value="GO!" >
<input type="button" class="stop" value="STOP!" >
Aku punya masalah pemungutan suara dan setelah halaman ditutup jajak pendapat terus sehingga menyebabkan pengguna akan melewatkan update seperti mysql nilai yang ditetapkan untuk selanjutnya 50 detik setelah halaman penutupan, meskipun aku membunuh ajax request, saya pikir jauh sekitar, menggunakan $_SESSION untuk mengatur var won't pembaruan dalam jajak pendapat diri hingga berakhir dan yang baru dimulai, jadi yang saya lakukan adalah menetapkan nilai di database saya sebagai 0 = offpage , sementara aku'm polling saya query yang baris dan return false; ketika's 0 sebagai query di polling akan mendapatkan anda saat ini nilai-nilai yang jelas...
Saya harap ini membantu
Saya telah berbagi [demo][1] yang menunjukkan bagaimana untuk membatalkan permintaan AJAX-- jika data tidak dikembalikan dari server dalam waktu yang telah ditetapkan menunggu waktu.
HTML :
<div id="info"></div>
KODE: JS
var isDataReceived= false, waitTime= 1000;
$(function() {
// Ajax request sent.
var xhr= $.ajax({
url: 'http://api.joind.in/v2.1/talks/10889',
data: {
format: 'json'
},
dataType: 'jsonp',
success: function(data) {
isDataReceived= true;
$('#info').text(data.talks[0].talk_title);
},
type: 'GET'
});
// Cancel ajax request if data is not loaded within 1sec.
setTimeout(function(){
if(!isDataReceived)
xhr.abort();
},waitTime);
});