AJAX:我如何解决需要同步请求的问题?

时间:2022-03-17 03:49:00

I'm deleting a previously asked question and asking again more succinctly now that I have a bit more understanding of the problem.

我正在删除之前提出的问题,并且现在再次更简洁地询问我对这个问题有了更多的了解。

I have a page that uses a lot of AJAX and is updated and dynamically populated with content (form elements and div's with text returned from other form element).

我有一个页面,它使用了很多AJAX,并且更新并动态填充内容(表单元素和div与其他表单元素返回的文本)。

I really need to be able force users to wait until AJAX requests are processed (for example after they have completed a text field that has submitted some values) before they continue. From what I gather using synchronous requests can cause problems with the browser hanging etc...

我真的需要能够强制用户等待,直到他们继续之前处理AJAX请求(例如,在他们完成提交了一些值的文本字段之后)。从我使用同步请求收集的内容可能导致浏览器挂起等问题...

I also need to have a javascript function that executes multiple AJAX function calls but i also need them to execute one at a time. Currently using asynchronous calls produces unpredictable results... maybe I'm going about this the wrong way. There is a lot of code so it's hard to provide a short example but I'll give it a try below:

我还需要一个执行多个AJAX函数调用的javascript函数,但我还需要它们一次执行一个。目前使用异步调用会产生不可预测的结果......也许我会以错误的方式解决这个问题。有很多代码,所以很难提供一个简短的例子,但我会在下面试一试:

The from below (which is itself inserted by an Ajax function) dynamically adds more form elements to the page if it is the first time the input has been edited (first time the content is written to the database... subsequently it will just update the existing db entry and I don't need to add the additional form items)

如果是第一次编辑输入(第一次将内容写入数据库...随后它将只更现有的db条目,我不需要添加其他表单项)

   <form name='talkItemForm' id='talkItemFrom-<?php print $_POST[talkItemID]; ?>' class='talkItemForm' method='post'>

   <input type='hidden' id='talkItemID' name='talkItemID' value='<?php print $_POST[talkItemID]; ?>'><input type='hidden' id='talkID' name='talkID' value='<?php print $_POST[talkID]; ?>'>

   <input type='text' name='talkItemInput' id='talkItemInput' value='New Topic...'  onblur=" updateTalkItem(this.parentNode, '<?php print $_POST[talkID]; ?>', '<?php print $_POST[talkItemID]; ?>'); isNewTalkItem('<?php print $_POST[talkID]; ?>', '<?php print $_POST[talkItemID]; ?>', '<?php print generateTalkItemID()+1; ?>','<?php print generateNoteID(); ?>'); "/>

   </form>

Invokes:

调用:

   function isNewTalkItem (talkID, talkItemID, newTalkItemID, newNoteID){

      var url = "./wp-content/themes/twentyten/addBelowIfNew.php";

      var poststr = "talkItemID=" + talkItemID;

      http_request = false;
      if (window.XMLHttpRequest) { // Mozilla, Safari,...
         http_request = new XMLHttpRequest();
         if (http_request.overrideMimeType) {
            // set type accordingly to anticipated content type
            //http_request.overrideMimeType('text/xml');
            http_request.overrideMimeType('text/html');
         }
      } else if (window.ActiveXObject) { // IE
         try {
            http_request = new ActiveXObject("Msxml2.XMLHTTP");
         } catch (e) {
            try {
               http_request = new ActiveXObject("Microsoft.XMLHTTP");
            } catch (e) {}
         }
      }
      if (!http_request) {
         alert('Cannot create XMLHTTP instance');
         return false;
      }

      http_request.onreadystatechange = function(){


           if (http_request.readyState == 4) {
               if (http_request.status == 200 || http_request.status == 0) {

                  result = http_request.responseText;

        //following code will note execute if this is not the first time this field has been edited... 
        if (result) {

                        // call to AJAX function that inserts a new <form>
            newNote(newNoteID, talkItemID);

                        // another call to AJAX function that inserts a new <form>
            newTalkItem(talkItemID, talkID);

        }

               } else {
                  alert('There was a problem with the request.');
               }

           }

      }    

      http_request.open('POST', url, true);
      http_request.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
      http_request.setRequestHeader("Content-length", poststr.length);
      http_request.setRequestHeader("Connection", "close");
      http_request.send(poststr);

2 个解决方案

#1


0  

When I first stared to answer this question I incorrectly assumed you were using ajax. As Mikhail stated, you should really learn that, it makes things much easier, simpler, and cleaner

当我第一次盯着回答这个问题时,我错误地认为你正在使用ajax。正如米哈伊尔所说,你应该真正了解它,它使事情变得更容易,更简单,更清洁

I think I can pretty much answer both of your questions with similar answers.

我想我几乎可以用类似的答案回答你的两个问题。

As far as the first question, you're right, doing synchronous requests will lock up the browser process while it waits for the request to return. What you can do is either make it so the next part of the UI is invisible while you wait for the results to return or make it uneditable. Here is an example of an ajax request that could do that:

至于第一个问题,你是对的,做同步请求会在等待请求返回时锁定浏览器进程。您可以做的是,在等待结果返回或使其不可编辑时,使UI的下一部分不可见。以下是可以执行此操作的ajax请求的示例:

$.ajax({ url: "test.html", context: document.body, success: function(){ // make ui editable }});

$ .ajax({url:“test.html”,context:document.body,success:function(){// make ui editable}});

Similarly, for your second question, you can just nest them:

同样,对于第二个问题,您可以嵌套它们:

$.ajax({ url: "test.html", context: document.body, success: function(){

$ .ajax({url:“test.html”,context:document.body,success:function(){

$.ajax({ url: "test.html", context: document.body, success: function(){

      $.ajax({ url: "test.html", context: document.body, success: function(){

          $(this).addClass("done");

      }});

   }});

}});

}});

#2


1  

There may be a better approach to solving your overall task, but several points can be made regardless:

可能有更好的方法来解决您的整体任务,但无论如何都可以做出以下几点:

  1. Learn jquery and use that for your ajax -- cleaner syntax, easier to read and debug.
  2. 学习jquery并将其用于ajax - 更清晰的语法,更易于阅读和调试。
  3. To make your users wait for ajax to be done set a flag before requesting a call, and unset it when ajax returns. Whatever functionality needs to wait for ajax answer check if the flag is set and abort the function call.
  4. 要让您的用户等待ajax完成,请在请求呼叫之前设置一个标志,并在ajax返回时取消设置。无论什么功能需要等待ajax应答检查是否设置了标志并中止函数调用。
  5. Waiting for previous ajax to finish before starting a new call sounds like a bad design. but to answer your question anyway -- you can create a chain of ajax calls such that each time data is loaded, a callback function starts the next ajax call.
  6. 在开始新的通话之前等待之前的ajax完成听起来像是一个糟糕的设计。但无论如何要回答你的问题 - 你可以创建一个ajax调用链,这样每次加载数据时,回调函数都会启动下一个ajax调用。

Again, all of this is much easier through jquery. http://www.jquery.com/

同样,通过jquery可以更轻松地完成所有这些工作。 http://www.jquery.com/

#1


0  

When I first stared to answer this question I incorrectly assumed you were using ajax. As Mikhail stated, you should really learn that, it makes things much easier, simpler, and cleaner

当我第一次盯着回答这个问题时,我错误地认为你正在使用ajax。正如米哈伊尔所说,你应该真正了解它,它使事情变得更容易,更简单,更清洁

I think I can pretty much answer both of your questions with similar answers.

我想我几乎可以用类似的答案回答你的两个问题。

As far as the first question, you're right, doing synchronous requests will lock up the browser process while it waits for the request to return. What you can do is either make it so the next part of the UI is invisible while you wait for the results to return or make it uneditable. Here is an example of an ajax request that could do that:

至于第一个问题,你是对的,做同步请求会在等待请求返回时锁定浏览器进程。您可以做的是,在等待结果返回或使其不可编辑时,使UI的下一部分不可见。以下是可以执行此操作的ajax请求的示例:

$.ajax({ url: "test.html", context: document.body, success: function(){ // make ui editable }});

$ .ajax({url:“test.html”,context:document.body,success:function(){// make ui editable}});

Similarly, for your second question, you can just nest them:

同样,对于第二个问题,您可以嵌套它们:

$.ajax({ url: "test.html", context: document.body, success: function(){

$ .ajax({url:“test.html”,context:document.body,success:function(){

$.ajax({ url: "test.html", context: document.body, success: function(){

      $.ajax({ url: "test.html", context: document.body, success: function(){

          $(this).addClass("done");

      }});

   }});

}});

}});

#2


1  

There may be a better approach to solving your overall task, but several points can be made regardless:

可能有更好的方法来解决您的整体任务,但无论如何都可以做出以下几点:

  1. Learn jquery and use that for your ajax -- cleaner syntax, easier to read and debug.
  2. 学习jquery并将其用于ajax - 更清晰的语法,更易于阅读和调试。
  3. To make your users wait for ajax to be done set a flag before requesting a call, and unset it when ajax returns. Whatever functionality needs to wait for ajax answer check if the flag is set and abort the function call.
  4. 要让您的用户等待ajax完成,请在请求呼叫之前设置一个标志,并在ajax返回时取消设置。无论什么功能需要等待ajax应答检查是否设置了标志并中止函数调用。
  5. Waiting for previous ajax to finish before starting a new call sounds like a bad design. but to answer your question anyway -- you can create a chain of ajax calls such that each time data is loaded, a callback function starts the next ajax call.
  6. 在开始新的通话之前等待之前的ajax完成听起来像是一个糟糕的设计。但无论如何要回答你的问题 - 你可以创建一个ajax调用链,这样每次加载数据时,回调函数都会启动下一个ajax调用。

Again, all of this is much easier through jquery. http://www.jquery.com/

同样,通过jquery可以更轻松地完成所有这些工作。 http://www.jquery.com/