3

这是一个关于如何制作一个 Web 应用程序的通用设计问题,该应用程序将接收大量上传的数据、对其进行处理并返回结果,所有这些都不会出现可怕的 5 分钟旋转沙滩球或可能的 HTTP 超时。

以下是要求:

  • 制作一个 Web 表单,您可以在其中上传包含 URL 列表的 CSV 文件
  • 当用户单击“提交”时,服务器获取文件,并检查每个 URL 以查看其是否有效,以及页面的标题标签是什么。
  • 结果是一个包含 URL 的可下载 CSV 文件,以及结果 HTTP 代码
  • 输入 CSV 可能非常大(> 100000 行),因此提取过程可能需要 5-30 分钟。

到目前为止,我的解决方案是在客户端站点上有一个旋转的 javascript 循环,它每秒查询一次服务器以确定工作的整体进度。这对我来说似乎很笨拙,我不愿接受这是最好的解决方案。

我正在使用 perl、模板工具包和 jquery,但任何使用任何 Web 技术的解决方案都是可以接受的。

编辑: 一个可能的解决方案的例子是这个问题:如何实现基本的“长轮询”?

4

3 回答 3

3

您可以使用 AJAX 执行此操作,但使用类似 COMET 的实现可能会获得更好的实时结果。我相信 COMET 实现是专门为绕过一些超时限制而设计的,但我没有使用任何超时限制,所以我无法提供直接指导。

无论哪种方式,我的建议是在工作到达服务器后将其移交给另一个进程。

我已经为这种性质的批处理任务工作了许多不同的解决方案,我最喜欢的一个是将批处理工作移交给另一个进程。在这样的系统中,上传页面将工作交给一个单独的处理器,并立即返回指令,让用户监控该过程。

批处理器可以通过以下几种方式实现:

  • fork 并从 IO 中分离 child 以完成批处理。父级完成 Web 请求。
  • 将上传内容保存到处理队列(例如:文件系统上的文件,数据库中的记录)并让 Web 服务器通知外部处理器 - 自定义守护进程或现成的调度程序,如 *nix 的“at”系统。

然后,您可以为用户提供多种监控流程的方法:

  • 上传确认页面包含批处理过程的同步实时监控器(通过 COMET 或 Flash)。完成后,确认页面可以引导用户下载。
  • 像上面一样,但监视器不是实时的,而是通过 AJAX 或页面元刷新使用定期轮询
  • 一个队列监视器页面,向他们显示他们正在运行的任何批处理的状态。

批处理器可以通过多种方法传达其状态:

  • 更新数据库中的记录
  • 生成处理日志
  • 使用命名管道

将代码交给另一个进程有很多好处:

  • 当用户意外停止浏览器时,该过程将继续。
  • 使用外部进程会强制您以一种允许您随时分离监视器并重新连接的方式来传达批处理状态。例如:当用户在过程完成之前不小心导航离开页面时。
  • 如果您决定需要分散批处理以在 Web 流量较低的时间进行,则更容易实施批处理限制和延迟。
  • 您不必担心网络超时(客户端或服务器端)。
  • 您可以重新启动 Web 服务器,而不必担心是否中断了批处理过程。
于 2010-06-09T01:13:07.587 回答
1

最简单的方法是批处理甚至流式传输作业。如果您将其视为页面上的数据表。如果表有 > 100000 条记录,您是否只需一次请求所有记录。我会这样做:

  1. 发送下载文件的请求。

  2. 发送请求以处理 100 个(任意数量)记录。

    一种。过程记录。

    湾。保存到临时 csv 文件。

    C。回复完成/未完成过程的状态。

    d。如果状态未完成,请重复第二步。

于 2010-06-09T05:13:58.490 回答
0

您提到客户端不可信任,因此我建议(在客户端)每 X 条记录预先解析文件,将校验和附加到每个记录子集,然后允许客户端通过固定数量的连接上传代理,以便您可以更准确地监控进度。

于 2017-08-07T05:08:05.723 回答