同域测试
分析:
1.浏览器地址:http://manage.jt.com/test.html
2.ajax请求地址:http://manage.jt.com/test.json
结论:当浏览器地址与ajax请求的地址(协议://域名:端口)相同时可以实现正常的业务调用。
<script type="text/javascript" src="http://manage.jt.com/js/jquery-easyui-1.4.1/jquery.min.js"></script>
<!--引入类库之后,执行js代码-->
<script type="text/javascript">
<!--让整个页面加载完成之后执行js-->
$(function(){
$.get("http://manage.jt.com/test.json",function(data){
alert(data.name);
})
})
</script>
跨域测试
分析:
1.浏览器地址:http://www.jt.com/test.html
2.ajax请求地址:http://manage.jt.com/test.json
结论:
如果请求地址(协议://域名:端口)不相同则导致请求调用失败。
浏览器-同源策略说明
说明: 浏览器规定 发起ajax时如果请求协议/域名/端口号如果3者有一个与当前的浏览器的地址不相同时,则违反了同源策略的规定.则浏览器不予解析返回值.
跨域问题:违反了同源策略的规定就是跨域请求。
跨域的方式
1、JSONP跨域
2、cors跨域
JSONP跨域原理
1.利用javascript中的src属性实现跨域请求;
2.自定义回调函数function callback(xxxx);
3.将返回值结果进行特殊的格式封装 callback(json);
4.由于利用src属性进行调用,所以只能支持get请求类型。
封装返回值
hello({"id":"1","name":"tom"})
页面js编辑
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>测试JSON跨域问题</title>
<script type="text/javascript">
/*JS是解释执行的语言 */
/*定义回调函数 */
function hello(data){
alert(data.name);
}
</script>
<!--该json一直保存到浏览器中等待调用,但是没有函数名称无法调用 -->
<script type="text/javascript" src="http://manage.jt.com/test.json"></script>
<script type="text/javascript" src="http://manage.jt.com/js/jquery-easyui-1.4.1/jquery.min.js"></script>
</head>
<body>
<h1>JS跨域问题</h1>
</body>
</html>
JSONP
JSONP(JSON with Padding)是JSON的一种“使用模式”,可用于解决主流浏览器的跨域数据访问的问题。由于同源策略,一般来说位于 server1.example.com 的网页无法与不是 server1.example.com的服务器沟通,而 HTML 的
JSONP优化
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>JSONP测试</title>
<script type="text/javascript" src="http://manage.jt.com/js/jquery-easyui-1.4.1/jquery.min.js"></script>
<script type="text/javascript">
$(function(){
alert("测试访问开始!!!!!")
$.ajax({
url:"http://manage.jt.com/web/testJSONP",
type:"get", //jsonp只能支持get请求
dataType:"jsonp", //dataType表示返回值类型
jsonp: "callback", //指定参数名称
jsonpCallback: "hello", //指定回调函数名称
success:function (data){ //data经过jQuery封装返回就是json串
console.log(data);
}
});
})
</script>
</head>
<body>
<h1>JSON跨域请求测试</h1>
</body>
</html>
编辑后端Controller
package com.jt.web.controller;
import com.jt.pojo.ItemDesc;
import com.jt.util.ObjectMapperUtil;
import jdk.nashorn.internal.runtime.regexp.JoniRegExp;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
public class JSONPController {
/**
* 实现JSONP跨域请求
* url地址: http://manage.jt.com/web/testJSONP?callback=xxxxxx
* 参数: 暂时没有可以不接
* 返回值: callback(JSON);
*/
@RequestMapping("/web/testJSONP")
public String testJSONP(String callback){
ItemDesc itemDesc = new ItemDesc();
itemDesc.setItemId(1000L).setItemDesc("JSONP测试!!!");
String json = ObjectMapperUtil.toJSON(itemDesc);
return callback+"("+json+")";
}
}
控制台输出
JSONPObject说明
@RequestMapping("/web/testJSONP")
public JSONPObject testJSONP(String callback){
ItemDesc itemDesc = new ItemDesc();
itemDesc.setItemId(1000L).setItemDesc("JSONP测试!!!");
return new JSONPObject(callback, itemDesc);
}
JSONP全局异常处理机制
问题说明
当后端服务器执行出错时,会执行全局异常的处理,但是JSONP的请求的调用要求返回值类型是callback(json)结构,所以需要重构全局异常处理的返回值结构类型。
编辑全局异常处理机制
package com.jt.aop;
import com.fasterxml.jackson.databind.util.JSONPObject;
import com.jt.vo.SysResult;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.RestControllerAdvice;
import javax.servlet.http.HttpServletRequest;
@RestControllerAdvice //定义全局异常的处理类
public class SystemAOP {
//定义全局异常的方法
/**当遇到什么异常时,程序开始执行 参数一般是calss类型
* 如果一旦发生异常,则应该输出异常的信息,之后返回错误数据即可
* @return
*
* 解决跨域全局异常处理的规则:
* jt项目的跨域都是使用JSONP http://xxxx?callback=xxxx
* 如果请求中携带了callback参数,则认为是JSONP跨域请求。
* 如何获取callback的参数?
* HttpServletRequest用这个对象从controller中获取参数
*
*/ @ExceptionHandler({RuntimeException.class})
public Object systemAop(Exception e,HttpServletRequest request){
e.printStackTrace();
String callback = request.getParameter("callback");
if(StringUtils.isEmpty(callback)){
return SysResult.fail();
}else{
return new JSONPObject(callback, SysResult.fail());
}
}
}
cors跨域
cors调用原理
实现cors调用
在公共配置文件中添加cors配置
@Configuration //标识我是一个配置类
public class CorsConfig implements WebMvcConfigurer {
//在后端 配置cors允许访问的策略
@Override
public void addCorsMappings(CorsRegistry registry){
registry.addMapping("/**")
.allowedMethods("GET","POST") //定义允许跨域的请求类型
.allowedOrigins("*") //任意网址都可以访问
.allowCredentials(true) //是都允许携带cookie
.maxAge(1800); //设定请求长连接超时时间 (探针)
}
}
cors调用响应头解析
cors跨域测试
JSON数据格式
关于跨域的总结
1.jsonp
jsonp本质利用javaScript中的src属性的get请求实现的跨域.
返回值必须经过特殊的格式封装.
2.cors
添加在响应头中信息.指定哪些服务器允许访问.
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。