3

我知道(通过阅读 SO 和其他网站上的无数帖子)持久连接并不是绝大多数开发人员非常喜欢的东西(如果脚本突然终止,连接没有关闭,你可能会结束锁定一些表等)但它真的那么糟糕吗?

在我的开发机器(T3400 双核 CPU、4 GB RAM 和 5400RPM 硬盘)上,页面加载时间因我使用的是持久连接还是非持久连接而有很大不同。非持久连接的 2.09 秒与持久连接的(大约)68 毫秒非常不同。这里有两个示例屏幕截图供您查看:non-persistentpersistent

我了解持久连接的风险(我并没有真正每天使用它们,虽然我觉得这个概念很有趣并且我想探索它),但是没有任何方法可以检测非关闭连接吗?

例如,类似于 mysqli 的change_user但用于 PDO 的等价物,或者某种 PHP 脚本,服务器作为 cron 作业每 X 秒运行一次以检查剩余物并随后关闭它们?我正在阅读,register_shutdown_function但是,如果我理解正确,它会在脚本完成后被调用,所以在实践中,这可能意味着每次脚本完成时它都会结束关闭我的持久连接。还是我错了?

编辑

为了准确起见,我忘了提及我的软件堆栈,所以让我来弥补一下。我当前的堆栈由以下元素组成:Windows 7 (x86) SP1作为操作系统,,Apache 2.4.3PHP 5.4.9我总是使用最新版本)和MySQL 5.5.28. 将堆栈运行为localhost(我可能正在将其迁移到专用机器,但现在它保持这样)。

4

1 回答 1

2

为避免每次关机时连接都会关闭,您可以检查error_get_last()您的关机功能。

请注意,这error_get_last()也会返回 E_NOTICE 等“错误”。这应该根据您的需要被过滤掉。

<?php

register_shutdown_function('shutdown');

function shutdown() {

    static $ignore = array (
        E_STRICT,
        E_NOTICE,
        E_USER_NOTICE,
        E_DEPRECATED,
        E_USER_DEPRECATED, // ...
    );

    $error = error_get_last();
    // if no error has been queued or it should be ignored ...
    if(is_null($error) || in_array($error['type'], $ignore)) {
        return; // do nothing
    }

    // here comes your connection close code
    connection_close($your_connection);
}

但这是一个非常老套的解决方案,有很多限制,请参见 www.php.net

我想知道,因为使用非永久连接时服务页面需要大约 2 秒。这真的意味着建立与数据库服务器的连接需要大约 2 秒吗?如果是这样,我会注意这个,因为它看起来很长。您使用什么数据库服务器?数据库服务器是否位于不同的机器上?

于 2012-12-14T15:17:41.640 回答