symfony反向代理是基于httpcache类的轻量http缓存层,仅依据响应头(如cache-control、etag)工作,需手动设置缓存头且不支持标签失效;生产环境推荐varnish/nginx,但可与httpcache协同使用。

Symfony 反向代理(也叫网关缓存或 HTTP 缓存层)是部署在应用前的独立缓存组件,它不依赖外部服务(如 Varnish 或 Nginx),而是由 Symfony 自带的 HttpCache 类实现。配置它不复杂,但需要明确它的定位:它只处理符合 HTTP 缓存规范的响应,不是万能缓存,也不替代 Redis 或文件缓存。
启用内置反向代理
默认情况下,Symfony 的主入口文件(如 public/index.php)直接使用 Kernel::handle(),不经过缓存。要启用反向代理,需改用 HttpCache 包裹内核:
- 创建
public/app.php(或重命名现有入口),内容如下:
require_once dirname(__DIR__).'/config/bootstrap.php'; use App\Kernel; use Symfony\Bundle\FrameworkBundle\HttpCache\HttpCache; $kernel = new Kernel($_SERVER['APP_ENV'], (bool) $_SERVER['APP_DEBUG']); $kernel->boot(); $cache = new HttpCache($kernel); $cache->handle($_SERVER);
- 确保
APP_ENV=prod且APP_DEBUG=false,因为HttpCache在 debug 模式下会跳过缓存逻辑 - 该代理会自动读取响应头中的
Cache-Control、ETag、Last-Modified等字段来决定是否缓存或返回 304
控制缓存行为:响应头是关键
反向代理本身不主动缓存,它完全依赖控制器返回的响应头。你必须显式设置这些头才能让缓存生效:
- 在控制器中设置标准缓存策略:
$response = new Response($content); $response->setPublic(); $response->setMaxAge(3600); // 缓存 1 小时 $response->setSharedMaxAge(3600); return $response;
- 支持 ETag 自动生成(需启用):
$response->setEtag($someUniqueHash); // 或让 Symfony 自动计算(基于响应内容) $response->setEtag(md5($content));
- 配合条件请求,客户端发
If-None-Match时,HttpCache会自动返回 304
自定义缓存规则与失效逻辑
HttpCache 允许继承并扩展其行为,比如添加自定义缓存键、按 URL 路径排除缓存、或集成外部失效机制:
- 新建类继承
HttpCache:
class MyHttpCache extends HttpCache
{
protected function getKey(Request $request): string
{
// 可加入 host、locale、用户角色等维度
return parent::getKey($request).'-'.$request->getPreferredLanguage();
}
}
- 在入口文件中使用该类替换原
HttpCache - 注意:它不支持标签化清除(tag-based invalidation),如需精细失效,应搭配 Redis +
cache.adapter.redis_tag_aware使用,反向代理仅作最外层加速
和外部反向代理共存的建议
生产环境通常不用 Symfony 自带代理,而选 Varnish 或 Nginx 缓存,因为它们性能更高、功能更全。但两者可协同:
- Symfony
HttpCache可作为开发/测试环境的轻量替代,无需额外运维 - 上线后,Nginx/Varnish 放在最前端,Symfony 应用退为上游;此时仍需保持控制器输出合规响应头,否则外层代理无法识别缓存意图
- 若同时启用两者,注意避免重复缓存或头冲突(例如 Nginx 设置了
add_header Cache-Control,可能覆盖 PHP 输出的头)











