我要完成的工作
我需要触发1到3个不同的$.post()请求,它是1个调用,2个连续调用还是3个连续调用是由一些基本的用户选择决定的.每个呼叫只能在前一个呼叫完全结束之后开始.
我正在处理3个简单的行为案例-向用户显示“复选框1”,“复选框2”和“继续”按钮,“
>不选择任何内容,然后按“继续”按钮,这将对“ /remote.PHP”进行XHR调用,
>用户选择仅选择“复选框1”或“复选框2”,然后按“继续”按钮,这将调用绑定到复选框1的$.post()函数1或调用该复选框的$.post()函数2绑定到复选框2,然后对“ /remote.PHP”进行XHR调用,
>或用户同时选中两个CheckBox 1 2,然后按Continue,这将调用$.post()函数1,然后调用$.post()函数2,然后对’/remote.PHP’进行XHR调用.
我需要确保在复选框绑定的$.post()函数启动并完成之前,不会触发Continue-button $.post()函数.
问题
问题在于,如果按照我的理解,如果选择了复选框1并选择了复选框2,然后按了“继续”按钮,则加载顺序应为:
>复选框1绑定的$.post()请求被触发并完成,然后
>复选框2绑定的$.post()请求被触发并完成,然后
>继续按钮绑定$.post()触发,并且在绑定到“继续”按钮绑定函数的函数末尾通过AJAX更改页面.
因此,结果应如下所示:
XHR finished loading: POST "/cart.PHP?action=add&product_id=1280". XHR finished loading: POST "/cart.PHP?action=add&product_id=1284". XHR finished loading: POST "/remote.PHP".
@H_502_28@相反,它通常是这样出现的:
XHR finished loading: POST "/cart.PHP?action=add&product_id=1280". XHR finished loading: POST "/remote.PHP". XHR finished loading: POST "/cart.PHP?action=add&product_id=1284".
@H_502_28@因此,当页面由于“最后一个” /“继续按钮”功能结尾处的AJAX而改变时,既没有发生CheckBox 1或CheckBox 2操作,也没有发生两者之一,或者两者都在后端注册(即添加到购物车中),但不会像最终AJAX在先前的$.post()调用完成之前触发并完成时那样反映在AJAXified DOM中.
我的密码
HTML
HTML是基本的:
<form method="post" action="#" onsubmit="newChooseShippingProvider(); return false;"> <label for="delSigCheck" class="del-sig-text"><input id="delSigCheck" type="checkBox" onchange="addDelSigToCart();" title="Add Delivery Signature"></label> <label for="addInsCheck" class="ins-add-calc"><input id="addInsCheck" type="checkBox" onchange="addInsToCart();" title="Add Delivery Signature" data-ins-id="1284"></label> <input type="submit" value="Continue" class="btn Small"> </form>
@H_502_28@Javascript / jQuery
这是我最近尝试的第-4或第5-尝试,仍然无法使用:
function addDelSigToCart() { $('#delSigCheck').toggleClass('checked'); } function addInsToCart() { $('#addInsCheck').toggleClass('checked'); } function newChooseShippingProvider() { var originalCheckout = ExpressCheckout.ChooseShippingProvider(); if ($('.ShippingProviderList .radio span').hasClass('checked')) { var addInsCheck = $('#addInsCheck').hasClass('checked'); var delSigCheck = $('#delSigCheck').hasClass('checked'); var insId = $('#addInsCheck').attr('data-ins-id'); var addDelSigUrl = '/cart.PHP?action=add&product_id=1280'; var addInsUrl = '/cart.PHP?action=add&product_id=' + insId; if (delSigCheck && addInsCheck) { $.post(addDelSigUrl, function() { $.post(addInsUrl, function() { originalCheckout; }); }); } else if (!delSigCheck && !addInsCheck) { originalCheckout; } else if (delSigCheck && !addInsCheck) { $.post(addDelSigUrl, function() { originalCheckout; }); } else if (!delSigCheck && addInsCheck) { $.post(addInsUrl, function() { originalCheckout; }); } } else { originalCheckout; }
@H_502_28@我尝试过的
我已经经历了多个链接$.post()调用的版本,但是似乎没有任何一致的方法.
我现在使用的是什么,对于广泛的测试来说,最适合我的方法是使用setTimeout延迟一段时间来链接函数,如下所示:
... if (delSigCheck && addInsCheck) { $.post(addDelSigUrl); setTimeout(function() { $.post(addInsUrl); setTimeout(function() { ExpressCheckout.ChooseShippingProvider(); }, 1300); }, 1300); } else if ...
@H_502_28@上面的版本是我现在使用的版本,因为它似乎提供了最一致的结果,看到脚本的加载通常为1,2,3,然后是基于功能1和2进行了适当更改的DOM AJAXified.但是,我不认为setTimeout可以正常工作,即使我将其增加到5000或10000时,动作是“瞬时”执行的,并且没有延迟发生(至少肯定没有接近5-10秒的时间).
我还尝试将函数放入$.post()的成功回调中:
... if (delSigCheck && addInsCheck) { $.post(addDelSigUrl, function() { setTimeout(function() { $.post(addInsUrl, function() { setTimeout(function() { originalCheckout; }, 1300); }); }, 1300); }); } else if ...
@H_502_28@最后,我还尝试了:
$.when($.post(addDelSigUrl)).then(originalCheckout);
@H_502_28@以及.done和成功:但它们均无效,并且$.posts()的加载以意外的顺序失败.
问题
>我做错了什么?
>如何使它完全装载1次,然后完全装载2次,然后只有3次点火和装载?更新1:
我刚刚尝试了jfriend00’s answer:
$.post(addDelSigUrl, { cache: false }).then(function(data1) { //CONSOLE.LOGing HERE console.log(data1); return $.post(addInsUrl, { cache: false }); }).then(function(data2) { //CONSOLE.LOGing HERE console.log(data2); return originalCheckout; });
@H_502_28@但这仍然导致:
XHR finished loading: POST "/cart.PHP?action=add&product_id=1280". XHR finished loading: POST "/remote.PHP". XHR finished loading: POST "/cart.PHP?action=add&product_id=1284".
@H_502_28@并且两个console.logs在第一个“ XHR …”之后立即触发,然后/remote.PHP触发(尽管它应作为OriginalCheckout的一部分最后触发),然后第三个XHR触发.
更新2
现在,我们已经通过.then()以正确的顺序触发并加载了XHR,问题的第二部分是我的第三个XHR /remote.PHP使用后端的数据通过AJAX更新了DOM.该数据的一部分是第一个和第二个$.posts.
我认为在通过服务器端PHP对后端执行某些操作之前,第3个AJAX调用正在触发并完成毫秒,因此,超过50%的时间,通过第3个AJAX调用进行DOM更新会丢失来自第一个和/或第二个调用(最常见的DOM更改包括CheckBox 1 / AJAX调用1,但不包括2).
我怎样才能解决这个问题?我已经尝试过setTimeout,但是即使将其设置为30000,它似乎也无法正常工作,一旦第1/2次完成,第3 AJAX就会启动.
最新的前端代码:
function newChooseShippingProvider() { if ($('.ShippingProviderList .radio span').hasClass('checked')) { var addInsCheck = $('#addInsCheck').hasClass('checked'); var delSigCheck = $('#delSigCheck').hasClass('checked'); var insId = $('#addInsCheck').attr('data-ins-id'); var addDelSigUrl = '/cart.PHP?action=add&product_id=1280'; var addInsUrl = '/cart.PHP?action=add&product_id=' + insId; if (delSigCheck && addInsCheck) { $.post(addDelSigUrl).then(function(data1) { return $.post(addInsUrl); }).then(function(data2) { return ExpressCheckout.ChooseShippingProvider(); }); } else if (!delSigCheck && !addInsCheck) { ExpressCheckout.ChooseShippingProvider(); } else if (delSigCheck && !addInsCheck) { $.post(addDelSigUrl).then(function(data1) { return ExpressCheckout.ChooseShippingProvider(); }); } else if (!delSigCheck && addInsCheck) { $.post(addInsUrl).then(function(data1) { return ExpressCheckout.ChooseShippingProvider(); }); } } else { ExpressCheckout.ChooseShippingProvider(); } }
@H_502_28@解决方法:
排序jQuery ajax操作的最简单方法是使用内置的promise:
$.post(...).then(function(data1) { return $.post(...); }).then(function(data2) { return $.post(...); }).then(function(data3) { // everything done here });
@H_502_28@向您展示精确序列的工作演示:http://jsfiddle.net/jfriend00/zcfr2xy0/
好的,看来问题在于您正在执行此操作:
var originalCheckout = ExpressCheckout.ChooseShippingProvider();
@H_502_28@然后,您认为以后的某个时候,您可以这样做:
originalCheckout;
@H_502_28@这将以某种方式执行前者.事实并非如此.您的ExpressCheckout.ChooseShippingProvider()函数将立即执行,并将执行该函数的返回结果分配给originalCheckout.
您根本无法那样做.当函数名称后有()时,表示立即执行.我建议您只替换originalCheckout的所有实例;与ExpressCheckout.ChooseShippingProvider();.
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 [email protected] 举报,一经查实,本站将立刻删除。