jquery 没有同步 AJAX 也能做到吗?

gg58donl  于 2023-01-25  发布在  jQuery
关注(0)|答案(2)|浏览(225)

出于性能原因,我想将下面的代码从同步AJAX更改为异步AJAX。这可能吗?我发现几乎所有的AJAX调用都是同步的,所以我感觉我缺少了一个设计模式。一般来说,如果您需要显示从服务器返回的数据,那么您不需要等待(异步:false),以便服务器在继续之前使用数据进行响应?
在下面的代码中,元素'a.popup'绑定了两个'click'处理程序。第一个是lightbox(未显示),第二个是下面所示的代码。我尝试在不使用“async:false”,但它不起作用。

function completed_investment($inputs) {

        var result;

        jQuery.ajax({
            type: 'POST',
            url: '/ajax/completed_investment',
            dataType: 'json',
            data: $inputs,
            async: false,          // need to wait until get result.
            success: function(data) {
                result = data;
            }
        });
        return result;
}

// AJAX - Completed
jQuery('a.open-popup').click(function(){
    var $parent = jQuery(this).parent();
    var $InvestmentID = $parent.siblings('input').attr('value');
    var $inputs;
    var $outputs;

    $inputs = { 'InvestmentID' : $InvestmentID };
    $outputs = completed_investment($inputs);

    // If an investment was completed, update HTML
    if ($outputs.state == 'Begin')
    {

        $parent.siblings('.plan-msg').remove();
        $parent.removeClass('completed-button')
                    .addClass('add-inv-button ')
                    .html('+ Add to Your Plan');
        $newpoints = '(+' + $outputs.points + " " + $outputs.plural + ")";
        $parent.siblings('.done-points').removeClass('done-points')
                                        .addClass('add-points')
                                        .html($newpoints);
    }
});
2vuwiymt

2vuwiymt1#

你的直觉是正确的:不要使用同步 AJAX 。相反,将期望“result”的代码放在“success”回调中!

jQuery('a.open-popup').click(function(){
    var $parent = jQuery(this).parent();
    var $InvestmentID = $parent.siblings('input').attr('value');
    var $inputs;
    var $outputs;

    $inputs = { 'InvestmentID' : $InvestmentID };
    $outputs = completed_investment($inputs, function($outputs) {
      if ($outputs.state == 'Begin')
        {

          $parent.siblings('.plan-msg').remove();
          $parent.removeClass('completed-button')
                .addClass('add-inv-button ')
                .html('+ Add to Your Plan');
          $newpoints = '(+' + $outputs.points + " " + $outputs.plural + ")";
          $parent.siblings('.done-points').removeClass('done-points')
                                    .addClass('add-points')
                                    .html($newpoints);
         }
    });

然后更改进行 AJAX 调用的函数:

function completed_investment($inputs, whenFinished) {

    var result;

    jQuery.ajax({
        type: 'POST',
        url: '/ajax/completed_investment',
        dataType: 'json',
        data: $inputs,
        async: true,
        success: function(data) {
            whenFinished(data);
        }
    });
}

JavaScript的基本思想是,由于***将一些代码打包到匿名函数中并将其随意丢弃***是如此容易,因此不需要让代码像您所描述的那样“等待”。相反,您只需将工作打包并将其交给服务函数用作事件处理程序。当HTTP请求完成时,该事件将触发事件。由于JavaScript中的作用域规则,代码中可用的局部变量仍然可以完全按照处理程序函数传递到 AJAX 机制时设置的方式使用。

dgjrabp2

dgjrabp22#

试试这个(未测试):

function completed_investment($inputs) {
    jQuery.ajax({
        type: 'POST',
        url: '/ajax/completed_investment',
        dataType: 'json',
        data: $inputs,
        async: false,          // need to wait until get result.
        success: function($outputs) {
            // If an investment was completed, update HTML
            if ($outputs.state == 'Begin')
            {

                $parent.siblings('.plan-msg').remove();
                $parent.removeClass('completed-button')
                            .addClass('add-inv-button ')
                            .html('+ Add to Your Plan');
                $newpoints = '(+' + $outputs.points + " " + $outputs.plural + ")";
                $parent.siblings('.done-points').removeClass('done-points')
                    .addClass('add-points')
                    .html($newpoints);
            }
        }
    });
    // Notice: no return value
}

// AJAX - Completed
jQuery('a.open-popup').click(function(){
    var $parent = jQuery(this).parent();
    var $InvestmentID = $parent.siblings('input').attr('value');
    var $inputs;

    $inputs = { 'InvestmentID' : $InvestmentID };
    completed_investment($inputs);
});

相关问题