Spring Boot对Ajax跨域访问的支持实现
2017-06-11 17:52
246 查看
Spring Boot对Ajax跨域访问的支持实现
作者在SE305课程中,需要设计一款新时代互联网购票系统,团队使用vue.js前端,Spring MVC的后台架构。开发过程中遇到跨域访问的问题,故写成此博客进行探讨解决方案。主要涉及的话题有:Spring Boot
AJAX
跨域访问
问题定义
究竟什么是跨域访问?作者引用了MDN对CORS的定义https://developer.mozilla.org/zh-CN/docs/Web/HTTP/Access_control_CORS当一个资源从与该资源本身所在的服务器的域或端口不同的域或不同的端口请求一个资源时,资源会发起一个跨域 HTTP 请求。
比如,站点 http://domain-a.com 的某 HTML 页面通过 的 src 请求
http://domain-b.com/image.jpg。网络上的许多页面都会加载来自不同域的CSS样式表,图像和脚本等资源。
出于安全考虑,浏览器会限制从脚本内发起的跨域HTTP请求。例如,XMLHttpRequest 和 Fetch 遵循同源策略。因此,使用
XMLHttpRequest或 Fetch
的Web应用程序只能将HTTP请求发送到其自己的域。为了改进Web应用程序,开发人员要求浏览器厂商允许跨域请求。
下面是简单的流程图:
根本解决思路
客户端和服务器之间使用 CORS 首部字段来处理跨域权限:也就是说在HTTP request以及response加入CORS对应的首部行字段即可解决。下面讲解在spring下的后台解决方案
实现方案
方案一
在Controller类或其方法上加@CrossOrigin注解@CrossOrigin(origins = "*", maxAge = 3600) @RestController @RequestMapping("/Cinema") public class CinemaController { //Cinema控制器,跨域来源为*即任何来源 }
方案二
在web.xml中配置一个CorsFilter<filter-mapping> <filter-name>CorsFilter</filter-name> <url-pattern>/*</url-pattern> </filter-mapping>
而filter的实现如下
@Component public class InitCORSFilter extends OncePerRequestFilter { private Logger logger = LoggerFactory.getLogger(InitCORSFilter.class); public InitCORSFilter() { } //表示服务器端允许任意Domain访问请求 @Override protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain) throws ServletException, IOException { if (request.getHeader("Access-Control-Request-Method") != null && "OPTIONS".equals(request.getMethod())) { response.addHeader("Access-Control-Allow-Origin", "*"); response.addHeader("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, OPTIONS"); response.addHeader("Access-Control-Allow-Headers", "origin, content-type, accept, x-requested-with, sid, mycustom, smuser"); response.addHeader("Access-Control-Max-Age", "600"); //Max age为10mins } filterChain.doFilter(request, response); } }
方案三(本次项目使用的方法)
本次项目使用spring-boot,可以把CorsFilter作为@Bean加入到@Configuration中即可配置,方便简洁。@Configuration public class CorsConfig { private CorsConfiguration buildConfig() { CorsConfiguration corsConfiguration = new CorsConfiguration(); corsConfiguration.addAllowedOrigin("*"); corsConfiguration.addAllowedHeader("*"); corsConfiguration.addAllowedMethod("*"); return corsConfiguration; } @Bean public CorsFilter corsFilter() { UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource(); source.registerCorsConfiguration("/**", buildConfig()); return new CorsFilter(source); } }//通过任意请求
总结
解决的不二思路就是当捕获到Cors请求(使用Filter实现)时,返回包含特定Header的Response。相关文章推荐
- Java Spring Boot 服务器端断点续传功能支持 实现代码
- springboot实现服务器端消息推送(H5原生支持)
- 在U-Boot中实现对Yaffs镜像的支持
- u-boot2010.03 移植篇(四)-----支持DM9000,实现tftp下载
- SpringBoot事务注解实现原理
- Spring Boot中实现Quartz动态定时任务
- 如何做实时监控?—— 参考 Spring Boot 实现
- Spring支持的Remoting实现技术
- Spring-mvc+SockJS实现即时通讯教程,并提供各种浏览器版本的支持
- springboot springjpa 支持多个数据源
- MAVEN下实现spring boot打包成war包(spring boot 01)
- 4. Spring Boot 1.2.5,Spring Data JPA多数据源支持
- u-boot2010.03 移植篇(四)-----支持DM9000,实现tftp下载
- 【spring-boot】spring-boot集成ehcache实现缓存机制
- Spring-boot的控制器实现
- [Spring Boot Debug]在 intellij idea 中无法编译 javad代码 -source 1.6 中不支持 diamond 运算符
- spring 对 timer 的支持---实现简单的web中定时器操作
- spring实现jdbctemplate添加事务支持示例
- intellij+springboot+springloaded 实现热部署
- 如何做实时监控?—— 参考 Spring Boot 实现