thinkphp默认不自动缓存db或model查询,必须显式调用cache::get/set或查询链式cache()方法;redis键名需匹配配置前缀,且cache()仅对查询构建器有效,ttl单位为秒。

缓存接口数据必须走 Cache::get/set,不是所有查询都自动缓存
ThinkPHP 默认不会给任意 Db::find() 或 Model::get() 自动加 Redis 缓存。你写的 Db::name('user')->find(1) 就是直连数据库,哪怕配置了 Redis 驱动也不会命中缓存。
真正触发缓存的写法只有两种:
-
Cache::get($key)+Cache::set($key, $value, $ttl)手动控制读写 -
Db::table('user')->cache($key, $ttl)->find(1)显式调用cache()链式方法(仅对查询构建器生效)
Model 类的 UserModel::find(1) 即使继承自 think\Model,也不走缓存——除非你在模型里重写了 getCacheKey() 并配合全局查询缓存开关(极少用,易出错)。
Redis 缓存键名不匹配是接口返回旧数据的头号原因
比如你代码里写的是 Cache::get('user_'.$id),但 config/cache.php 里配置了 'prefix' => 'tp6_cache:',那实际存进 Redis 的 key 是 tp6_cache:user_123,而 Cache::get() 会自动加前缀,所以没问题;但如果你用原生 $redis->get('user_123') 就永远拿不到。
更常见的是多环境/多实例混淆:
- 开发机和测试机共用一个 Redis 实例,但 prefix 不同 → 相互看不到对方缓存
- TP6 启用了标签缓存(tag cache),但
php think clear:cache不清 tag,得用Cache::tag('user')->clear() - 前端请求带了
X-Requested-With: XMLHttpRequest,后端却按普通页面逻辑缓存,导致接口和页面共享同一 key
验证方式:用 redis-cli 连上后执行 keys "tp6_cache:user_*",确认 key 是否真实存在、值是否最新。
cache() 链式方法只对查询构建器有效,且 TTL 单位是秒不是分钟
Db::table('user')->where('status', 1)->cache('active_users', 60)->select() 这行能缓存,但下面这些都不行:
-
Db::query('SELECT * FROM user WHERE status = ?', [1])->cache(...)——query()返回数组,没有cache()方法 -
Db::name('user')->find(123)没加cache()→ 完全不走缓存层 -
cache('user_123', 1)(数字 1)→ 实际缓存 1 秒,不是 1 分钟,别被单位骗了
另外注意:cache($key, $ttl) 的 $key 是可选参数,省略时框架会自动生成哈希,但自动生成的 key 无法手动清除,排查问题时极难定位。
APP_DEBUG 开启时,路由缓存和模板缓存全部失效,但数据缓存照常工作
很多人清完缓存还看到旧数据,第一反应是“缓存没清干净”,结果发现是 APP_DEBUG = true 导致整个路由缓存机制关闭,每次请求都重新解析路由+加载控制器+执行逻辑——你以为是缓存没更新,其实是代码每次都重新跑了一遍,但中间某步又读了旧缓存值。
快速验证:在控制器里加一行 dump(config('app.app_debug'));,输出 true 就说明你根本没进路由缓存流程,别浪费时间查 Redis key。
真正要关掉的不是 APP_DEBUG,而是确认 config/cache.php 中 'default' => 'redis' 且对应 store 配置无误;再检查 runtime/cache/ 目录权限是否允许写入(尤其 Docker 环境里 uid 不一致极易导致缓存写失败但无报错)。
php免费学习视频:立即使用
踏上前端学习之旅,开启通往精通之路!从前端基础到项目实战,循序渐进,一步一个脚印,迈向巅峰!











