《javascript高级程序设计》笔记(二十一)
Ajax与Comet
Ajax能够向服务器请求额外的数据而无需卸载页面。
Ajax技术的核心是XMLHttpRequest对象(简称XHR)。可以使用XHR对象取得新数据,然后通过DOM将新数据插入到页面,Ajax通信与数据格式无关 ,不一定是XML数据。
(一)XMLHttpRequest对象
IE 7+ Firefox Opera Chorme Safari都支持原生的XHR对象,使用XMLHttpRequest构造函数 var xhr = new XMLHttpRequest();
如果要支持IE的早起版本
function createXHR(){ if (typeof XMLHttpRequest != "undefined"){ return new XMLHttpRequest(); } else if (typeof ActiveXObject != "undefined"){ if (typeof arguments.callee.activeXString != "string"){ var versions = ["MSXML2.XMLHttp.6.0", "MSXML2.XMLHttp.3.0", "MSXML2.XMLHttp"], i, len; for (i=0,len=versions.length; i < len; i++){ try { new ActiveXObject(versions[i]); arguments.callee.activeXString = versions[i]; break; } catch (ex){ //skip } } } return new ActiveXObject(arguments.callee.activeXString); } else { throw new Error("No XHR object available."); } }
1.XHR的用法
使用XHR对象时,要调用的第一个方法是open(),接收3个参数: 要发送的请求类型(get、post等)、 请求的URL 和 表示是否异步发送请求的布尔值,如:
xhr.open("get","example.php",false)
URL相当于执行代码的当前页面,调用open()方法不会真正发送请求,只是启动一个请求以备发送。
发送特定请求,要调用send()方法: xhr.send(null)。如果不需要通过请求主体发送数据,必须传入null,调用send()之后,请求会被分派到服务器。
XHR对象的属性:
responseText:响应本体被返回的文本
responseXML:如果响应的内容类型是"text/xml"或"application/xml",这个属性将保存包含相应数据的HTTP状态。
status:响应的HTTP状态。
statusText:HTTP状态的说明。
一般可以将HTTP状态代码为200作为响应成功的标志。状态代码为304表示请求的资源没有被修改,可以直接使用浏览器缓存的版本。
响应主体的内容保存到responseText属性,对非XML数据,responseXML属性的值为0。
readyState属性表示请求/响应过程的当前活动阶段:
0:为初始化,未调用open()方法。
1:启动。已调用open()方法,但未调用send()方法。
2:发送。已调用send()方法,但未接收到响应。
3:接收。已接收到部分响应数据
4:完成。已接收到全部响应数据,可以在客户端使用。
只要readyState的值变化,就会触发readystatechange事件,可以用它来检测readyState的值。一般只检测4。必须在调用open()之前制定onreadystatechange事件处理程序。
xhr.onreadystatechange = function(event){ //请求/相应过程的当前活动阶段 if (xhr.readyState == 4){ //HTTP状态代码 if ((xhr.status >= 200 && xhr.status < 300) || xhr.status == 304){ alert(xhr.responseText); } else { alert("Request was unsuccessful: " + xhr.status); } } }; xhr.open("get", "example.txt", true); xhr.send(null);
接收到响应之前可以调用abort()方法取消异步请求。
2.HTTP头部信息
setRequestHeader()方法可以设置自定义的请求头部信息,接收两个参数:头部字段的名称和头部字段的值。必须在调用open()之后切调用send()之前调用它。
3.GET请求
GET是最常见的请求,最常用于向服务器查询信息。必要时可以将查询字符串添加到URL末尾。
查询字符串中每个参数的名称和值都必须使用encodeURIComponent()进行编码,才能放到URL的末尾。而且所有名-值对必须由&分隔。
xhr.open("get","example.php?name1=value1&name2=value2",true );
4.POST请求
通常用于向服务器发送应该保存的数据。
第一步:在open()方法第一个参数传入"post"
第二步:向send()方法传入某些数据。
使用XHR模仿表单提交:将Context-Type头部信息设置为application/x-www-form-unlencoded,也就是表单提交时的内容类型,然后以适当的格式创建一个字符串。
(二)XMLHttpRequest 2 级
1.FormData
FormData类型:序列化表单、创建于表单格式相同的数据。
var data = new FormData(); data.append("name", "Nico")
append()方法接收两个参数:键和值。通过向FormData构造函数传入表单元素,可以用表单元素的数据填入键和值。
2.超时设定
IE8+中 timeout属性表示请求在等待相应多少毫秒后就终止。如果在规定时间浏览器没有接受相应,就会触发timeout事件,进而调用ontimeout事件处理程序。
xhr.open("get", "timeout.php", true); xhr.timeout = 1000; xhr.ontimeout = function(){ alert("Request did not return in a second."); }; xhr.send(null);
3.overrideMimeType()方法
用于重写XHR相应的MIME类型,因为返回响应的MIME类型决定了XHR对象如何处理它,所以能处重写服务器返回的MIME类型很有用。
Firefox、Safari 4+、Opera 10.5、Chrome
(三)进度事件
定义了与客户端服务器通信有关的事件,最早只针对XHR操作,目前被其他API借鉴。
进度事件:loadstart progress error abort load loaded
每个请求都是从触发loadstart事件开始,接下来是一或多个progress事件,然后触发error、abort或load事件的一个,最后触发loaded。
Firefox 3.5+ Safari 4+ Chrome IE8只支持load
1.load事件
相应接收完毕后触发load事件,其target属性指向XHR对象实例,可以访问到XHR对象的所有方法和属性。只要浏览器接收到服务器相应,都会触发load事件,因此要检测status属性。
2.progress事件
在浏览器接收新数据期间周期性触发。onprogress事件处理程序接收一个event对象,其target属性是XHR对象,包含三个额外属性:lengthComputable、position、和totalSize。
lengthComputable:进度信息是否可用的布尔值。
position:已经接收的字节数。
totalSize:根据Content-Length响应头部确定的预期字节数。
必须 在调用open方法之前添加onprogress事件处理程序。
(四)跨源资源共享
CORS定义了再必须访问跨源资源时浏览器与服务器应该如何沟通。
CORS的思想是使用自定义的HTTP头部让浏览器与服务器沟通,从而决定请求或响应是否成功。
如果服务器任务请求可以接受,就在Access-Control-Allow-Origin头部回发相同的源信息。
1.IE对CORS的实现
XDR对象的使用方法与XHR类似,创建一个XDomainRequest的实例,调用open()方法,再调用send()方法。只接受两个参数:请求的类型和URL。
所有XDR请求都是异步执行,请求返还后触发load事件,数据保存在responseText属性。
2.其他浏览器对CORS的实现
Firefox 3.5+ Safari4+ Opera XMLHttpRequest对象实现对CORS的原生支持。在请求另一个域的资源时用XHR对象并在open()方法传入绝对URL。通过跨域XHR对象可以访问status和statusText属性,还支持同步请求。但有一些限制。
3.Preflighted Requests
Preflighted Requests:透明服务器验证机制,用来支持开发人员使用自定义的头部、GET或POST之外的方法和不同类型的主体内容。
Firefox 3.5+ Safari 4+ Chrome IE10及之前不支持
4.带凭据的请求
通过将withCredentials属性设置为true可以指定某个请求应该发送凭据。
Firefox 3.5+ Safari 4+ Chrome IE10及之前不支持
5.跨浏览器的CORS
检测XHR是否支持CORS的最简单方式是检查是否存在withCredentials属性,再结合检测XDomainRequest对象是否存在。
(五)其他跨域技术
1.图像Ping
动态创建图像,使用它们的onload和onerror事件处理程序确定是否接收了相应。
最常用于跟踪用户点击页面或动态广告曝光次数。缺点:只能发送GET请求,无法访问服务器的相应文本。
2.JSONP
被包含在函数调用中的JSON,由两部分组成:回调函数和数据。回调函数是当响应到来时应该在页面中调用的函数。
3.Comet
是一种服务器向页面推送数据的技术,能让信息近乎实时地被推送到页面。
实现方式:长轮询和流。
轮询的优势是所有浏览器都支持,使用XHR对象和setTimeout()就能实现。
HTTP流:浏览器向服务器发送一个请求,服务器保持链接打开,周期性地向浏览器发送数据。所有服务器端语言支持打印到输出缓存然后更新。
Firefox Safari Opera Chrome 通过监听readystatechange事件及检测readySatate的值是否为3就能利用XHR对象实现HTTP流。
4.服务器发送事件
SSE是围绕只读Comet交换推出的API或者模式。SSE API用于创建到服务器的单向链接,武器通过这个连接可以发生任务数量的数据。服务器相应的MIME类型必须是text/event-stream,而且是料理的javascript API能解析格式输出。
Firefox 6+ Safari 5+ Opera11+ Chrome
先要创建新的EventSource对象,并传送一个入口点。传入的URL要与创建对象的页面同源。
5.Web Sockets
在一个独特的持久链接上提供双工、双向通信。标准的HTTP服务器无法实现Web Sockets,只有支持这种协议的专门服务器才能工作。
使用自定义协议而非HTTP协议的好处是能在客户端和服务器之间发送非常少量的数据。确定是制定协议的时间比javascript API长。
Firefox 6+ Safari 5+ Chrome
①Web Sockets API
要创建Web Sockets,先实例一个Web Sockets对象并传入要链接的URL(绝对)。
②发送和接收数据
要向浏览器发送数据,使用send()方法并传入任意字符串。Web Sockets只能通过连接发送纯文本数据,对于复杂的数据结构,在通过连接发送前要序列化。服务器向客户端发送数据时Web Sockets对象触发message事件。
③额外事件
open error close
6.SSE 与 Web Sockets
是否有自由度建立和维护Web Sockets服务器
需不要要双向通信。
(六)安全
为确保通过XHR访问的URL安全,通行的做法是验证发送请求者是否有权访问相应的资源。
郑重声明:本站内容如果来自互联网及其他传播媒体,其版权均属原媒体及文章作者所有。转载目的在于传递更多信息及用于网络分享,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。