关于javascript:如何让jquery执行同步而非异步的Ajax请求?

How can I get jQuery to perform a synchronous, rather than asynchronous, Ajax request?

我有一个提供标准扩展点的javascript小部件。其中之一是beforecreate函数。它应该返回false以防止创建项目。

我已经使用jquery向这个函数添加了一个Ajax调用:

1
2
3
4
5
6
7
8
beforecreate: function (node, targetNode, type, to) {
  jQuery.get('http://example.com/catalog/create/' + targetNode.id + '?name=' + encode(to.inp[0].value),

  function (result) {
    if (result.isOk == false)
        alert(result.message);
  });
}

但我希望阻止我的小部件创建该项,所以我应该在母亲函数中返回false,而不是在回调中。有没有使用jquery或其他浏览器API执行同步Ajax请求的方法?


从你的jQuery文件:指定选项异步和同步的AJAX请求to get a false。然后你可以在一些数据集的回调函数,可你的妈妈。

这里是你的代码会建议:如果发生的样子。

1
2
3
4
5
6
7
8
9
beforecreate: function (node, targetNode, type, to) {
    jQuery.ajax({
        url: 'http://example.com/catalog/create/' + targetNode.id + '?name=' + encode(to.inp[0].value),
        success: function (result) {
            if (result.isOk == false) alert(result.message);
        },
        async: false
    });
}


你可以把jQuery的Ajax程序通过调用在同步模式

1
jQuery.ajaxSetup({async:false});

然后将你的Ajax调用使用jQuery.get( ... );

它只是又一次转折。

1
jQuery.ajaxSetup({async:true});

我想同样的事情就是AS内的red"亚当,但它可能是一个乐于助人的人,不想reconfigure jQuery.get()或更多的jQuery.post()精心jQuery.ajax()友好的语法。


优秀的解决方案。我注意到,当我试图实现它,如果我成功返回的a值为未定义的条款,它回来。我们有一个商店,它在一个变量的变量和回报。这是一个方法来:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
function getWhatever() {
  // strUrl is whatever URL you need to call
  var strUrl ="", strReturn ="";

  jQuery.ajax({
    url: strUrl,
    success: function(html) {
      strReturn = html;
    },
    async:false
  });

  return strReturn;
}


所有这些答案是做点小姐在Ajax异步调用的假想的:浏览器造成边坡条件直到Ajax请求。很想解决这个问题的流量控制库浏览器没有挂上。这里是一个例子:在frame.js

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
beforecreate: function(node,targetNode,type,to) {

    Frame(function(next)){

        jQuery.get('http://example.com/catalog/create/', next);
    });

    Frame(function(next, response)){

        alert(response);
        next();
    });

    Frame.init();
}


1
2
3
4
5
6
7
8
9
10
11
12
13
function getURL(url){
    return $.ajax({
        type:"GET",
        url: url,
        cache: false,
        async: false
    }).responseText;
}


//example use
var msg=getURL("message.php");
alert(msg);


记住,如果你做跨域Ajax调用(使用jsonp)-你可以做的synchronously async标志将被忽略,由jQuery。

1
2
3
4
5
$.ajax({
    url:"testserver.php",
    dataType: 'jsonp', // jsonp
    async: false //IGNORED!!
});

