nginx跨域访问配置的几种方法实现

 更新时间:2025年12月08日 10:58:38   作者:猩火燎猿  
本文详细介绍了Nginx跨域配置方法,包括基本配置、只允许指定域名、携带Cookie的跨域、动态设置允许的Origin、支持不同路径的跨域控制、静态资源跨域以及根据请求方法细分CORS策略,感兴趣的可以了解一下

一、基本跨域配置

在 nginx 的 location 块中添加以下内容:

location /api/ {
    add_header 'Access-Control-Allow-Origin' '*' always;
    add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS, PUT, DELETE' always;
    add_header 'Access-Control-Allow-Headers' 'Origin, Content-Type, Accept, Authorization' always;
 
    # 处理预检请求(OPTIONS)
    if ($request_method = 'OPTIONS') {
        add_header 'Access-Control-Max-Age' 1728000;
        add_header 'Content-Type' 'text/plain charset=UTF-8';
        add_header 'Content-Length' 0;
        return 204;
    }
 
    # 其他反向代理/静态资源配置...
    proxy_pass http://backend-server;
}

说明:

  • Access-Control-Allow-Origin:允许哪些域访问,* 表示所有域。
  • Access-Control-Allow-Methods:允许的 HTTP 方法。
  • Access-Control-Allow-Headers:允许的请求头。
  • OPTIONS 方法用于处理 CORS 预检请求,返回 204 No Content。

二、只允许指定域名跨域

