[英]Call multiple scripts through ajax. Script 2 should be called only after Script 1 has finished its execution
I have 4 scripts which I want to call one after another through ajax. 我有4个脚本,我想通过ajax一个接一个地调用。
I want to call script_2
only after script_1
has completed execution. 我想在
script_1
完成执行后才调用script_2
。
It means first I want to call script_1
in ajax, display the result of script_1
execution in its respective div and then call second script, show its result in second div and so on. 这意味着首先我要在ajax中调用
script_1
,在其各自的div中显示script_1
执行的结果,然后调用第二个脚本,在第二个div中显示其结果,依此类推。
Currently what I am doing is creating a new ajax call inside the onreadystatechange()
function (in a nested way). 目前我正在做的是在
onreadystatechange()
函数内创建一个新的ajax调用(以嵌套的方式)。
Below is the pseudo-code: 下面是伪代码:
var script1_ajax = new XMLHttpRequest();
script1_ajax.onreadystatechange=function() {
if (script1_ajax.readyState==4 && script1_ajax.status==200) {
document.getElementById('result').innerHTML = script1_ajax.responseText;
//create second ajax request and call it
//similarly create two more nested ajax calls and call it
}
}
I don't think this is the proper way of doing this. 我不认为这是这样做的正确方法。 Please suggest how to do this in a less complicated way.
请以不太复杂的方式建议如何做到这一点。
In two words: abstract and callback: 用两个词来说:抽象和回调:
//abstract the AJAX code
function ajax(url,data,callback){
var xhr = new XHR(...
//the rest of the AJAX setup here
xhr.onreadystatechange=function() {
if (xhr.readyState === 4 && xhr.status === 200) {
callback(xhr.responseText); //execute callback
}
}
xhr.send();
}
function script1(){
//call ajax
ajax('test1.php','somedata',function(returndata){
//this callback gets executed when ajax is done
document.getElementById('result').innerHTML = returndata;
//execute next
script2();
});
}
function script2(){
ajax('test1.php','somedata',function(returndata){
document.getElementById('result').innerHTML = returndata;
script3();
});
}
function script3(){
//and so on...
}
script1(); //execute first
On the otherhand, you can use jQuery.ajax
, which pretty much looks the same way: 另一方面,你可以使用
jQuery.ajax
,它看起来几乎一样:
function script1(){
$.get('url','data',function(data){
$('#result').html(data);
script2();
});
}
function script2(){
$.get('url','data',function(data){
$('#result').html(data);
script3();
});
}
function script3(){
//and so on
}
script1(); //execute first
Likely your best option is using a Javascript library, for example jQuery. 可能你最好的选择是使用Javascript库,例如jQuery。 jQuery has the
jQuery.Deferred()
object which can be used to easily represent a promise (a future result) thus allowing easy chaining of function calls. jQuery具有
jQuery.Deferred()
对象,可用于轻松表示promise(未来结果),从而允许轻松链接函数调用。 Note that $.get()
, for example, returns a Deferred
(see the documentation below in the page). 请注意,
$.get()
返回Deferred
(请参阅下面的文档)。 This article also has a nice solution and a working jsfiddle, but it quites diverges from the Deferred
approach, which is simply a matter of 这篇文章也有一个很好的解决方案和一个工作的jsfiddle,但它与
Deferred
方法有所不同,这只是一个问题
function _get(url, params, success) {
return function() {
return $.get(url, params, success);
}
}
$.get("http://host/1", {}, updateDiv) // see the doc for $.get()
.pipe(_get("http://host/2")) // see $.Deferred() and pipe()
.pipe(_get("http://host/3"))
.pipe(_get("http://host/4"));
If you don't know jQuery, $.get(url, params, callback)
is the way to make asynchronous HTTP GET requests 如果您不了解jQuery,
$.get(url, params, callback)
是进行异步HTTP GET请求的方法
Note: I updated the code, since deferred.then()
requires a callback (I gave it a promise) and replaced then()
with pipe()
, which gives the intended behavior on current jQuery versions (actually in 1.8 it seems then()
is an alias to the current pipe()
) 注意:我更新了代码,因为
deferred.then()
需要一个回调(我给它一个promise)并用pipe()
代替then()
pipe()
,它给出了当前jQuery版本的预期行为(实际上在1.8当时似乎是then()
是当前pipe()
的别名)
You could just do it this way. 你可以这样做。 Say you had to load three scripts and the third has a callback.
假设您必须加载三个脚本,第三个脚本具有回调。
$.get("js/ext/flowplayer-3.2.8.min.js")
.pipe($.get("js/eviflowplayer.js"))
.pipe($.get("js/evi.flowplayer.js", {}, function()
{
W.EVI.FLOWPLAYER.init(elem.attr('id'));
});
There are more examples using $.getScript()
. 还有更多使用
$.getScript()
示例 。
Well actually is quite proper (idea), you can of course use jQuery and its async option in ajax call to force it be synced ( http://api.jquery.com/jQuery.ajax/ ), or do the same thing as in our code by using success()
callback handling. 实际上是非常合适的(想法),你当然可以在ajax调用中使用jQuery及其async选项来强制它同步( http://api.jquery.com/jQuery.ajax/ ),或者做同样的事情在我们的代码中使用
success()
回调处理。
As go for code of this request, I am sure you are aware it fail on some browsers? 至于这个请求的代码,我相信你知道它在某些浏览器上失败了吗? and it looks bad as you got to invoke same set of functions twice, try to put them into functions, maybe wrap whole ajax request in some class/JSON.
它看起来很糟糕,因为你需要两次调用相同的函数集,尝试将它们放入函数中,也许在一些类/ JSON中包装整个ajax请求。
third option is that you force sync mode yourself with setTimeout()
/ clearTimeout()
implementation or setInterval()
but it is not a way I would recommend. 第三个选项是你自己用
setTimeout()
/ clearTimeout()
实现或setInterval()
强制同步模式,但这不是我推荐的方式。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.