【问题标题】:Why PHP PDO connects to different database when using persistent connection?为什么 PHP PDO 在使用持久连接时连接到不同的数据库?
【发布时间】:2018-10-29 19:15:17
【问题描述】:

我使用 PHP 的 PDO 连接到 MySQL,如下所示:

$driver_options[PDO::ATTR_PERSISTENT] = true;
$db = new PDO('mysql:host='.$host.';dbname='.$db_name, $user, $pass, $driver_options);

我在这台服务器上有 2 个数据库(我们称它们为 database_A 和 database_B),有时会发生非常奇怪的事情。即使 $db_name 100% 设置为“database_A”,也会连接到“database_B”。

这是完全随机的。我可以再次运行相同的脚本 10 次,一切都很好。第 11 次出现此问题。

我从没想过会发生这种情况。它给了我a lot of headache。谁能解释一下?不使用持久性的唯一解决方案是什么?

【问题讨论】:

  • 可能是您之前为某些测试或类似配置配置了 database_B 吗?那么这可能是一个缓存问题...
  • 不要问我为什么以及如何,但我曾经听说过在mysql:hostname 之间放置一个空格,比如mysql: host 来解决连接问题。
  • 是的 --> php.net/manual/en/pdo.connections.php Example #4 Notes
  • @PeterM 不幸的是,这个技巧对我不起作用。
  • 为不同的数据库设置并尝试不同的凭据。

标签: php mysql pdo


【解决方案1】:

PDO::ATTR_PERSISTENT 受部分支持,取决于您使用的 PHP 版本和 SQL 服务器。 由于不稳定,我建议不要在驱动器选项中将此属性设置为 true。

我能够复制您的案例,并且发现 ODBC 连接池层正在缓存连接,并且由于您的连接被设置为持久连接,因此每次建立新连接时都会重置缓存。

【讨论】:

  • OP 询问。我想他可能使用的技术可能还不能迁移到最新版本。
  • 能否提供重现此错误的步骤?
【解决方案2】:
$driver_options[PDO::ATTR_PERSISTENT] = true;
$db = new PDO('mysql:host='.$host.';dbname='.$db_name, $user, $pass,    $driver_options);

执行上述操作时,PDO 连接被放置在“持久连接池”中,但池的目的不是缓存数据库,而是内存分配、身份验证和设置基础. 是使用时间的东西(不是那么多)。

您在new PDO() 调用中提供的任何其他内容都是LOST

如果您有两个具有相同凭据的数据库,则可以随机交换它们 - 正如您所经历的那样。

因此,不要new PDO 语句中指定数据库,而是在新的 PDO 对象准备好后立即使用USE databasename SQL 语句。

或者,正如 PankajKumar 建议的那样,为两个数据库设置不同的凭据。那么错误的缓存命中就不会发生(但是一旦有人重复使用这些相同的凭据,例如“ubuntu/ubuntu”或“root/”就不会再次发生)。

【讨论】:

    【解决方案3】:

    我想您是在生产环境中运行它,或者在不经常重新加载的开发系统中运行它。

    因此请重新启动所有 php worker/instances/threads 并检查问题是否再次出现。

    我相信这些过程之一是保留您的旧配置。当您的网络服务器实际选择使用旧的东西时,会随机地默默地导致您的错误。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2016-03-27
      • 2013-05-14
      • 2018-10-19
      • 1970-01-01
      • 2011-11-30
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多