mod_cache_disk必须与mod_proxy协同工作才能缓存java后端响应,单独启用无效;需同时加载mod_proxy、mod_proxy_http、mod_cache、mod_cache_disk及mod_headers等模块,并配置cacheenable disk、cacheignoreheaders set-cookie、cacheignorenolastmod on,且java端必须返回public+max-age缓存头。

mod_cache_disk 必须和 mod_proxy 搭配才能缓存 Java 后端响应
单独启用 mod_cache 和 mod_cache_disk 不会自动缓存动态请求——Apache 默认只缓存满足严格条件的响应,比如带 Cache-Control 或 Expires 头、状态码为 200/301/404、且无 Set-Cookie 的响应。Java 应用(如 Spring Boot)默认不设这些头,所以即使配置了磁盘缓存,也几乎全是 X-Cache: MISS。
真正起作用的链路是:mod_proxy 把请求转发给后端 → Java 返回带缓存头的响应 → mod_cache_disk 拦截并落盘。所以必须同时启用:
-
mod_proxy和mod_proxy_http -
mod_cache和mod_cache_disk -
mod_headers或mod_expires(用于补全或覆盖响应头)
漏掉任意一个,缓存就形同虚设。
CacheEnable disk / 的路径匹配很关键,不是写 / 就能缓存全部
CacheEnable disk / 看似作用于根路径,实际只对 Apache 直接处理的请求生效;而经 ProxyPass 转发的请求,其“路径”在 Apache 内部仍以代理目标为准。常见错误是:
- 写了
CacheEnable disk /,但后端返回的是Set-Cookie,被默认忽略(需加CacheIgnoreHeaders Set-Cookie) - 写了
CacheEnable disk /api/,但代理规则是ProxyPass /v1/ http://localhost:8080/api/,此时实际缓存路径应为/v1/,而非后端真实路径 - 缓存目录权限不对:
CacheRoot "/var/cache/apache2/mod_cache_disk"必须由 Apache 进程用户(如www-data)可写,否则日志里只有(13)Permission denied
建议先用 CacheEnable disk /static/ 测试静态资源缓存,确认目录结构和命中率后再扩展到动态路径。
Java 响应头必须显式声明 public + max-age,否则 mod_cache_disk 直接跳过
Apache 的缓存策略非常保守:哪怕 Java 返回了 Cache-Control: max-age=3600,只要没带 public,mod_cache_disk 就认为它不可共享,拒绝缓存。Spring Boot 中典型写法是:
Apache Superset 是一个广泛采用的开源 BI 平台,用于 SQL 探索、图表构建和仪表板交付。当代理需要查询仓库数据、组装仪表板或使用成熟的分析界面解释指标而不是临时笔记本代码时,此技能非常有用。
ResponseEntity.ok()
.header("Cache-Control", "public, max-age=3600")
.body(data);
注意以下几点:
- 不要用
private或含no-store的值,它们会让缓存彻底失效 - 含用户身份、Session 或 CSRF Token 的接口,绝不能缓存,必须返回
Cache-Control: private, no-cache - 如果 Java 无法改代码,可在 Apache 配置中用
Header edit Cache-Control "private" "public"强制覆盖(仅限可信内部服务)
缓存是否生效,最直接验证方式是看响应头是否有 X-Cache: HIT from example.com,以及 CacheRoot 下是否生成了 hash 子目录文件。
CacheIgnoreNoLastMod On 是绕过 Last-Modified 缺失导致 MISS 的关键开关
很多 Java 接口不返回 Last-Modified 头,而 mod_cache_disk 默认要求它存在才考虑缓存(尤其配合 CacheLastModifiedFactor 时)。结果就是大量响应明明有 max-age 却始终 MISS。
解决方法是在缓存配置块中加上:
<ifmodule mod_cache_disk.c> CacheIgnoreNoLastMod On # 其他配置... </ifmodule>
这个开关一开,Apache 就不再检查 Last-Modified,完全依赖 Cache-Control 或 Expires 决定是否缓存。这是 Java 场景下最容易被忽略、却影响最大的配置项。
缓存路径、响应头、忽略头检查——这三个点没对齐,mod_cache_disk 就只是个空转的模块。别指望重启一次就能生效,得逐层验证头、日志、文件系统三者是否一致。










