jeremiah-shaulov / pdoi
改进的MySQL连接池PDO
v1.0.1
2021-02-14 22:10 UTC
Requires
- php: >=7.4
Requires (Dev)
- phpunit/phpunit: ^9.5
README
此库提供与 PDO
API 匹配的类,并且可以用于几乎不需要修改应用程序的情况下替换 PDO
。此类称为 Pdoi
。它支持大多数(但不全部)PDO
功能。对于MySQL以外的驱动程序,它的工作方式与 PDO
完全相同(函数调用被转发到内部 PDO
实例),而对于MySQL,它明确使用 mysqli
扩展。
这是为了实现两个目标
- 更合理的连接池。
- 访问
mysqli
特定功能。
关于数据库连接池
截至2021年1月,我在PHP世界中看不到可用的数据库连接池解决方案。
可以使用 "p:" 前缀为主机名创建 mysqli
的持久连接。而通过 PDO
,它们可以通过 PDO::ATTR_PERSISTENT
属性来创建。与PHP-FPM进程池一起,这可以构建真正的数据库连接池系统。
即使在PHP4上也能工作,但没有人实际使用它们,因为存在重用脏连接的问题。
- 一次发出的
SET @flag=1
将在下次连接使用时初始化设置。 - 开始且未提交的事务将持有受影响的行上的锁。
SELECT Get_lock('Busy', 10)
将阻止池中其他并行连接进入关键部分。
截至2021年1月,mysqli
和 PDO
中当前的持久连接实现通过调用 mysqli_change_user()
函数重置连接状态。但我的经验表明,用户锁没有被释放。我猜想这个函数在从池中选取连接并使用它之前被调用。因此,从连接被单独留下到新使用(可能根本不会发生)的整个时间段内,锁都锁定着它们想要锁定的东西。
每个连接应在脚本结束时立即重置。此库在 Pdoi
对象的析构函数中调用 mysqli_change_user()
。我喜欢PHP中的引用计数对象,以及析构函数在对象不再使用时立即被调用。
安装
为您的应用程序创建一个目录,切换到该目录,并执行
composer require jeremiah-shaulov/pdoi
示例
<?php require_once 'vendor/autoload.php'; use Pdoi\Pdoi as Pdo; $db = new Pdo ( 'mysql:host=localhost', 'root', '', [ PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION, PDO::ATTR_DEFAULT_FETCH_MODE => PDO::FETCH_ASSOC, PDO::MYSQL_ATTR_MULTI_STATEMENTS => false, PDO::MYSQL_ATTR_USE_BUFFERED_QUERY => false, PDO::ATTR_PERSISTENT => true, ] ); var_dump($db->query("SELECT Connection_id()")->fetchColumn());
从CLI运行此示例将每次显示不同的 Connection_id()
,因为进程生命周期中只有一个连接。但从PHP-FPM运行将显示相同的连接号出现多次。