【发布时间】:2013-01-30 23:16:32
【问题描述】:
首先,对不起我的英语,我在谷歌翻译的帮助下写了这篇文章。
我正在尝试使用 PHP 和 Ajax 制作像 Google Wave 这样的应用程序。我有一个 textarea,当用户输入内容时,页面上的 javascript 检测到 oninput 并将 textarea 的内容发送到服务器,服务器将内容存储到数据库中。
我正在做的是,每次我通过 XHR 发送内容时,都有XHR.abort() 总是会中断之前的 XHR 请求。数据库中的数据很好,但有时它存储的是以前的版本。
我知道这是因为 PHP 没有停止执行,即使客户端已经中止,有时前一个请求比上一个请求花费了更多时间并且在最后一个请求之后完成,所以我阅读了函数手册“ignore_user_abort”和“connection_aborted”,但问题仍然存在。
我创建了这个脚本来模拟这种情况,我希望当我中止连接时(按“停止”,关闭选项卡/窗口),数据库上没有任何新数据,但 5 秒后,我仍然有新数据,所以当用户中止连接时我需要帮助来回滚事务。
这是要模拟的脚本(定义了 PDO_DSN、PDO_USER、PDO_PASS):
<?php
ignore_user_abort(true);
ob_start('ob_gzhandler');
$PDO = new PDO(PDO_DSN, PDO_USER, PDO_PASS, array(PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES utf8'));
$PDO->beginTransaction();
$query = $PDO->query('INSERT INTO `table` (`content`) VALUES (' . $PDO->quote('test') . ')');
sleep(5);
echo ' ';
ob_flush();
flush();
if (connection_aborted()) {
$PDO->rollBack();
exit;
}
$PDO->commit();
ob_end_flush();
【问题讨论】:
-
如果设置
ignore_user_abort(false)会怎样? -
@ExplosionPills 问题依然存在,
connection_aborted()无法与ignore_user_abort(false)一起使用 -
在您尝试执行输出之前,php 无法可靠地检测连接是否/何时中止。见注释:php.net/manual/en/function.ignore-user-abort.php
-
@MarcB 我执行了输出,见代码的第 11 行。
-
问题是
$PDO = new PDO...为当前的PHP脚本创建了一个连接。您不能从 另一个 PHP 脚本中断当前执行。您可以使用一个脚本将 tmp 文件写入磁盘,然后检查 tmp 文件以及是否缺少回滚。任何脚本都可以删除 tmp 文件。
标签: php mysql ajax rollback abort