避免在jQuery中使用async:false的策略?

jQuery文档强烈建议您在执行$.ajax请求时不要将async设置为false

但是,我看到同步问题的常见解决方案涉及到这样做。 然后我看到人们因为反对文档的推荐而受到严厉批评 。

话虽如此,我试图使用一个承诺,以避免使用async:false ,没有运气。

这是我正在使用的代码。 我有一个调用addToOrder的onclick事件:

 function saveTemplate() { var formData = getFormData(); return $.ajax({ type: "POST", url: "/p/session/save/" + sessionid + "/template//", data: formData, async: true, success: function(msg){ var rsp = $.parseJSON(msg); if (rsp.response === 'Saved') { sessionid = rsp.sessionid; $("#save-preview-data-response").html("   " + rsp.response).fadeIn(100).delay(1000).fadeOut(1000); } else { $("#save-preview-data-response").css('color','#ff0000').html("   " + rsp.response).fadeIn(100).delay(1000).fadeOut(1000); } } }); } function addToOrder() { var saved = saveTemplate(); var issaved; saved.success(function(e) { var rsp = $.parseJSON(e); issaved = (rsp.response == 'Saved') ? true : false; }); if(issaved) { $.ajax({ type: "POST", url: "addToOrder/respond/json", data: "sid=" + sessionid, async: true, success: function(msg){ var rsp = $.parseJSON(msg); if (rsp.response === 'Saved') { alert(msg); } } }); } } 

issaved将始终评估为false,因为在saveTemplate有时间运行之前正在评估它。 我找到的唯一解决方案是设置async:false但是我正在接受我认为严重但不愿意的警告。 还有哪些其他解决方案?

避免在jQuery中使用async:false的策略?

学会爱回调。 :-)当人们这样做:

 // The synchronous way function doSomething() { var foo; $.ajax({ url: "/the/url", async: false, success: function(response) { foo = response.foo; } }); return foo; } // ...somewhere else, we use it function flurgle() { var bar = /* go get `bar` from somewhere */; var x = 52; if (doSomething() === bar) { x -= 10; } niftyFunctionUsing(x); } 

……事件驱动的异步方式真的没那么大不同:

 // The asynchronous way function doSomething(callback) { $.ajax({ url: "/the/url", success: function(response) { callback(response.foo); } }); } // ...somewhere else, we use it function flurgle() { var bar = /* go get `bar` from somewhere */; var x = 52; doSomething(function(foo) { if (foo === bar) { x -= 10; } niftyFunctionUsing(x); }); } 

由于回调经常涉及闭包(上面的那些,这就是我们访问xbar ),我的博客中的这篇文章可能会有所帮助: 闭包并不复杂

您可以更改SaveTemplate函数以接受作为保存时运行的函数的参数。 然后在你的addToOrder函数中,你可以使用你在那里的代码生成一个匿名函数或重构,这样大部分代码都在另一个你可以按名称传递的函数中。

我们的想法是,在您进行异步调用的同时使用异步代码,您可以在那里停止处理该问题(即保存代码)并在回调中选择运行。 您可以在异步调用之后继续执行不相关的操作(例如,向用户发出消息,说“请等待”)但是与保存相关的任何其他代码必须位于由ajax的success属性中的回调集触发的函数中组态。

将第二个.ajax()调用放在第一个.success()函数内。