laravel 9+ 默认不兼容 predis 是因为其默认使用 phpredis 扩展(c 扩展),且 config/database.php 中 'client' => env('redis_client', 'phpredis') 预设为 phpredis;若未显式设 redis_client=predis 并安装 predis/predis 包,laravel 会尝试用 phpredis 实例化连接,导致 class "predis\client" not found 或 session/cache 静默失效。

不能直接“切换”,必须同时改 SESSION_DRIVER、REDIS_CLIENT 和扩展依赖,否则会报 Class "Predis\Client" not found 或静默失败。
为什么 Laravel 9+ 默认不兼容 Predis?
Laravel 9 开始默认使用 phpredis 扩展(C 扩展),且 config/database.php 中的 'client' => env('REDIS_CLIENT', 'phpredis') 已预设为 phpredis。即使你装了 predis/predis,只要 REDIS_CLIENT 没显式设为 predis,Laravel 仍会尝试用 phpredis 实例化连接 —— 而它根本找不到 Predis\Client 类。
- 错误现象:
Class "Predis\Client" not found,或更隐蔽的:Session 写不进 Redis、缓存命中率始终为 0,但无任何报错 - 根本原因:Laravel 的 Redis 连接工厂根据
REDIS_CLIENT值决定实例化哪个客户端类,不匹配就崩或跳过 - 注意:
predis/predis已被作者弃用(2020 年起),Laravel 官方也明确建议迁移到phpredis;仅在无法装扩展的受限环境才考虑回退
要切到 Predis,这三步缺一不可
只改 .env 或只装包,必然失败。必须同步调整以下三项:
- 运行
composer require predis/predis(确认vendor/predis/predis存在) - 在
.env中设:REDIS_CLIENT=predis(必须显式写,不能靠默认值) - 检查
config/database.php中'redis' => [ 'client' => env('REDIS_CLIENT', 'phpredis') ]—— 确保该行未被硬编码成'phpredis',否则.env设置无效
Session 和 Cache 都得单独验证是否真走 Predis
改完配置后,php artisan config:clear 和 php artisan cache:clear 必须执行,否则旧配置可能还在内存里。然后验证两个关键路径:
- Session:登录后,在
artisan tinker中运行Redis::connection('session')->keys('laravel_session*'),看是否有 key 返回;若空,说明 Session 没写进 Redis,大概率还是在用phpredis或连接失败 - Cache:执行
cache()->store('redis')->put('test', 'ok', 60),再用Redis::connection('cache')->get('test')读取;如果报错或返回 null,检查config/cache.php中'redis'驱动是否指向了正确的 connection 名(如'connection' => 'cache'),且该 connection 在database.php中存在并设对了database值 - 别忘了:若用了多个 Redis 连接(比如
default、cache、session),每个连接的'client'都继承自顶层'client',不支持单个 connection 单独指定客户端
PHP 扩展残留会导致最诡异的失败
如果你之前装过 phpredis 扩展(extension=redis.so),即使现在想用 Predis,PHP 进程仍可能加载该扩展,并干扰类自动加载逻辑 —— 尤其在 CLI 模式下(artisan、tinker)和 FPM 模式行为不一致。
- 查是否加载:
php -m | grep redis,有输出就说明扩展已启用 - 临时禁用:注释掉
php.ini中的extension=redis.so行,重启 PHP-FPM 或 Apache - 线上环境务必统一:FPM 和 CLI 的
php.ini可能不同,php --ini和phpinfo()查清楚各自加载的是哪个
真正麻烦的不是改配置,而是你以为改完了,其实某个地方还卡着旧 client、旧扩展、旧连接池缓存 —— 最稳的办法是:改完立刻进 tinker,用 Redis::connection()->client() 打印实例类型,看到 Predis\Client 对象才算落地成功。
php免费学习视频:立即使用
踏上前端学习之旅,开启通往精通之路!从前端基础到项目实战,循序渐进,一步一个脚印,迈向巅峰!











