Symfony中Doctrine主从连接调试:如何查看查询执行的主/从库
如何在Symfony+Doctrine的主从配置中查看查询使用的是主库还是从库
要解决这个主从查询追踪的问题,最可靠的方式是自定义Doctrine的SQL日志记录器,把每条查询对应的连接类型(主库/从库)直接追加到日志输出里。下面是具体的实现步骤:
方法一:自定义Doctrine SQL Logger
这个方法能让你全局控制日志内容,每条查询前都会明确标注是主库还是从库,方便长期调试。
- 创建自定义日志类
在你的Symfony项目中,新建src/Logger/CustomDoctrineLogger.php文件,实现Doctrine的SQLLogger接口:
<?php namespace App\Logger; use Doctrine\DBAL\Logging\SQLLogger; use Doctrine\DBAL\Connection; use Psr\Log\LoggerInterface; class CustomDoctrineLogger implements SQLLogger { private $logger; public function __construct(LoggerInterface $logger) { $this->logger = $logger; } public function startQuery($sql, array $params = null, array $types = null) { // 获取当前活跃的数据库连接 $connection = Connection::getCurrentConnection(); // 利用Doctrine主从连接自带的方法判断是否为从库 $connectionType = $connection->isConnectedToSlave() ? 'SLAVE' : 'MASTER'; // 输出带连接类型标记的日志 $this->logger->debug(sprintf('[%s] %s', $connectionType, $sql), [ 'params' => $params ?? [], 'types' => $types ?? [], ]); } public function stopQuery() { // 接口要求必须实现,无需额外操作 } }
- 注册服务并配置Doctrine使用它
在config/services.yaml中注册这个自定义日志服务:
services: App\Logger\CustomDoctrineLogger: arguments: ['@logger'] # 依赖Symfony默认的日志服务
然后在config/packages/doctrine.yaml里,给你的主从连接配置指定这个SQL日志器:
doctrine: dbal: default_connection: default connections: default: url: '%env(DATABASE_URL)%' # 主库连接地址 slave: - url: '%env(DATABASE_SLAVE_URL)%' # 从库连接地址 sql_logger: '@App\Logger\CustomDoctrineLogger' # 启用自定义日志器
- 查看日志
重启应用后,执行tail -f app/logs/dev/dev-2018-05-15.log(如果是Symfony 4+版本,日志路径为var/log/dev.log),就能看到每条查询前都标注了[MASTER]或[SLAVE],轻松区分查询走的是哪个库。
方法二:临时验证方案(快速调试)
如果只是临时需要验证某段代码的查询连接,可以在代码中手动输出连接信息:
$connection = $entityManager->getConnection(); dump($connection->isConnectedToSlave() ? '当前使用从库' : '当前使用主库');
不过这个方法只能针对特定代码块,无法全局追踪所有查询。
额外调试提示
- Doctrine默认会自动将读操作路由到从库,写操作路由到主库。如果遇到副本延迟导致的旧数据问题,可以强制读主库:
$query = $entityManager->createQuery('SELECT u FROM App\Entity\User u'); $query->setHint(\Doctrine\ORM\Query::HINT_FORCE_PARTITION, 'master'); $users = $query->getResult(); - 确保dev环境的日志级别设置为
DEBUG,这样所有Doctrine查询都会被记录到日志中。
内容的提问来源于stack exchange,提问作者Bouffe
相关产品推荐
相关产品推荐

