php - 我应该如何通过 AJAX 发出长 PHP 请求,定期检查状态更新,并在请求取消时关闭脚本?

标签 php ajax http session-variables session-cookies

我正在开发的部分 PHP 网络应用程序需要执行以下操作:

  1. 向 PHP 脚本发出 AJAX 请求,这可能需要一秒到一小时的时间,并在完成后在页面上显示输出。
  2. 定期更新网页上的加载栏,由长时间运行的 PHP 脚本中的状态变量定义。
  3. 允许长时间运行的 PHP 脚本检测 AJAX 请求是否被取消,以便它能够及时正确关闭。

我目前的解决方案:

  • client.php:创建对 request.php 的 AJAX 请求,然后每秒向 status.php 发出一个请求,直到初始请求完成。生成并传递唯一标识符 (uid),以防应用程序的多个实例正在运行。
  • request.php:每次取得进展时,将当前进度百分比保存到 $_SESSION["progressBar"][uid]。 (每次都要运行session_start()和session_write_close()。)完成后,返回client.php需要的数据。
  • status.php:运行 session_start(),返回 $_SESSION["progressBar"][uid],并运行 session_write_close()。

不足之处:

我的解决方案满足了我的前两个要求。对于第三种,我想在 request.php 中使用 connection_aborted() 来了解请求是否被取消。但是,文档说:

PHP will not detect that the user has aborted the connection until an attempt is made to send information to the client. Simply using an echo statement does not guarantee that information is sent, see flush().

我可以简单地提供无意义的输出,但每次我调用 session_start() 时,PHP 必须发送一个 cookie。我想使用相同的 session ,但文档说:

When using session cookies, specifying an id for session_id() will always send a new cookie when session_start() is called, regardless of if the current session id is identical to the one being set.

我对解决方案的想法,没有一个令我满意:

  • 状态数据库,或写入临时文件,或任务管理系统。这似乎比我需要的更复杂!
  • 自定义 session 处理程序。这与上述解决方案基本相同。
  • 在一个请求中流式传输进度数据和结果数据。这解决了所有问题,但我基本上会重新实现 AJAX。这不可能是对的。

请告诉我我遗漏了什么!为什么 PHP 不立即知道连接何时终止?为什么 PHP 必须重新发送 cookie,即使它完全相同?回答这些问题中的任何一个都会有很大的帮助!

衷心感谢。

最佳答案

为什么不在 status.php 中设置第二个 session 变量,由唯一请求标识符和访问时间戳组成。

如果客户端关闭,它会停止从 status.php 获取更新,并且 session 变量会停止更新,这会在 request.php 中触发干净的关闭,如果变量在一定时间内没有更新。

关于php - 我应该如何通过 AJAX 发出长 PHP 请求,定期检查状态更新,并在请求取消时关闭脚本?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14284830/

相关文章:

javascript - 无法阻止点击登录后密码在密码字段中自动延长

php - 尝试在 MYSQL 中使用 IF 和 MAX 来获取两个表之间的最新日期

java - 如何让用java编写的服务只能处理来自定义的ip的请求?

c++ - HTTP 代理检测 HTTP 客户端断开连接

javascript - jquery:来自 php 的数组从未定义

php - 为什么 AJAX 不向我的 PHP 页面发送数据?

jquery - jsonp 与 jquery

php - 如何以在 php 中作为字符串回显的形式填充单选按钮?

javascript - 执行 ajax POST 时 options.data.indexOf 不是一个函数

http - 具有基本身份验证的 http 的 Fluentd 插件