yii2.0.48默认session使用php file存储,负载均衡或容器化下会话丢失,需显式配置redis等后端及timeout;redis需正确定义组件、指定database、设置timeout=1;cookie应启用httponly、secure(yii_env_prod)、samesite(strict/lax);并禁用auto_start,按需手动open。

Yii2.0.48 中 Session 默认使用 PHP 原生 file 存储,单机部署尚可,但一上负载均衡或容器化环境就会出现登录态丢失、跨请求数据不一致等问题,必须显式配置存储后端与生命周期策略。
修改 session 组件配置
打开 config/web.php,在 components 数组中找到或新增 'session' 键:
将 'class' => 'yii\web\Session' 保留,但必须覆盖 'handler' 和 'timeout' 两项——不设 handler 仍走 file,不设 timeout 则沿用 php.ini 的 1440 秒,极易被用户感知为“突然掉线”。
【timeout 必须设为整数秒,不能写 '30 minutes' 或 '0.5 hour'】
若使用 Redis 存储,handler 配置如下:
'handler' => [ 'class' => 'yii\redis\Session', 'redis' => 'redis', // 对应 config/components 中定义的 redis 组件名 ]
Redis Session 部署要点
确保 config/main.php 或 config/web.php 的 components 中已正确定义 'redis':
'redis' => [ 'class' => 'yii\redis\Connection', 'hostname' => '127.0.0.1', 'port' => 6379, 'database' => 1, // 不要用 database 0,避免与缓存混用 ]
执行 redis-cli -n 1 KEYS "yii:*" 可验证 session 是否真正写入该库;若返回空,说明 handler 未生效或 redis 连接失败。
Redis 连接超时默认是 0(无限),但生产环境必须设 'timeout' => 1,否则网络抖动时 PHP 进程会长时间阻塞,拖垮整个应用。
Cookie 安全强化
Session ID 通过 Cookie 传输,不加固等于裸奔:
在 session 配置中加入:'cookieParams' => [ 'httpOnly' => true, 'secure' => YII_ENV_PROD, 'sameSite' => 'Strict' ]
【sameSite 设为 'Strict' 会阻止跨站 POST 提交携带 session cookie,若站点需嵌入 iframe 或对接第三方表单,此处必须改为 'Lax'】
secure 参数设为 YII_ENV_PROD 而非硬编码 true,否则开发环境 HTTPS 未启用时将无法写入 cookie。
禁用 session 自动启动
Yii 默认在应用初始化时就启动 session,哪怕控制器根本不需要——这会强制生成 session ID、写入存储、增加 Redis QPS。
第一步:在 web/index.php 中,require __DIR__ . '/../vendor/autoload.php'; 后添加:
ini_set('session.auto_start', '0');
第二步:在需要 session 的控制器 action 开头,显式调用 \Yii::$app->session->open(); —— 仅当真要读写时才开,避免无谓开销。
第三步:确认所有 beforeAction() 中未调用 $this->redirect() 或 $this->refresh(),这些方法内部会隐式触发 session 启动,绕过你的手动控制。











