hyperf微服务内部调用应通过connectionfactory封装多库连接,按业务域配置语义化数据库连接(user_db/order_db/log_db),显式声明driver与pool参数并合理设置max_connections,rpc服务中构造注入connectionfactory实现协程安全、可维护的跨库查询,事务严格限定单库。

Hyperf 微服务内部调用需兼顾多库隔离、协程安全与业务可维护性。不建议在 RPC 方法里硬编码连接名或重复写 Db::connection(...),应通过分层封装解耦数据源逻辑。
按业务域划分数据库连接
在 config/autoload/databases.php 中为不同模块定义语义化连接名,例如:
- user_db:用户中心主库(MySQL 8.0,含密码插件适配)
- order_db:订单分片库(MySQL 5.7,启用预处理模拟)
- log_db:只读日志库(独立 PostgreSQL 实例)
每个连接必须显式声明 driver、pool 参数,并按实例实际能力设置 max_connections(如 RDS MySQL 5.7 max_connections=200,则对应连接池设 ≤150)。
封装连接工厂类
新建 app/Database/ConnectionFactory.php,统一管理连接获取逻辑:
namespace App\Database;
use Hyperf\Database\Connection;
use Hyperf\Database\ConnectionInterface;
use Hyperf\Di\Annotation\Inject;
class ConnectionFactory
{
public function getUserConnection(): ConnectionInterface
{
return \Hyperf\DbConnection\Db::connection('user_db');
}
public function getOrderConnection(): ConnectionInterface
{
return \Hyperf\DbConnection\Db::connection('order_db');
}
public function getLogConnection(): ConnectionInterface
{
return \Hyperf\DbConnection\Db::connection('log_db');
}
}
该类可配合依赖注入使用,避免全局静态调用污染测试边界;也可根据上下文(如租户 ID、业务标签)动态返回连接,但需注意跨库 JOIN 不支持,关联查需拆成多次查询+内存拼接。
在 RPC 服务中安全使用
服务提供者(Provider)的业务方法内,优先通过构造函数注入 ConnectionFactory:
class UserService implements UserInterface
{
public function __construct(
private ConnectionFactory $connectionFactory,
private LoggerInterface $logger
) {}
public function getUserWithOrders(int $uid): array
{
$user = $this->connectionFactory->getUserConnection()
->table('users')->where('id', $uid)->first();
$orders = $this->connectionFactory->getOrderConnection()
->table('orders')->where('user_id', $uid)->get();
return ['user' => $user, 'orders' => $orders];
}
}
事务需严格限定在单库内,跨库操作不可加同一 transaction 包裹。若需最终一致性,改用本地消息表 + 定时补偿。
注意连接池与协程生命周期
Hyperf 默认启用协程驱动,但需确认:
- Swoole 运行在协程模式(
enable_coroutine => true) - 数据库连接池配置中
pool.max_connections不超过后端 DB 实例允许上限 - 避免在协程外(如 TaskWorker 或 PHP-FPM 模式)复用同一 Connection 实例
所有数据库操作天然协程化,无需手动 yield 或 await,但阻塞式文件读写、sleep 等仍会破坏调度,须替换为协程等价 API。











