Springboot如何优雅的解决ajax+自定义headers的跨域请求
1、什么是跨域
由于浏览器同源策略(同源策略,它是由Netscape提出的一个著名的安全策略。现在所有支持JavaScript 的浏览器都会使用这个策略。所谓同源是指,域名,协议,端口相同。),凡是发送请求url的协议、域名、端口三者之间任意一与当前页面地址不同即为跨域。
具体可以查看下表:
2、springboot如何解决跨域问题
1.普通跨域请求解决方案:
①请求接口添加注解@CrossOrigin(origins = "http://127.0.0.1:8020", maxAge = 3600)
说明:origins = "http://127.0.0.1:8020" origins值为当前请求该接口的域
②通用配置(所有接口都允许跨域请求)
新增一个configration类 或 在Application中加入CorsFilter和CorsConfiguration方法
@Configuration
public class CorsConfig {
private CorsConfiguration buildConfig() {
CorsConfiguration corsConfiguration = new CorsConfiguration();
corsConfiguration.addAllowedOrigin("*"); // 1允许任何域名使用
corsConfiguration.addAllowedHeader("*"); // 2允许任何头
corsConfiguration.addAllowedMethod("*"); // 3允许任何方法(post、get等)
return corsConfiguration;
} @Bean
public CorsFilter corsFilter() {
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
source.registerCorsConfiguration("/**", buildConfig()); // 4
return new CorsFilter(source);
}
}
2.ajax自定义headers的跨域请求
$.ajax({
type:"GET",
url:"http://localhost:8766/main/currency/sginInState",
dataType:"JSON",
data:{
uid:userId
},
beforeSend: function (XMLHttpRequest) {
XMLHttpRequest.setRequestHeader("Authorization", access_token);
},
success:function(res){
console.log(res.code)
}
})
此时请求http://localhost:8766/main/currency/sginInState接口发现OPTIONS http://localhost:8766/main/currency/sginInState 500错误,普通跨域的解决方案已经无法解决这种问题,为什么会出现OPTIONS请求呢?
原因
浏览器会在发送真正请求之前,先发送一个方法为OPTIONS的预检请求 Preflighted requests 这个请求是用来验证本次请求是否安全的,但是并不是所有请求都会发送,需要符合以下条件:
请求方法不是GET/HEAD/POST
POST请求的Content-Type并非application/x-www-form-urlencoded, multipart/form-data, 或text/plain
请求设置了自定义的header字段
对于管理端的接口,我有对接口进行权限校验,每次请求需要在header中携带自定义的字段(token),所以浏览器会多发送一个OPTIONS请求去验证此次请求的安全性。
为何OPTIONS请求是500呢?
OPTIONS请求只会携带自定义的字段,并不会将相应的值带入进去,而后台校验token字段时 token为NULL,所以验证不通过,抛出了一个异常。
那么我们现在来解决这种问题:
① spring boot项目application.yml中添加
spring:
mvc:
dispatch-options-request: true
注意:这种解决方案可能在某些情况下并不能解决OPTIONS问题,原因可能是环境问题,也可能是复杂的自定义filter过滤器配置问题等。
②添加过滤器配置
第一步:手写RequestFilter请求过滤器配置类此类需要实现HandlerInterceptor类,HandlerInterceptor类是org.springframework.web.servlet.HandlerInterceptor下的。
具体代码实现:
@Component
public class RequestFilter implements HandlerInterceptor {
public boolean preHandler(HttpServletRequest request,HttpServletResponse response,Object handler){
response.setHeader("Access-Control-Allow-Origin", "*");
response.setHeader("Access-Control-Allow-Credentials", "true");
response.setHeader("Access-Control-Allow-Methods", "GET, HEAD, POST, PUT, PATCH, DELETE, OPTIONS");
response.setHeader("Access-Control-Max-Age", "86400");
response.setHeader("Access-Control-Allow-Headers", "Authorization");
// 如果是OPTIONS请求则结束
if (HttpMethod.OPTIONS.toString().equals(request.getMethod())) {
response.setStatus(HttpStatus.NO_CONTENT.value());
return false;
}
return true;
}
}
第二步:手写MyWebConfiguration此类需要继承WebMvcConfigurationSupport。
注意:WebMvcConfigurationSupport是2.x版本以上的,1.x版本为WebMvcConfigurerAdapter 。
具体代码实现:
@Component
public class MyWebConfiguration extends WebMvcConfigurationSupport{
@Resource
private RequestFilter requestFilter;
@Override
public void addInterceptors(InterceptorRegistry registry) {
// 跨域拦截器
registry.addInterceptor(requestFilter).addPathPatterns("/**");
}
}
此时我们就完美解决了ajax+自定义headers的跨域请求了,欢迎随时交流学习。
推荐阅读(点击文字可跳转)
3.线上环境部署概览
4.Springboot Vue shiro 实现前后端分离、权限控制
Springboot如何优雅的解决ajax+自定义headers的跨域请求的更多相关文章
- Springboot如何优雅的解决ajax+自定义headers的跨域请求[转]
1.什么是跨域 由于浏览器同源策略(同源策略,它是由Netscape提出的一个著名的安全策略.现在所有支持JavaScript 的浏览器都会使用这个策略.所谓同源是指,域名,协议,端口相同.),凡是发 ...
- Ajax+Spring MVC实现跨域请求(JSONP)(转)
背景: AJAX向后台(springmvc)发送请求,报错:已阻止交叉源请求:同源策略不允许读取 http://127.0.0.1:8080/DevInfoWeb/getJsonp 上的远程资源.可 ...
- Ajax+Spring MVC实现跨域请求(JSONP)
背景: AJAX向后台(springmvc)发送请求,报错:已阻止交叉源请求:同源策略不允许读取 http://127.0.0.1:8080/DevInfoWeb/getJsonp 上的远程资源.可 ...
- Ajax+Spring MVC实现跨域请求(JSONP)JSONP 跨域
JSONP原理及实现 接下来,来实际模拟一个跨域请求的解决方案.后端为Spring MVC架构的,前端则通过Ajax进行跨域访问. 1.首先客户端需要注册一个callback(服务端通过该callba ...
- 20191204-使用nginx解决ajax测试调用接口跨域问题
问题描述 之前要测试一个http的接口,在postman中测试成功,但使用ajax调用却跨域.于是通过使用ngin反向代理的方式来解决ajax调用跨域问题 测试页面的内容 <html> & ...
- Ajax操作如何实现跨域请求 (JSONP和CORS实现Ajax跨域的原理)
由于浏览器存在同源策略机制,同源策略阻止ajax (XMLHttpRequest) 从一个源加载的文档或脚本获取或设置另一个源加载的文档的属性. 特别的:由于同源策略是浏览器的限制,所以请求的发送和响 ...
- jQuery Ajax 简单的实现跨域请求
html 代码清单: <script type="text/javascript" src="http://www.youxiaju.com/js/jquery-1 ...
- ajax发送多个跨域请求回调不混乱
var count = 0; var codes = ""; function refreshCache(urls){ try { var url = urls.split(&qu ...
- 解决asp.net mvc的跨域请求问题
web.config中配置如下内容: <system.webServer> <httpProtocol> <customHeaders> <add name= ...
随机推荐
- hdu5319 简单模拟
题意很好懂,大致就是三种颜色,红和蓝一起会变绿,给个终态矩阵,问从原始状态到终态最少画几笔? 按一定规则画 思路就是记红为1,蓝为2,绿为3,先遍历绿色,针对每一块绿色进行删除,每找到一块绿色,首先 ...
- D3DXCreateTexture
HRESULT D3DXCreateTexture( __in LPDIRECT3DDEVICE9 pDevice, __in UINT Width, __in UINT Height, __in U ...
- Sicily 8843 Ranking and Friendship
http://soj.me/8843 题意:几个人想做好朋友,朋友之间相差位置小于等于k,且长度相同分析:排序,将长度相同的放在一起.若长度相同,第i个人能放进去的条件是位置相差下雨等于k. ...
- HDU 5739 Fantasia 双连通分量 树形DP
题意: 给出一个无向图,每个顶点有一个权值\(w\),一个连通分量的权值为各个顶点的权值的乘积,一个图的权值为所有连通分量权值之和. 设删除顶点\(i\)后的图\(G_i\)的权值为\(z_i\),求 ...
- Redis实现之字典跳跃表
跳跃表 跳跃表是一种有序数据结构,它通过在每个节点中维持多个指向其他节点的指针,从而达到快速访问节点的目的.跳跃表支持平均O(logN).最坏O(N)的时间复杂度查找,还可以通过顺序性操作来批量处理节 ...
- 【01】《html5权威指南》(扫描版)(全)
[01]<html5权威指南>(扫描版)(全) []魔芋:无高清电子书. 只看第五部分,高级功能. 作者:(美)弗里曼 著,谢延晟,牛化成,刘美英 译 [美]adam freeman ...
- loj2045 「CQOI2016」密钥破解
CQOI 板子大赛之 pollard rho #include <iostream> #include <cstdio> using namespace std; typede ...
- Python-S9——Day100-Web前端框架之Vue
01 课程简介: 02 let和const: 03 箭头函数: 04 对象的单体模式: 05 nodejs介绍和npm操作: 06 webpack.babel介绍和vue的第一个案例: 07 昨日内容 ...
- PHP 与 Redis 入门教程
Redis 官方推荐的 PHP 客户端是 Predis 和 phpredis. 前者是完全使用 PHP 代码实现的原生客户端,而后者则是使用 C 语言编写的 PHP 扩展.在功能上两者区别并不大,就性 ...
- Leetcode 525.连续数组
连续数组 给定一个二进制数组, 找到含有相同数量的 0 和 1 的最长连续子数组. 示例 1: 输入: [0,1] 输出: 2 说明: [0, 1] 是具有相同数量0和1的最长连续子数组. 示例 2: ...