使用tenancyforlaravel实现中心域登录跳转租户子域报403未认证问题求助
问题根因
你遇到的403未认证错误是两个核心配置缺失导致的:
- Laravel默认Session cookie仅在生成cookie的当前域名下生效,中心域
example.com生成的登录态cookie无法被子域foo.example.com读取 - 多库模式下,租户子域的
auth中间件默认查询当前租户独立库的users表,和中心域登录时校验的中心库users表数据不互通,就算Session正常传递也会因为找不到对应用户返回未认证
解决步骤
1. 配置Session跨子域共享
修改项目根目录.env文件中的Session配置项:
SESSION_DOMAIN=.example.com SESSION_SAME_SITE=lax # 生产环境开启HTTPS后可补充配置 SESSION_SECURE=true
修改后执行php artisan config:clear清空配置缓存。该配置会让所有example.com的一级、二级子域都能共享中心域生成的登录态Cookie。
2. 适配多库模式下的用户认证逻辑
你可以根据业务需求选择以下任意一种方案:
方案A:同步用户数据到租户库
在创建租户的逻辑中,同步将对应用户的账号信息(ID、邮箱、密码等)写入新租户的独立库users表,保证中心库和租户库的用户主键ID完全一致,租户侧auth中间件可以直接查询到匹配的用户信息。
方案B:自定义租户侧Auth Guard
修改config/auth.php,新增一个专门读取中心库的Guard,租户侧受保护路由指定使用该Guard进行认证,避免查询租户库的用户表:
// config/auth.php 中 guards 数组新增 'central_auth' => [ 'driver' => 'session', 'provider' => 'central_users', ], // providers 数组新增 'central_users' => [ 'driver' => 'eloquent', 'model' => App\Models\User::class, 'connection' => 'central', // 这里填写你中心库的数据库连接名称 ],
修改tenant.php中的中间件引用:
Route::middleware(['auth:central_auth'])->group(function () { Route::get('/dashboard', function () { return 'Tenant' . tenant('id'); }); });
3. 校验中间件执行顺序
确保InitializeTenancyBySubdomain中间件在StartSession中间件之前执行,避免租户初始化晚于Session启动,导致Session配置读取错误。你可以在app/Http/Kernel.php的$middlewareGroups中调整顺序:
protected $middlewareGroups = [ 'web' => [ \App\Http\Middleware\EncryptCookies::class, \Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse::class, \Stancl\Tenancy\Middleware\InitializeTenancyBySubdomain::class, // 移到StartSession之前 \Illuminate\Session\Middleware\StartSession::class, // 其余中间件保持原有顺序不变 ], ];
内容的提问来源于stack exchange,提问作者Svoby
相关产品推荐
相关产品推荐

