多实例部署的Next.js 16应用有个隐形陷阱:默认内存缓存让每个容器各自为政。两台ECS任务共享一个ALB,各自执行'use cache'函数,写入本地LRU,彼此看不见对方的数据。调用revalidateTag('posts')只清掉收到请求的那台机器的缓存——用户刷新页面,运气不好就命中旧数据。
Next.js 16把缓存拆成了两套接口。cacheHandler(单数)管Pages Router的ISR和按需重验证;cacheHandlers(复数)管新的'use cache'指令和cacheComponents: true。社区里最流行的开源方案@fortedigital/nextjs-cache-handler@3.2.0在package.json里声明支持next: ">=16.1.5",但README把复数API整列标成❌:cacheHandlers配置、'use cache'指令、'use cache: remote'、'use cache: private'、cacheComponents——全部"Not yet supported - Help needed"。
社区PR #207试图补全这些功能,因PHASE_PRODUCTION_BUILD回归问题被维护者搁置三个月。维护者在Issue #152里说得直白:"Next.js只关心Vercel,不关心其他云或集群环境。"这意味着多实例部署的Redis缓存支持,短期内不会出现在官方路线图上。
作者有套跑在AWS ECS Fargate上的多实例Next.js 16应用,需要这些功能现在就工作。于是另起炉灶做了个小包@leejpsd/nextjs-cache-handler@0.2.0,MIT协议。核心思路是一个wrapper同时实现两套接口,带几个生产环境刚需的默认值。
配置方式很直接:next.config.ts里同时指定cacheHandler和cacheHandlers,分别指向两个入口文件。cache-components.cjs里createCacheComponentsHandler接收redis客户端配置、buildNamespace(按部署版本自动隔离)、abortTimeoutMs: 1500、staleWhileRevalidate: true,以及可选的singleFlight: true(v0.2新增的防缓存击穿)。
这个方案让'use cache'、revalidateTag、updateTag、cacheLife全部可用。作者在真实流量环境里做了验证——这是上游开源方案目前没覆盖的场景。
热门跟贴