文章目录
1.Ajax简述
AJAX是“Asynchronous Javascript And XML”(异步JavaScript和XML),用于创建快速动态网页的技术。有很多使用 AJAX 的应用程序案例:新浪微博、Google 地图、开心网等等。
- 那么,首先来了解一下Ajax的同步、异步请求方式?
同步请求:当前发出请求之后,浏览器不再运行,必须等待请求执行完成(返回数据)后,再去执行后续代码。我们知道js是单线程的,所以避免在原生js的Ajax请求中使用同步请求方式,会造成阻塞状态或假死现象。
异步请求:当前发出的请求与后续代码同时执行。即在请求过程中浏览器可以做任何事情,互不妨碍。
2.实现Ajax
1) 关键:XMLHttpRequest 对象
所有的异步交互都是通过XMLHttpRequest对象实现的。它用于幕后与服务器交换数据,进行后台数据的访问。
优点:
- 源于异步交互的优势,所有拥有局部刷新技术,可以在不重新加载页面的情况下更新网页的数据。
比如说:百度搜索页面(重新搜索内容 在本页面刷新新内容)- 在页面已加载后从服务器请求数据
- 在页面已加载后从服务器接收数据
- 在后台向服务器发送数据
2) 工作原理:
Ajax的原理简单来说通过XmlHttpRequest对象来向服务器发异步请求,从服务器获得数据,然后用javascript来操作DOM而更新页面。这其中最关键的一步就是从服务器获得请求数据。
3) 步骤:
1)创建对象
- 所有现代的浏览器(IE7+、Firefox、Chrome、Safari 和 Opera)都支持XMLHttpRequest对象。
var http = new XMLHttpRequest();
- 旧版本的 Internet Explorer(IE5 和 IE6)使用 ActiveX 对象。
var http = new ActiveXObject("Microsoft.XMLHTTP");
比如说为了保证所有浏览器的兼容性,我们就可以去做出如下判断:
if (window.XMLHttpRequest)
{
// IE7+, Firefox, Chrome, Opera, Safari 浏览器执行代码
var http=new XMLHttpRequest();
}
else
{
// IE6, IE5 浏览器执行代码
var http=new ActiveXObject("Microsoft.XMLHTTP");
//可以把http写成全局变量
}
2)建立服务器连接
http.open(method,url,async);
open()方法的参数:
- method:请求的类型;GET 或 POST
- url:文件在服务器上的位置(请求的服务器路径)
- async:true(异步)或 false(同步)
当使用 async=true 时,请规定在响应处于 onreadystatechange 事件中的就绪状态时执行的回调函数
区别GET 或 POST两种请求方式:
- GET请求会将参数跟在URL后进行传递,而POST请求则是作为HTTP消息的实体内容发送给WEB服务器。
- GET方式提交的数据最多只能是1024字节,而POST方式传输的数据量大,可以达到2M。
- GET方式请求数据会被浏览器缓存起来,可从浏览器的历史记录中读取到这些数据,例对于账号密码等私密数据缺乏安全性。而POST方式相对来说就可以避免这些问题。
- Post请求必须设置Content-Type值为application/x-form-www-urlencoded;
- 发送请求时,GET请求的参数在URL中,所以send()的参数为null,而POST请求在使用send()时,需要赋传递的参数data。
3)发送请求
http.send(string);
send()方法的参数:
- string:仅用于POST请求方式
4)服务器响应
http.onreadystatechange = function () {}
每当 readyState 改变时,就会触发 onreadystatechange 事件。
- readyState:存有 XMLHttpRequest 的5种状态。
0: 请求未初始化
1: 服务器连接已建立
2: 请求已接收
3: 请求处理中
4: 请求已完成,且响应已就绪- status:
200: “OK”
404: 未找到页面(当 readyState 等于 4 且状态为 200 时,表示响应已就绪)
为获得服务器的响应使用的属性:
- responseText :获得字符串形式的响应数据,用于来自服务器的响应并非 XML 。
//string类型- responseXML:获得 XML 形式的响应数据。 //object类型
请注意:字符串类型的json数据转化为对象型json :
JSON.parse(http.response);
对象json转化为string json :
JSON.stringify(data);
5)界面的渲染
判断状态,获取最终读取完成响应
4) 原生ajax的封装:
//原生ajax的封装
function method(mtd,url,data,async,comback){
// comback 异步执行的回调函数
//对象的创建
var http=new XMLHttpRequest();
// 判断请求方式(建立服务器连接 发送请求)
if(mtd=="get"){
if(data){
url+="?";
url+=data;
}
http.open(mtd,url,async);
http.send();
}
else{
http.open(mtd,url,async);
// 判断是否有data
if(data){
http.send(data);
}
else{
http.send();
}
}
// 响应 onreadystatechange属性
http.onreadystatechange=function () {
// 判断状态
if(http.readyState=="4"&&http.status=="200"){
comback(http.response);
}
}
}
// 原生js 尽量不要同步 因为原生js是单线程的 会造成线程堵死
//url:自己创建的josn文件
method("get","data/list.json",null,true,function (result) {
console.log(JSON.parse(result));
});
3.Ajax的跨域原理
- 首先,为什么会出现跨域问题呢?
因为浏览器考虑一定的安全因素,增加了同源策略,只要违背同源策略的操作都会被禁止,即浏览器报错。此时就出现了跨域问题。 - 什么情况会出现跨域呢?
(1) http://www.maodou.com/mao/list.html 1和2 协议不一致
(2) https://www.maodou.com/mao/list.html
(3)http://www.maodou.com:8080/mao/list.html 1和3端口不一致
(4)http://www.dou.com/mao/list.html 1和4 域名不一致
协议不一致, 端口不一致,域名不一致都会导致跨域 。 - 跨域如何解决?
1) CORS跨域
-
CORS跨域,主要是靠服务端进行配置。而且是对各种请求方法、各种数据请求类型都是完美支持的。
-
CORS跨域需要浏览器和服务器同时支持。
-
整个CORS通信过程,都是浏览器自动完成,不需要用户参与。对于开发者来说,CORS通信与同源的AJAX通信没有差别,代码完全一样。浏览器一旦发现AJAX请求跨源,就会自动添加一些附加的头信息,有时还会多出一次附加的请求,但用户不会有感觉。
因此,实现CORS通信的关键是服务器。只要服务器实现了CORS接口,就可以跨源通信。
2) josnp跨域
- 在原生js里面叫src跨域。
- jsonp跨域原理:
在前端上使用src进行跨域,script这种标签会发起一个get请求,并且这个请求是不受同源策略限制的,如果有我们将后台api以script标签来发送变成如下请求方式,那么不会有跨域问题了。可以在需要时动态创建script标签,使用完清除,避免内存的冗余和页面的不美观。
并且在接口上传入要执行的回调函数 (后台一定要处理回调函数,这样前台的函数才有响应)
//下面是jsonp跨域的回调函数
function getdata(result) {
console.log(result);
}
<script src="http://localhost:8080/jsonp.php?index=1&cb=getdata"></script>