1

我遇到了一些使用 ajax 从数据库中获取值的异步 JavaScript 代码的问题。

本质上,我想做的是在填充列表后刷新页面。为此,我尝试将以下代码插入到填充列表的函数中:

var timer1;
timer1 = setTimeout([refresh function], 1000);

正如您可能想象的那样,当列表填充时间少于 1 秒时,这可以正常工作,但当需要更长的时间时会导致问题。所以我有了将这段代码插入到每次ajax调用成功时调用的函数中的想法:

clearTimeout(timer1);
timer1 = setTimeout([refresh function], 1000);

所以理论上,每次获取列表元素时,计时器都应该重置,这意味着刷新函数只能在成功检索到最终列表元素后的 1 秒内调用。然而,在执行中,所有发生的事情都是 timer1 被重置一次,第一次到达第二个代码块。

任何人都可以看到问题可能是什么?或者如果有更好的方法来做到这一点?谢谢。

==========

编辑:要弄清楚我的 ajax 调用是如何工作的:代码结构的问题之一是ajax 调用实际上是嵌套的;原始 ajax 调用的回调方法本身就是另一个 ajax 调用,其回调方法包含数据库事务(不正确 - 见下文)。另外,我有两个这样的方法同时运行。我需要的是一种方法来确保在刷新页面之前所有级别的所有调用都已完成。这就是为什么我认为给这两种方法一个计时器,并在每次调用其中一个回调方法时重置它,会一直推回它的执行,直到所有线程都完成。

老实说,代码非常复杂——大约 140 行,包括辅助方法——我认为在这里发布它是不可行的。抱歉 - 如果没有代码没有人可以提供帮助,那么也许我会硬着头皮尝试以某种有意义的格式将其复制到这里。

==========

EDIT2:这是方法尝试执行的一般工作流程。该功能是一种“同步”功能,既可以向服务器发送数据,也可以从服务器检索数据。

  • I. 调用从本地数据库中检索项目的函数
  • 一世。每次获取项目时,都会将其发送到服务器(ajax)
  • 一种。当 ajax 回调时,该项目在本地更新以反映其成功/失败

  • 二、从本地数据库中检索(单独的)项目列表

  • 一世。每次获取项目时,都会从服务器(ajax)获取与该项目 ID 匹配的项目
  • 一种。从服务器成功获取后,将比较项目
  • 湾。如果服务器端项目更新,则更新本地项目

所以我在上面插入第二个代码块的地方是在“i”中。每个方法的部分,换句话说,ajax 应该(重复)回调的地方。我意识到我在上面的评论中有错误;实际上从来没有嵌套的 ajax 调用,而是数据库事务中的 ajax 调用中的数据库事务。

4

1 回答 1

1

到目前为止,你做得很好。您要使用的技巧是将事件链接在一起,如下所示:

function refresh()
{
    invokeMyAjaxCall(param1, param2, param3, onSuccessCallback, onFailureCallback);
}

function onSuccessCallback()
{
    // Update my objects here

    // Once all the objects have been updated, trigger another ajax call
    setTimeout(refresh, 1000);
}

function onFailureCallback()
{
    // Notify the user that something failed

    // Once you've dealt with the failures, trigger another call in 1 sec
    setTimeout(refresh, 1000);
}

现在,这样做的困难是:如果调用失败会发生什么?理想情况下,听起来您想确保不断更新来自服务器的信息,即使发生临时故障,您也想继续前进。

我在这里假设您的 AJAX 库允许您执行失败回调。但是,我见过一些库挂起而没有失败或成功的情况。如有必要,您可能需要使用一组单独的逻辑来确定与服务器的连接是否已中断并重新启动您的回调序列。

EDIT: I suspect that the problem you've got is a result of queueing the next call before the first call is done. Basically, you're setting up a race condition: can the first call finish before the next call is triggered? It may work most times, or it may work once, or it may work nearly all the time; but unless the setTimeout() is the very last statement in your "response-processing" code, this kind of race condition will always be a potential problem.

于 2012-08-09T19:16:27.877 回答