Spring Framework 从4.2开始支持配置CORS。
Spring MVC支持CORS的范围包括:
- 方法级别配置CORS
- 全局配置CORS
方法级别配置CORS
使用注解@CrossOrgin可以对@RequestMapping注解的方法设置CORS。
@RestController
@RequestMapping("/users")
public class UserController {
@CrossOrigin
@GetMapping("/{id}")
public User query(@PathVariable Long id) {
// ...
}
@RequestMapping(method = RequestMethod.DELETE, path = "/{id}")
public void remove(@PathVariable Long id) {
// ...
}
}
@CrossOrigin默认设置的orgins为所有,即Access-Control-Allow-Origin=*,指定的方法为@RequestMapping设置的HTTP方法。
@CrossOrigin支持以下几种配置:
- origins:配置请求来源,设置Access-Control-Allow-Origin。星号*表示所有。
- allowedHeaders:允许header,设置Access-Control-Allow-Headers。星号表示运行所有的头信息。
- exposedHeaders:暴露的头信息,设置Access-Control-Expose-Headers,默认空。
- allowCredentials:设置Access-Control-Allow-Credentials,请求是否带cookie信息,默认为允许。
- maxAge:设置Access-Control-Max-Age,默认为1800秒,即30分。
- methods:请求的HTTP方法,默认为@RequestMapping设置的HTTP方法。
@CrossOrigin也可配置在Controller级别设置,应用于Controller里的所有@RequestMapping的方法
@CrossOrigin(maxAge = 3600)
@RestController
@RequestMapping("/users")
public class UserController {
@CrossOrigin("http://example.com")
@GetMapping("/{id}")
public User query(@PathVariable Long id) {
// ...
}
@RequestMapping(method = RequestMethod.DELETE, path = "/{id}")
public void remove(@PathVariable Long id) {
// ...
}
}
当Controller级别和方法级别同时配置了@CorsOrigin时,它会合并两者的配置。
全局配置CORS
全局配置有两种方式:基于JavaConfig和基于XML。
JavaConfig
JavaConfig使用CorsRegistry对全局配置CORS。
@Configuration
@EnableWebMvc
public class WebConfig extends WebMvcConfigurerAdapter {
@Override
public void addCorsMappings(CorsRegistry registry) {
registry.addMapping("/api/**")
.allowedOrigins("http://domain2.com")
.allowedMethods("PUT", "DELETE")
.allowedHeaders("header1", "header2", "header3")
.exposedHeaders("header1", "header2")
.allowCredentials(false).maxAge(3600);
}
}
Spring Boot 配置全局CORS
使用spring-boot可以把@EnableWebMvc去掉。也可以返回一个WebMvcConfigurer
@Configuration
public class MyConfiguration {
@Bean
public WebMvcConfigurer corsConfigurer() {
return new WebMvcConfigurerAdapter() {
@Override
public void addCorsMappings(CorsRegistry registry) {
registry.addMapping("/api/**")
.allowedOrigins("http://domain2.com")
.allowedMethods("PUT", "DELETE")
.allowedHeaders("header1", "header2", "header3")
.exposedHeaders("header1", "header2")
.allowCredentials(false).maxAge(3600);
}
};
}
}
XML
xml使用<mvc:cors></cors>
<mvc:cors>
<mvc:mapping path="/api/**"
allowed-origins="http://domain1.com, http://domain2.com"
allowed-methods="GET, PUT"
allowed-headers="header1, header2, header3"
exposed-headers="header1, header2" allow-credentials="false"
max-age="123" />
<mvc:mapping path="/resources/**"
allowed-origins="http://domain1.com" />
</mvc:cors>