当前位置:首页 > 后端开发 > 正文

Java跨域访问如何解决?

在Java中解决跨域访问,主要通过服务端配置实现: ,1. 使用 @CrossOrigin注解标注Controller方法 ,2. 实现 WebMvcConfigurer接口配置全局CORS规则 ,3. 通过过滤器手动添加响应头(如Access-Control-Allow-Origin) ,4. Spring Security中配置 CorsConfigurationSource ,本质是服务端设置HTTP响应头允许跨域请求。

Spring Boot的@CrossOrigin注解(控制器级别)

适用场景:单个Controller或方法需要跨域

@RestController
public class UserController {
    // 允许所有来源访问此接口
    @CrossOrigin(origins = "*")
    @GetMapping("/users")
    public List<User> getUsers() {
        return userService.getAllUsers();
    }
    // 限制特定域名访问
    @CrossOrigin(origins = "https://trusted-domain.com")
    @PostMapping("/update")
    public ResponseEntity updateUser() {
        // 业务逻辑
    }
}

优点:简单直接,无需全局配置
缺点:需在每个接口重复添加注解


全局CORS配置(Spring MVC)

适用场景:整个项目统一跨域规则

Java跨域访问如何解决?  第1张

@Configuration
public class CorsConfig implements WebMvcConfigurer {
    @Override
    public void addCorsMappings(CorsRegistry registry) {
        registry.addMapping("/api/**")  // 指定路径
                .allowedOrigins("https://www.example.com", "http://localhost:3000")
                .allowedMethods("GET", "POST", "PUT", "DELETE")
                .allowedHeaders("*")
                .allowCredentials(true)
                .maxAge(3600);  // 1小时内预检请求缓存
    }
}

关键参数说明

  • allowCredentials(true):允许携带Cookie
  • maxAge(3600):减少OPTIONS预检请求次数

CorsFilter(Servlet容器级别)

适用场景:非Spring项目或需更底层控制

@Bean
public CorsFilter corsFilter() {
    UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
    CorsConfiguration config = new CorsConfiguration();
    config.setAllowCredentials(true);
    config.addAllowedOrigin("https://secure-client.org");
    config.addAllowedHeader("*");
    config.addAllowedMethod("OPTIONS");
    config.addAllowedMethod("GET");
    config.addAllowedMethod("POST");
    source.registerCorsConfiguration("/**", config); // 应用到所有路径
    return new CorsFilter(source);
}

Nginx反向代理(基础设施层解决)

适用场景:前端与API服务器分离部署

server {
    listen 80;
    server_name api.yourdomain.com;
    location / {
        # 允许跨域
        add_header 'Access-Control-Allow-Origin' 'https://web.yourdomain.com';
        add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
        add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,Content-Type';
        add_header 'Access-Control-Allow-Credentials' 'true';
        # 反向代理到Java应用
        proxy_pass http://localhost:8080;
    }
}

优势:无需修改Java代码,性能更高


JSONP(传统方案,仅限GET请求)

适用场景:兼容老旧浏览器(不推荐新项目使用)

@GetMapping("/getData")
public void getData(HttpServletRequest req, HttpServletResponse res) {
    String callback = req.getParameter("callback"); // 获取回调函数名
    String data = "{"name":"John"}"; // JSON数据
    // 返回JavaScript函数调用
    res.setContentType("application/javascript");
    res.getWriter().write(callback + "(" + data + ")");
}

前端调用

<script>
function handleData(data) {
    console.log(data.name); // 输出John
}
</script>
<script src="http://api-server.com/getData?callback=handleData"></script>

安全最佳实践

  1. 限制来源域名:避免使用,明确指定allowedOrigins
  2. 禁用敏感接口跨域:如/admin/**路径不开放CORS
  3. 启用HTTPS:跨域传输必须使用加密连接
  4. 验证Origin头:防止伪造请求(Spring Security可配置)

引用说明

  • Mozilla CORS指南:https://developer.mozilla.org/zh-CN/docs/Web/HTTP/CORS
  • Spring官方文档:https://docs.spring.io/spring-framework/reference/web/webmvc-cors.html
  • OWASP安全建议:https://cheatsheetseries.owasp.org/cheatsheets/Cross-Site_Request_Forgery_Prevention_Cheat_Sheet.html
0