server块中add_header不全局生效,因其不继承至子块且无法处理options预检请求;需在每个location中显式配置add_header ... always,并用if拦截options返回204。

直接在 server 块里加 add_header 并不能真正实现“全局跨域”,因为 Nginx 的 add_header 指令**不会继承到子块中**,且对 OPTIONS 预检请求必须单独拦截处理,否则带认证或自定义头的请求必然失败。
为什么 server 块里写 add_header 不等于全局生效
Nginx 的 add_header 只作用于当前上下文(server、location 或 if),且不会向下继承。比如你在 server 块写了:add_header 'Access-Control-Allow-Origin' '*';
但所有 location 块里的响应默认不带这个头——除非该 location 也显式写了 add_header,或者你用 always 参数强制注入(仅限 Nginx ≥1.7.5)。
-
add_header在server块中定义 ≠ 所有子location自动携带 CORS 头 - 静态资源(如
/assets/)、API 接口(如/api/)、甚至根路径/,都需各自确保头被添加 - 若某个
location内有proxy_pass或fastcgi_pass,且未配置add_header,则响应压根没有 CORS 头
如何让所有响应都带 CORS 头(含预检)
必须同时满足两个条件:头能覆盖全部路径 + OPTIONS 请求不被转发给后端。最稳妥的做法是:在每个需要响应的 location 中显式配置,并用 if ($request_method = 'OPTIONS') 拦截预检。
前端设计与 UI/UX 全方位优化专家。覆盖视觉层次、排版系统、色彩理论、响应式布局、交互体验、动画动效、无障碍访问、性能优化八大维度,帮助开发者将普通页面升级为高品质产品级界面。前端设计与 UI/UX 全方位优化专家。覆盖视觉层次、排版系统、色彩理论、响应式布局、交互体验、动画动效、无障碍访问、性能优化八大维度,帮助开发者将普通页面升级为高品质产品级界面。
- 不要依赖
server块统一写,而是把 CORS 配置下沉到每个关键location,例如:location / { ... }、location /api/ { ... } - 每处都加
add_header ... always;(always确保即使返回 304 或错误码也带头) -
if ($request_method = 'OPTIONS')必须放在proxy_pass或fastcgi_pass之前,否则预检请求会透传到后端,而多数后端不处理它 - 示例最小可用片段:
if ($request_method = 'OPTIONS') { add_header 'Access-Control-Allow-Origin' '*' always; add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS' always; add_header 'Access-Control-Allow-Headers' 'Content-Type, Authorization' always; add_header 'Access-Control-Max-Age' 1728000 always; add_header 'Content-Type' 'text/plain; charset=utf-8' always; add_header 'Content-Length' 0 always; return 204; }
带 credentials 时不能用 *,且必须配 Access-Control-Allow-Credentials
前端若设了 credentials: 'include'(比如发 Cookie 或 Authorization),Nginx 就不能用 '*' 作 Access-Control-Allow-Origin 值,否则浏览器直接拒绝响应。
- 必须指定确切源,例如:
add_header 'Access-Control-Allow-Origin' 'https://app.example.com' always; - 必须同步加:
add_header 'Access-Control-Allow-Credentials' 'true' always; - 注意:一旦加了
Access-Control-Allow-Credentials true,Access-Control-Allow-Origin就不能再是*,否则整个 CORS 响应会被浏览器忽略 - 多域名支持需用
map模块动态匹配,不能靠硬编码或 if 判断多个域名
真正“全局”不是靠一次配置覆盖所有路径,而是靠结构化地在每个出口位置补全头 + 正确拦截 OPTIONS。最容易漏掉的是 always 参数和 if 块的位置——这两点一错,90% 的跨域问题就还在控制台里报着错。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!










