跨域问题Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin
文章目录1.bug详情:2.解决方案【前后端解决方案】:2.1.前端方案:2.1.1. 设置Access-Control-Allow-Origin2.1.2. 设置proxyTable2.2.后端方案:2.2.1. 在controller对应的方法里添加“Access-Control-Allow-Origin”标头”2.2.2. @CrossOrigin注解解决跨域3.结语:1.bug详情:v..
·
文章目录
1.bug详情:
vue项目,用axios请求,前后端联调,在局域网内,
浏览器访问别人的地址可以获取数据,但是通过接口请求,就会跨域
2.解决方案【前后端解决方案】:
2.1.前端方案:
2.1.1. 设置Access-Control-Allow-Origin
如果XMLHttpRequest 请求的URL和当前页面不同一个域中时,
浏览器会检测响应http header中有没有 Access-Control-Allow-Origin项,
如果此项值为空或者与当前页面的域不匹配时,就会报此错误。
解决方案:设置Access-Control-Allow-Origin为【请求的域名+端口】,有人也说设置*,情况不同吧,可以试试
config.headers["Access-Control-Allow-Origin"]="http://127.0.0.1:8080";
还有很多其他实现方式,例如:
config.headers.setItem("Access-Control-Allow-Origin","127.0.0.1:8081");
所以自由发挥,最后头信息加上Access-Control-Allow-Origin就OK
2.1.2. 设置proxyTable
设置proxyTable,实际上就是设置代理路径
(PS:设置config文件之后,需要重新npm run dev)
dev: {
env: require('./dev.env'),
port: 8080,
autoOpenBrowser: true,
assetsSubDirectory: 'static',
assetsPublicPath: '/',
proxyTable: {
'/api': {
target: '请求地址ip加端口',
changeOrigin: true,
pathRewrite: {
'^/api': '/'
}
}
},
}
2.2.后端方案:
2.2.1. 在controller对应的方法里添加“Access-Control-Allow-Origin”标头”
既然说了《请求的资源上不存在“Access-Control-Allow-Origin”标头》,
那么我就在controller文件对应的方法里给他添加一个标头就好了
/**
* 查询当前登录用户的信息
* DSY
*/
@RequestMapping(value = "/login", method = RequestMethod.GET)
@ResponseBody
public User login(HttpServletResponse response, @RequestParam(value="username")String username,@RequestParam(value="password")String password) {
response.setHeader("Access-Control-Allow-Origin", "*");
return loginService.getUser(username, password);
}
2.2.2. @CrossOrigin注解解决跨域
如果你用的也是spring框架,并且版本在4.2以上,可以用@CrossOrigin这个注解,
括号中的url可以换成“”*“”,如果这个controller里有多个方法,注解可以直接写在类的最上边。
a.写在方法上:
/**
* 查询当前登录用户的信息
* DSY
*/
//写在方法上
@CrossOrigin(origins = "http://localhost:8080/") // 实现跨域 要求spring的版本必须4.2以上
@RequestMapping(value = "/login", method = RequestMethod.GET)
@ResponseBody
public User login(HttpServletResponse response, @RequestParam(value="username")String username,@RequestParam(value="password")String password) {
return loginService.getUser(username, password);
}
b.写在类上:
//写在类上,不用每个方法都写这个注解了
@CrossOrigin(origins="*",maxAge=3600)
@RestController
public class LoginController {}
2.2.3. 今天发现一个特别强的,只需要启动类上加代码就可以了
@Bean
public CorsFilter corsFilter() {
final UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
final CorsConfiguration config = new CorsConfiguration();
config.setAllowCredentials(true); // 允许cookies跨域
config.addAllowedOrigin("*");// 允许向该服务器提交请求的URI,*表示全部允许。。这里尽量限制来源域,比如http://xxxx:8080 ,以降低安全风险。。
config.addAllowedHeader("*");// 允许访问的头信息,*表示全部
config.setMaxAge(18000L);// 预检请求的缓存时间(秒),即在这个时间段里,对于相同的跨域请求不会再预检了
config.addAllowedMethod("*");// 允许提交请求的方法,*表示全部允许,也可以单独设置GET、PUT等
source.registerCorsConfiguration("/**", config);
return new CorsFilter(source);
}
3.结语:
解决办法还有很多,我提及部分只是对我的项目比较受用,大家可以多尝试尝试,
然后如果单使用哪一条无效就把这些都加上吧,总有一条适合你!!!(我就这么干的໒( ◔ ▽ ◔ )७)
以后我遇到新的解决办法也会在博客里更新的。
更多推荐
已为社区贡献1条内容
所有评论(0)