Laravel 8集成Spatie多租户后队列Worker无法处理任务问题排查
解决spatie/laravel-multitenancy队列Worker数据库未选择问题
核心原因
队列Worker是常驻进程,启动时默认无租户上下文,若jobs表所在数据库未正确配置,或任务未携带租户标识,就会触发No database selected错误。
解决方案
1. 确认jobs表存储位置
jobs表必须放在landlord数据库中:
- 执行迁移时指定landlord连接:
php artisan migrate --database=landlord - 若已将
jobs表放在租户数据库中,需迁移到landlord库(租户感知队列依赖landlord库存储任务元数据,Worker启动时先从landlord取任务,再切换到租户库处理)。
2. 配置队列连接指向landlord
修改config/queue.php的数据库驱动配置,指定使用landlord连接:
'connections' => [ 'database' => [ 'driver' => 'database', 'table' => 'jobs', 'queue' => 'default', 'retry_after' => 90, 'connection' => 'landlord', // 关键:指定landlord连接 ], ],
3. 确保任务自动携带租户信息
你的配置中queues_are_tenant_aware_by_default已设为true,只要在租户上下文内分发任务,包会自动将租户ID附加到任务中:
// 例如在控制器(已自动设置租户)中分发任务 ProcessUserJob::dispatch($user);
若为自定义任务,无需额外实现接口,默认会被标记为租户感知;若需排除特定任务,可在任务类中添加:
public bool $tenantAware = false;
4. 验证租户数据库连接配置
检查config/database.php的tenant连接,需留空database字段,由SwitchTenantDatabaseTask动态设置:
'connections' => [ 'tenant' => [ 'driver' => 'mysql', 'host' => env('DB_HOST', '127.0.0.1'), 'port' => env('DB_PORT', '3306'), 'database' => '', // 必须留空,由租户切换任务填充 'username' => env('DB_USERNAME', 'forge'), 'password' => env('DB_PASSWORD', ''), 'charset' => 'utf8mb4', 'collation' => 'utf8mb4_unicode_ci', 'prefix' => '', 'strict' => true, ], ],
5. 单租户任务专属Worker(可选)
若需单独处理某租户的任务,可启动Worker时指定租户ID:
php artisan queue:work --queue=user --tenant=1
此方式仅适用于固定租户的场景,不推荐用于通用任务处理。
内容的提问来源于stack exchange,提问作者fahad shaikh
相关产品推荐
相关产品推荐

