如何处理长AJAX请求 – 发送响应但继续工作

我们使用jquery-ajax将指令集从浏览器发送到多层Web应用程序。 第一个组件(组件A,用C#编写)validation并将指令持久存储到数据库中,然后调用第二个组件(组件B,用Java编写,也通过HTTP调用),该组件在从指令中检索后对指令进行操作数据库。 浏览器客户端在提交作业后只通过组件A轮询rdbms表,因此在发送请求后它实际上已断开连接,并且不等待组件A的响应。

中间层(组件A)将成功消息返回给客户端以确认成功提交任务的最佳方式是什么,但仍然向请求处理程序(组件B)发出请求并释放其所有资源? 返回响应是页面的最终操作,因此在将其发送回浏览器之前,我们必须在另一个线程中执行某些操作。

我们考虑的另一个选择是在组件B中发生这种情况,其中任务处理程序向中间层发送回立即响应以确认请求,但随后继续在后台工作。 唯一的区别是我们产生额外线程来完成工作。

关于如何处理这个问题的任何好主意?

我们在这种情况下所做的是:

  • 浏览器将指令集发送到组件A.
  • 组件Avalidation指令集
  • 组件A在新的“跟踪”ID STATUS=PENDING下将指令集保存到DB
  • 组件向组件B发出请求以执行工作
  • “线程”在组件B中:
    • 组件B启动后台线程来完成工作,后台线程首先做的是将“跟踪ID”的STATUS=RUNNING更新为STATUS=RUNNING
    • 组件B主线程返回组件A成功
  • 组件A从组件B获得“已成功启动”消息,因此将其自己的“已成功启动”消息与“跟踪ID”一起返回给浏览器。 在此阶段,组件A完成请求,所有组件A资源都是空闲的。
  • 浏览器可以对组件A进行不同的调用,以检查数据库中“跟踪ID”的状态
  • 同时,组件B的后台“线程”仍在进行工作,可能记录“跟踪ID”的进度
  • 组件B完成工作,更新DB中的“跟踪ID” STATUS=OKSTATUS=OKSTATUS=ERROR并放弃所有资源。

所有这一切的优点是没有等待从您的应用程序的角度完成工作。 实际的工作是通过一个“背景”线程来完成的,就好像你用nohup dothework & shell一样把它踢掉了。 关键是使用DB来监控“跟踪ID”的状态。

有一些方法可以通过生成线程手动处理这种情况。 但是你将要面对的一个主要问题(我在编程经验中遇到过)是线程有点难以维护,如果处理不当会有一些缺点。 首先,error handlingfunction是有限的,您必须有一个外部表(持久化表)或全局变量记录或捕获所有这些错误。 另一个问题是服务器可以采取的处理限制。 如果在后台生成太multithreading,服务器处理限制以及因此同时生成的数据库请求将会变得很麻烦。

要避免的最佳解决方案是通过任何可用的后台任务框架。 它们的优点是它们将遵循生产者/消费者队列模式,并将通过在后台运行的单独守护进程为您完成所有跟踪。 但是,这里的缺点是守护进程仍然容易受到攻击。

还有一个选择是集成像Rabbit MQ这样的队列或消息传递服务。 这不仅可以扩展,而且可以在不同语言中实现非常好的实现。