🌐 Spring Boot 跨域处理终极指南

本文详细讲解 Spring Boot 项目中处理跨域问题的 4 种核心技巧,涵盖从基础概念到实战代码的完整解决方案,附代码注释避坑指南,助你彻底解决跨域难题!🚀


目录

  1. 什么是跨域?
  2. 理解 CORS
  3. Nginx 配置
  4. 配置类实现 addCorsMapping
  5. CorsFilter 过滤器模式
  6. 网关模式
  7. 方案对比总结

1. 什么是跨域?

  • 跨域(Cross-Origin)是浏览器基于 同源策略(Same-Origin Policy) 的安全限制。当以下任意一项不同**时,就会触发跨域:
要素 示例
协议不同 http:// vs https://
域名不同 a.com vs b.com
端口不同 localhost:8080 vs localhost:3000

跨域示意图


2. 理解 CORS

  • CORS(Cross-Origin Resource Sharing) 是现代浏览器支持的跨域解决方案,其核心是 HTTP 响应头 的协商机制:

CORS 关键响应头

响应头 作用
Access-Control-Allow-Origin 允许的源(域名)
Access-Control-Allow-Methods 允许的 HTTP 方法
Access-Control-Allow-Headers 允许的请求头
Access-Control-Max-Age 预检请求缓存时间(秒)

3. Nginx 配置

实现原理

  • 通过 Nginx 反向代理统一处理跨域,无需修改代码

配置示例

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
server {
listen 80;
server_name api.yourdomain.com;

location / {
# 允许跨域的域名(* 表示允许任意域名)
add_header 'Access-Control-Allow-Origin' '*';

# 允许的请求方法
add_header 'Access-Control-Allow-Methods' 'GET, POST, PUT, DELETE, OPTIONS';

# 允许的请求头
add_header 'Access-Control-Allow-Headers' 'Content-Type, Authorization';

# 处理预检请求
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://localhost:8080;
}
}

⚠️ 注意事项

  1. 生产环境不要使用 * 通配符,应指定具体域名
  2. 修改配置后需重载 Nginx:nginx -s reload

4. 配置类实现 addCorsMapping

实现原理

  • 通过 Spring Boot 的 WebMvcConfigurer 接口全局配置 CORS 规则。

代码示例

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.CorsRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;

@Configuration
public class CorsConfig implements WebMvcConfigurer {

@Override
public void addCorsMappings(CorsRegistry registry) {
registry.addMapping("/**") // 匹配所有路径
.allowedOrigins("http://localhost:3000") // 允许的源
.allowedMethods("GET", "POST", "PUT", "DELETE") // 允许的方法
.allowedHeaders("*") // 允许的请求头
.allowCredentials(true) // 允许发送 Cookie
.maxAge(3600); // 预检请求缓存时间
}
}

⚠️ 注意事项

  1. allowCredentials(true) 时不能使用 `allowedOrigins(“*”)
  2. 要处理 OPTIONS 预检请求的响应

5. CorsFilter 过滤器模式

实现原理

  • 通过自定义 Filter 在请求处理前添加 CORS 响应头。

代码示例

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.cors.CorsConfiguration;
import org.springframework.web.cors.UrlBasedCorsConfigurationSource;
import org.springframework.web.filter.CorsFilter;

@Configuration
public class GlobalCorsConfig {

@Bean
public CorsFilter corsFilter() {
// 1. 创建 CORS 配置对象
CorsConfiguration config = new CorsConfiguration();

// 允许的域名(不要使用 *)
config.addAllowedOrigin("http://localhost:3000");

// 允许的请求方法
config.addAllowedMethod("*");

// 允许的请求头
config.addAllowedHeader("*");

// 允许发送 Cookie
config.setAllowCredentials(true);

// 预检请求缓存时间(秒)
config.setMaxAge(3600L);

// 2. 为所有路径添加配置
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
source.registerCorsConfiguration("/**", config);

// 3. 返回 CorsFilter 对象
return new CorsFilter(source);
}
}

⚠️ 注意事项

  1. Filter 的顺序可能影响功能,建议设置为最高优先级
  2. 避免同时使用多种 CORS 配置方式导致冲突

6. 网关模式

实现原理

  • 在 API 网关层(如 Spring Cloud Gateway)统一处理跨域。

Gateway 配置示例

1
2
3
4
5
6
7
8
9
10
11
spring:
cloud:
gateway:
globalcors:
cors-configurations:
'[/**]':
allowedOrigins: "http://localhost:3000"
allowedMethods: "*"
allowedHeaders: "*"
allowCredentials: true
maxAge: 3600

⚠️ 注意事项

  1. 网关需要处理所有服务的跨域问题
  2. 确保网关配置覆盖所有路由规则
  3. 生产环境应禁用 allowedMethods: "*"

7. 方案对比总结

方案 优点 缺点 适用场景
Nginx 配置 性能最佳,无需修改代码 需要运维配合 已有 Nginx 代理的项目
addCorsMapping 配置简单,纯 Spring 实现 无法处理非 Controller 请求 简单项目
CorsFilter 全局处理,优先级高 需注意 Filter 顺序 需要精细控制的场景
网关模式 统一管理微服务跨域 依赖网关组件 微服务架构

掌握这 4 种跨域处理方式,根据项目架构灵活选择,从此告别跨域烦恼!🎉