如果只允许某个域(如 https://www.example.com)跨域:

add_header 'Access-Control-Allow-Origin' 'https://www.example.com' always; 

三、完整示例

假设你有一个前端(端口 8080)和后端(端口 8000),nginx 代理 /api/ 到后端:

server {
    listen 80;
    server_name your.domain.com;
 
    location /api/ {
        proxy_pass http://127.0.0.1:8000;
        add_header 'Access-Control-Allow-Origin' '*' always;
        add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS, PUT, DELETE' always;
        add_header 'Access-Control-Allow-Headers' 'Origin, Content-Type, Accept, Authorization' always;
 
        if ($request_method = 'OPTIONS') {
            add_header 'Access-Control-Max-Age' 1728000;
            add_header 'Content-Type' 'text/plain charset=UTF-8';
            add_header 'Content-Length' 0;
            return 204;
        }
    }
}

四、配置后重载 nginx

每次修改配置后,记得重载 nginx:

nginx -s reload 

五、注意事项

  • 如果后端也设置了 CORS,可能会有冲突,建议只在一个地方设置。
  • 如果需要携带 cookie,Access-Control-Allow-Origin 不能为 *,必须指定具体域名,并加上 Access-Control-Allow-Credentials: true

六、支持携带 Cookie 的跨域配置

如果你需要前端跨域请求时携带 cookie(如登录态),CORS 需要特殊配置:

  1. Access-Control-Allow-Origin 不能为 *,必须指定具体的域名。
  2. 需要加上 Access-Control-Allow-Credentials: true

示例:

location /api/ {
    proxy_pass http://127.0.0.1:8000;
 
    add_header 'Access-Control-Allow-Origin' 'https://www.example.com' always;
    add_header 'Access-Control-Allow-Credentials' 'true' always;
    add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS, PUT, DELETE' always;
    add_header 'Access-Control-Allow-Headers' 'Origin, Content-Type, Accept, Authorization' always;
 
    if ($request_method = 'OPTIONS') {
        add_header 'Access-Control-Max-Age' 1728000;
        add_header 'Content-Type' 'text/plain charset=UTF-8';
        add_header 'Content-Length' 0;
        return 204;
    }
}

前端请求时需要设置:

fetch('https://api.example.com/api/', {
  credentials: 'include', // 允许携带 cookie
  // 其他参数
})

七、根据请求头动态设置允许的 Origin

有时你希望根据请求头 Origin 动态设置允许的域名,可以用 nginx 的变量:

location /api/ {
    proxy_pass http://127.0.0.1:8000;
 
    if ($http_origin ~* "^https://(www\.example\.com|other\.domain\.com)$") {
        add_header 'Access-Control-Allow-Origin' "$http_origin" always;
        add_header 'Access-Control-Allow-Credentials' 'true' always;
    }
 
    add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS, PUT, DELETE' always;
    add_header 'Access-Control-Allow-Headers' 'Origin, Content-Type, Accept, Authorization' always;
 
    # 处理预检请求
    if ($request_method = 'OPTIONS') {
        add_header 'Access-Control-Max-Age' 1728000;
        add_header 'Content-Type' 'text/plain charset=UTF-8';
        add_header 'Content-Length' 0;
        return 204;
    }
}

八、常见问题排查

  1. add_header 不生效?

    • 确认 always 关键字已加上。
    • 确认没有被其他配置覆盖。
    • 确认 location 块没有被其他 server/location 块覆盖。
  2. OPTIONS 请求未返回 204?

    • 检查 if 语句是否正确。
    • 检查是否被后端拦截。
  3. 前端报错:CORS header ‘Access-Control-Allow-Origin’ missing?

    • 检查响应头是否包含该字段。
    • 用浏览器开发者工具 Network 检查响应头。
  4. 携带 cookie 时跨域失败?

    • 确认 Access-Control-Allow-Origin 不是 *,而是具体域名。
    • 确认 Access-Control-Allow-Credentials: true 已设置。
    • 前端 fetch/axios 需配置 credentials。

九、nginx 跨域配置模板(推荐)

可以将以下内容作为通用模板:

location /api/ {
    proxy_pass http://backend-server;
 
    # 支持跨域
    set $cors '';
    if ($http_origin ~* '^https://(www\.example\.com|other\.domain\.com)$') {
        set $cors 'true';
    }
 
    if ($cors = 'true') {
        add_header 'Access-Control-Allow-Origin' "$http_origin" always;
        add_header 'Access-Control-Allow-Credentials' 'true' always;
    }
 
    add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS, PUT, DELETE' always;
    add_header 'Access-Control-Allow-Headers' 'Origin, Content-Type, Accept, Authorization' always;
 
    # 预检处理
    if ($request_method = 'OPTIONS') {
        add_header 'Access-Control-Max-Age' 1728000;
        add_header 'Content-Type' 'text/plain charset=UTF-8';
        add_header 'Content-Length' 0;
        return 204;
    }
}

十、针对不同路径/接口做跨域控制

有时你只希望对部分接口(如 /api/)开放跨域,对其他接口(如 /admin/)不开放,可以这样配置:

server {
    listen 80;
    server_name your.domain.com;
 
    # 只对 /api/ 开放跨域
    location /api/ {
        proxy_pass http://backend-api;
        add_header 'Access-Control-Allow-Origin' '*' always;
        add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS, PUT, DELETE' always;
        add_header 'Access-Control-Allow-Headers' 'Origin, Content-Type, Accept, Authorization' always;
 
        if ($request_method = 'OPTIONS') {
            add_header 'Access-Control-Max-Age' 1728000;
            add_header 'Content-Type' 'text/plain charset=UTF-8';
            add_header 'Content-Length' 0;
            return 204;
        }
    }
 
    # /admin/ 不开放跨域
    location /admin/ {
        proxy_pass http://backend-admin;
        # 不添加跨域相关 header
    }
}

十一、静态资源跨域(如图片、字体、JS/CSS)

如果你希望静态资源(如图片、字体文件等)可以被其他域引用,需为静态资源 location 添加 CORS 响应头:

location /static/ {
    root /var/www/html;
    add_header 'Access-Control-Allow-Origin' '*' always;
    add_header 'Access-Control-Allow-Methods' 'GET, OPTIONS' always;
    add_header 'Access-Control-Allow-Headers' 'Origin, Content-Type, Accept' always;
}

注意:如果你希望字体文件可被第三方引用,必须加上 Access-Control-Allow-Origin,否则会有跨域问题。

十二、根据请求方法细分 CORS 策略

有时你希望 GET/POST/PUT/DELETE 允许跨域,而 PATCH 不允许,可以这样写:

location /api/ {
    proxy_pass http://backend-server;
 
    if ($request_method ~* "GET|POST|PUT|DELETE|OPTIONS") {
        add_header 'Access-Control-Allow-Origin' '*' always;
        add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS, PUT, DELETE' always;
        add_header 'Access-Control-Allow-Headers' 'Origin, Content-Type, Accept, Authorization' always;
    }
 
    if ($request_method = 'OPTIONS') {
        add_header 'Access-Control-Max-Age' 1728000;
        add_header 'Content-Type' 'text/plain charset=UTF-8';
        add_header 'Content-Length' 0;
        return 204;
    }
}

十三、反向代理多后端的跨域配置

如果 nginx 代理多个后端(如 /api1//api2/),每个后端都需要跨域:

location /api1/ {
    proxy_pass http://backend1;
    add_header 'Access-Control-Allow-Origin' '*' always;
    # ...同上
}
 
location /api2/ {
    proxy_pass http://backend2;
    add_header 'Access-Control-Allow-Origin' '*' always;
    # ...同上
}

十四、nginx 1.7.5 及以上版本的 always 参数

确保你用的 nginx 版本支持 always 参数,否则有些 header 在 4xx/5xx 状态下不会返回。

十五、安全建议

  1. 生产环境不要使用 *,要指定具体域名。
  2. 不建议在 / 根路径全局添加 CORS,容易引发安全隐患。
  3. 如需支持多域名跨域,推荐用变量和正则动态判断。
  4. 如果接口涉及敏感数据,务必开启认证和 HTTPS。

十六、调试技巧

  • 用 Chrome/Firefox 开发者工具的 Network 面板查看 Response Headers,确认 CORS 头是否正确返回。
  • 使用 curl -i 命令直接发起跨域请求,检查响应头。
  • 检查 nginx 日志(access.log 和 error.log)排查问题。

十七、完整多场景配置模板

server {
    listen 80;
    server_name your.domain.com;
 
    # 静态资源
    location /static/ {
        root /var/www/html;
        add_header 'Access-Control-Allow-Origin' '*' always;
    }
 
    # API1 跨域
    location /api1/ {
        proxy_pass http://backend1;
        add_header 'Access-Control-Allow-Origin' 'https://www.a.com' always;
        add_header 'Access-Control-Allow-Credentials' 'true' always;
        add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS, PUT, DELETE' always;
        add_header 'Access-Control-Allow-Headers' 'Origin, Content-Type, Accept, Authorization' always;
        if ($request_method = 'OPTIONS') {
            add_header 'Access-Control-Max-Age' 1728000;
            add_header 'Content-Type' 'text/plain charset=UTF-8';
            add_header 'Content-Length' 0;
            return 204;
        }
    }
 
    # API2 跨域
    location /api2/ {
        proxy_pass http://backend2;
        add_header 'Access-Control-Allow-Origin' 'https://www.b.com' always;
        add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS, PUT, DELETE' always;
        add_header 'Access-Control-Allow-Headers' 'Origin, Content-Type, Accept, Authorization' always;
        if ($request_method = 'OPTIONS') {
            add_header 'Access-Control-Max-Age' 1728000;
            add_header 'Content-Type' 'text/plain charset=UTF-8';
            add_header 'Content-Length' 0;
            return 204;
        }
    }
}

到此这篇关于nginx跨域访问配置的几种方法实现的文章就介绍到这了,更多相关nginx跨域访问配置内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • nginx配置多域名共用服务器80端口

    nginx配置多域名共用服务器80端口

    本文主要介绍了配置Nginx.conf文件,使得同一台服务器上的服务程序能够根据域名分发到相应的端口进行处理,从而实现用户通过abc.com或xyz.com直接访问到不同“网站”,感兴趣的可以了解一下
    2025-03-03
  • Nginx 如何部署指定文件夹下的项目(本地测试)

    Nginx 如何部署指定文件夹下的项目(本地测试)

    这篇文章主要介绍了Nginx 如何部署指定文件夹下的项目(本地测试),分为配置vue.config.js,指定生成环境的包,配置路由模式为hash(history模式刷新后,找不到页面),本文讲解的非常详细,需要的朋友可以参考下
    2024-01-01
  • Nginx limit 限制访问模块的方法

    Nginx limit 限制访问模块的方法

    本篇文章主要介绍了Nginx limit 限制访问模块的方法,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2018-03-03
  • Nginx日志输出配置json格式

    Nginx日志输出配置json格式

    本文主要介绍了Nginx日志输出配置json格式,包含log_format和access_log两种命令,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2024-07-07
  • 在Nginx中如何为页面配置用户名密码认证访问

    在Nginx中如何为页面配置用户名密码认证访问

    这篇文章主要介绍了在Nginx中如何为页面配置用户名密码认证访问的问题,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2025-06-06
  • Nginx 连接tomcat时会话粘性问题分析及解决方法

    Nginx 连接tomcat时会话粘性问题分析及解决方法

    这篇文章主要介绍了Nginx 连接tomcat时会话粘性问题分析及解决方法的相关资料,非常不错,具有一定的参考借鉴价值,需要的朋友可以参考下
    2015-10-10
  • 使Nginx服务器支持.htaccess的方法

    使Nginx服务器支持.htaccess的方法

    这篇文章主要介绍了使Nginx服务器支持.htaccess的方法,.htaccess配置文件设置是Apache上的好东西,现在我们让Nginx服务器也能使用它,需要的朋友可以参考下
    2015-07-07
  • 详解nginx 配置多个tomcat共用80端口

    详解nginx 配置多个tomcat共用80端口

    本篇文章主要介绍了nginx 配置多个tomcat共用80端口,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2017-06-06
  • nginx中的两个模块的proxy_pass的区别解析

    nginx中的两个模块的proxy_pass的区别解析

    在nginx中配置proxy_pass代理转发时,如果在proxy_pass后面的url加/,表示绝对根路径;如果没有/,表示相对路径,把匹配的路径部分也给代理走。本文给大家介绍nginx中的两个模块的proxy_pass的区别,感兴趣的朋友一起看看吧
    2021-11-11
  • nginx日志切割定时任务的实现

    nginx日志切割定时任务的实现

    Nginx日志切割能有效管理日志,便于查询、控制存储空间、提高处理效率、方便备份与归档,减少数据丢失风险,实现方法包括重命名日志文件、编写定时日志脚本和设置crontab定时任务
    2024-11-11

最新评论