呼叫中心jsonp你可以使用:

  • Ajax调用你自己的域名做跨域调用服务器端
  • 改变你的代码工作asynchronously
  • 使用"函数库frame.js音序器"(这样回答)
  • 这不是一块阻塞UI执行(本答案)(我最喜欢的方式)

  • 注意:你不能使用async: false警告消息:由于本

    Starting with Gecko 30.0 (Firefox 30.0 / Thunderbird 30.0 / SeaMonkey 2.27), synchronous requests on the main thread have been deprecated due to the negative effects to the user experience.

    铬对这甚至警告:在控制台

    Synchronous XMLHttpRequest on the main thread is deprecated because of its detrimental effects to the end user's experience. For more help, check https://xhr.spec.whatwg.org/.

    这是你的页面如果你正在做的东西,因为这样它可以停止营运的任何一天。

    如果你想做一个安静的方式就像它安静不同步,但你应该使用异步/块然后等待着和一些可能是基于AJAX的,所以新的fetch API提供的样

    1
    2
    3
    4
    5
    6
    async function foo() {
      var res = await fetch(url)
      console.log(res.ok)
      var json = await res.json()
      console.log(json)
    }

    编辑铬是在同步工作disallowing XHR解雇当页页是我们的navigated或封闭了由用户。本beforeunload自然pagehide,卸载,和visibilitychange。

    如果这是你想要的,然后你的用例可能要看navigator.sendbeacon代替

    因此,它是可能的一个同步请求和页面禁用HTTP headers或者允许或iframe的属性


    一种通过给定carcione答案和修改它使用JSON。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
     function getUrlJsonSync(url){

        var jqxhr = $.ajax({
            type:"GET",
            url: url,
            dataType: 'json',
            cache: false,
            async: false
        });

        // 'async' has to be 'false' for this to work
        var response = {valid: jqxhr.statusText,  data: jqxhr.responseJSON};

        return response;
    }    

    function testGetUrlJsonSync()
    {
        var reply = getUrlJsonSync("myurl");

        if (reply.valid == 'OK')
        {
            console.dir(reply.data);
        }
        else
        {
            alert('not valid');
        }    
    }

    我加了"datatype JSON和responsejson .responsetext到酒店。

    我使用的组织状态的财产statustext返回的对象。注意,这是一个Ajax响应逆境状态,无论是有效的JSON。

    安切洛蒂在后端到返回正确的响应(高型)返回的JSON对象,否则将是未定义的。

    有两个方面的问题,回答时要考虑采取的原。一个程序的执行是synchronously AJAX(异步的设置:假)和其他的是在响应通过返回的返回语句调用函数,而比一个回调函数。

    我尝试它和它的工作岗位。

    我在去邮局了postdata和添加数据:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    function postUrlJsonSync(url, postdata){

        var jqxhr = $.ajax({
            type:"POST",
            url: url,
            data: postdata,
            dataType: 'json',
            cache: false,
            async: false
        });

        // 'async' has to be 'false' for this to work
        var response = {valid: jqxhr.statusText,  data: jqxhr.responseJSON};

        return response;
    }

    注意,上面的代码在只读的作品案例的WHERE异步是FALSE。如果你是一个真正的对象集jqxhr异步返回的是有效的在时间的Ajax调用返回后,只有当异步调用完成的,但太多太晚设置响应变量。


    你把自己封闭在一async: false浏览器。一个非阻塞同步解决方案,你可以使用下面的:

    es6 / ecmascript2015

    你可以使用一个es6发电机&;Co库:

    1
    2
    3
    4
    5
    6
    beforecreate: function (node, targetNode, type, to) {
        co(function*(){  
            let result = yield jQuery.get('http://example.com/catalog/create/' + targetNode.id + '?name=' + encode(to.inp[0].value));
            //Just use the result here
        });
    }

    ES7

    你可以使用asyc ES7在等待着。

    1
    2
    3
    4
    5
    6
    beforecreate: function (node, targetNode, type, to) {
        (async function(){
            let result = await jQuery.get('http://example.com/catalog/create/' + targetNode.id + '?name=' + encode(to.inp[0].value));
            //Just use the result here
        })();
    }


    这是一个例子:

    1
    2
    3
    4
    5
    6
    7
    8
    $.ajax({
      url:"test.html",
      async: false
    }).done(function(data) {
       // Todo something..
    }).fail(function(xhr)  {
       // Todo something..
    });


    首先,我们应该了解何时使用$.Ajax以及何时使用$.get/$.post。

    当我们需要对Ajax请求进行低级控制时,比如请求头设置、缓存设置、同步设置等,那么我们应该使用$.Ajax。

    $.get/$.post:当我们不需要对Ajax请求进行低级控制时,只需简单地将数据获取/发布到服务器。

    1
    2
    3
    4
    5
    6
    $.ajax({
      url: url,
      data: data,
      success: success,
      dataType: dataType
    });

    因此,我们不能将其他功能(同步、缓存等)与$.get/$.post一起使用。

    因此,对于通过Ajax请求进行的低级控制(同步、缓存等),我们应该使用$.Ajax。

    1
    2
    3
    4
    5
    6
    7
    8
     $.ajax({
         type: 'GET',
          url: url,
          data: data,
          success: success,
          dataType: dataType,
          async:false
        });


    因为不推荐使用XMLHttpReponse同步操作,所以我提出了以下封装XMLHttpRequest的解决方案。这使得有序的Ajax查询在本质上仍然是不对称的,这对于一次性使用CSRF令牌非常有用。

    它也是透明的,因此jquery等库将无缝运行。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    /* wrap XMLHttpRequest for synchronous operation */
    var XHRQueue = [];
    var _XMLHttpRequest = XMLHttpRequest;
    XMLHttpRequest = function()
    {
      var xhr   = new _XMLHttpRequest();
      var _send = xhr.send;

      xhr.send = function()
      {
        /* queue the request, and if it's the first, process it */
        XHRQueue.push([this, arguments]);
        if (XHRQueue.length == 1)
          this.processQueue();
      };

      xhr.processQueue = function()
      {
        var call = XHRQueue[0];
        var xhr  = call[0];
        var args = call[1];

        /* you could also set a CSRF token header here */

        /* send the request */
        _send.apply(xhr, args);
      };

      xhr.addEventListener('load', function(e)
      {
        /* you could also retrieve a CSRF token header here */

        /* remove the completed request and if there is more, trigger the next */
        XHRQueue.shift();
        if (XHRQueue.length)
          this.processQueue();
      });

      return xhr;
    };

    这是我使用jquery对异步请求的简单实现。我希望这对任何人都有帮助。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    var queueUrlsForRemove = [
        'http://dev-myurl.com/image/1',
        'http://dev-myurl.com/image/2',
        'http://dev-myurl.com/image/3',
    ];

    var queueImagesDelete = function(){

        deleteImage( queueUrlsForRemove.splice(0,1), function(){
            if (queueUrlsForRemove.length > 0) {
                queueImagesDelete();
            }
        });

    }

    var deleteImage = function(url, callback) {
        $.ajax({
            url: url,
            method: 'DELETE'
        }).done(function(response){
            typeof(callback) == 'function' ? callback(response) : null;
        });
    }

    queueImagesDelete();