Ajax是技术还是框架?走进Ajax的前世今生

2023-09-06 0 201

写在后面

看爸爸妈妈写诗把AJAX当架构表述,和Promiseaxios放在一同讲总的来说却是很多局限性的这儿撷取一则沙朗通的讲义期望透过责任编辑爸爸妈妈们能对AJAX有明晰的表述昌明文本主要就为写作《Ajax基础教程》重新整理讲义

天数下定决心你会在心灵中碰到谁,你的心下定决心你想谁再次出现在你的心灵里,而你的犯罪行为下定决心最终谁能遗留下————《梭罗》

Web百科辞典

Berners-lee发明者了 国际标准通用型词汇(Standard Generalized Markup language,SGML) 的两个开集称作 LZ77记号词汇(HyperText Markup Language,HTML)

建立了称作 LZ77数据传输协定(HyperText Transfer Protocol,HTTP) 的单纯协定,

还发明者了第二个Web应用程序,叫作WorldWideWeb

Web产业发展解释器:

起初的Web页面都是静态的,为了让Web动态,引入的 CGI(Common Gateway Interfase,通用型网关接口), 使用CGI在服务器端建立程序,CGI脚本能使用多种词汇编写。

对CGI的改进有了 appletapplet允许开发人员编写可嵌入在Web页面的小应用程序,在应用程序的Java虚拟机(JVM)中运行applet

后来Netscape建立了一种动态脚本词汇,最终命名为 JavaScript,设计JavaScript是为了让不太熟悉Java和Web的开发人员能够更轻松的开发applet,Microsoft也推出了 VBScript

Java再次出现一年以后,sun引入 Servlet 即Java代码不用像apple那样的客户端应用程序中运行了,把它控制在两个应用服务器上运行,但是servlet设计界面很不方便,需要以打印流来输出,

为了将表示与业务逻辑分离,再次出现了 JSP(JavaScript Pages),Microsoft也推出了ASP。用来设计页面

并不是只有MicrosoftSun在努力寻找办法来解决动态Web页面问题。1996年夏天,FutureWave发布了两个名叫 FutureSplash Animator的产品。这个产品起源于两个基于Java的动画播放器, FutureWave很快被Macromedia兼并,Macromedia则将这个产品改名为Flash

Flash:利用flash能发布高度交互的应用。

MicrosoftNetscape发布其各自应用程序的第4版时,Web开发人员有了两个新的选择:动态HTML (Dynamic HTML, DHTML)。DHTML 不是 W3C 国际标准。

DHTML革命动态HTML(Dynamic HTML,DHTML) 结合HTML 层叠式样式表(Cascading Style sheets,CSS),JavaScript,DOM

Microsoft对于交互式应用有一定了解,而且对于这种国际标准请求/响应模式的限制一直都不满意,因此提出了远程脚本 ,但是同步页面刷新问题一直没有很好的解决方案。

Ajax不只是两个特定的控制技术,更应算是一种技巧,JavaScript是其主要就组件。

Ajax相关的术语就是XMLHttpRequest 对象(XHR),它早在IE5 (于1999年春天发布)中就已经再次出现了,是作为Active X控件露面的。不过,最近再次出现的新现象是应用程序的支持。原先,XHR对象只在IE中得到支持(因此限制了它的使用)

但是从Mozilla 1.0Safari 1.2开始,对XHR对象的支持开始普及。这个很少使用的对象和相关的基本概念甚至已经再次出现在W3C国际标准中:DOM Level 3加载和保存规约(DOM Level 3 Load and Save Specification)。特别是随着Google Maps. Google Suggest, Gmail, Flickr, NetflixA9等应用变得越来越多手可热,XHR也已经成为事实上的国际标准。

是谁发明者了Ajax?

2005年2月, Adaptive PathJesse James Garrett最早创造了这个词。在他的文章Ajax:A New Approach to Web Applications (Ajax: Web应用的一种新方法)中,Garrett讨论了如何消除胖客户(或桌面)应用与瘦客户(或Web)应用之间的界限。

当然,当Google GoogleLabs发布Google MapsGoogle Suggest时,这个控制技术才真正为人所认识,而且此前已经有许多这方面的文章了。

但确实是Garrett最早提出了这个好名字,否则我们就得啰啰嗉嗉地说上大堆:异步(Asynchronous)、 XMLHttpRequest、 JavaScript. CSS、DOM 等等

尽管原来把Ajax认为是Asynchronous JavaScript + XML (异步 JavaScript + XML)的缩写,但如今,这个词的覆盖面有所扩展,把允许应用程序与服务器通信而无需刷新当前页面的控制技术都涵盖在内

所以如何表述AJAX:即AJAX是基于 XMLHttprequest对象(XHR),消除胖客户(桌面应用)与瘦客户(Web应用)应用之间的界线。透过异步通信,允许应用程序与服务器通信而无需刷新当前页面的控制技术。

使用XMLHTTPrequest对象

使用XMLHttpRequest对象发送请求和处理响应之前,必须先写JavaScript建立两个XMLHttpRequest对象。

由于XMLHttpRequest并不是两个W3C国际标准,能采用多种方法建立,Internet Explorer把XMLHttpRequest实现为两个ActiveXObject对象,其他应用程序把它实现为本地的Javascript对象。

varxmlHttpfunction createXMLHttpRequest(){ if(window.ActiveXObject){ //IE应用程序 xmlHttp = new ActiveXObject(“Microsoft.XMLHTTP”); }else if(window.XMLHttpRequest){ //其他应用程序 xmlHttp = new XMLHttprequest(); } }

方法和属性

方法属性

描述

void abort()

停止当前请求

String getAllresponseHeadders()

以字符串把HTTP请求的所有响应首部作为键值对返回

String getResponseheader(“”)

返回指定首部字段的字符串

void open(string method,string url,boolean asynch,string username,string password)

建立对服务器的调用,初始化请求的纯脚本方法,第三个参数表示调用为异步(true)却是同步(false),默认异步

void send(content)

向服务器发出请求,如果声明异步,立即返回,否则等待接收到响应为之,可选参数能是DOM对象的实例,输入流,或字符串,传入这个方法的文本会作为请求的一部分发送

void setRequestHeader(string header,string value)

把指定的首部设置为所提供的值,在设置任何首部前必须先调用open()后才可调用

属性

描述

onreaddystatechange

每个状态改变时都会触发这个事件处理器,通常会调用事件处理函数

readystate

请求的状态,0(未初始化),1(正在加载),2(已加载),3(交互中),4(完成)

responseText

返回服务器的响应,表示为两个字符串

responseXML

返回服务器的响应,表示为xml,能解析为DOM对象

status

服务器的HTTP状态码

statusText

服务器状态码对应原因短语

交互实例

<input type = “text” id = “email” name =“email” onblur = “validateEmail()”> <script type = “text/Javascript”> var xmlHttp; var email = document.getElementById(“email”); var url = “validata?emali = “+escape(email.value); //get方法数据作为URl一部分发送,地址数据?隔开。数据以键值对方式显示&隔开。 if(window.ActiveXObject){ //IE应用程序 xmlHttp = new ActiveXObject(“Microsoft.XMLHTTP”); }else if(window.XMLHttpRequest){//其他应用程序 xmlHttp = new XMLHttprequest(); } xmlHttp.open(“GET”,url); xmlHttp.onreadystatechange = callback; xmlHttp.send(null); function callback(){ if(xmlHttp.readyState ==4 ){ if(xmlHttp.status ==200){ //do something interesting here} } } }</script>

如何发送单纯请求

使用XMLHttprequest对象发送请求的基本步骤:

得到XMLHttpRequest对象的实例引用,能建立新实例,也能访问已有的实例变量。把对象的onreadystatechange属性设置为指向事件函数的指针。指定请求的属性,open()方法将请求发送给服务器,send()方法,如果没有数据作为请求体的一部分发送,使用null;<!DOCTYPE html PUBLIC “-//W3C//DTD XHTML 1.0 Transitional//EN” “http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd”> <html xmlns=“http://www.w3.org/1999/xhtml”> <head> <meta http-equiv=“Content-Type” content=“text/html; charset=utf-8” /> <title>simple XMLHttpRequest</title> <script type=“text/Javascript”> var xmlHttp; function createXMlHttprequest(){ if(window.ActiveXObject){ xmlHttp = new ActiveObject(“Microsoft.XMLHttp”); } else if(window.XMLHttpRequest){ xmlHttp = newXMLHttpRequest(); } }function srartRequest(){ createXMLHttprequest(); xmlHttp.onreadystatechange = handleStateChange; xmlHttp.open(“GET”,“simpleResponse.xml”,true); xmlHttp.send(null); }function handleStateChange(){ if(xmlHttp.readyState ==4){ if(xmlHttp.status == 200){ alert(“The servlet replied with:”+xmlHttp.responseYext); } } } </script> </head> <body> <form action=“#”> <input type=“button” value=“Start Basic Asynchronous Request” onclick=“startRequest()” /> </form> </body> </html>

与服务器通信

处理服务器响应:XMLHttpRequest对象提供responseText将响应提供为两个串responseXML将响应提供为一个XML对象。

将响应解析为纯文责任编辑件。

document.getElementBiId(“idName”).innerHTML = xmlHttp.responseText; //以字符串的方式返回响应的文本,并写入到IDName中。

将响应 解析为XML文件:

要使服务器按XML格式响应数据,需要Content_Type首部为text/xml,当为纯文本时:text/piain

用于处理XML文档的DOM元素的属性方法

属性方法名

描述

childNodes

返回文档元素所有子元素的数组

firstChild

返回当前元素的第二个下级子元素

lastChild

返回当前元素的最终两个子元素

nextsibling

返回紧跟在当前元素后面的元素

nodeValue

返回制定元素值得读/写属性

parentNode

返回元素的父节点

previousSibling

返回紧邻当前元素之前的元素

getElementById(document)

hasChildNodes()

返回当前元素中指定记号名的子元素的数据

getAttirbut(name)

返回元素的属性值,属性值由name指定

varXMLDoc= xmlHttp.responseXML;//响应以XML格式返回。

发送请求参数:

post方法将参数放在请求体中发送,get方法将讲参数追加到URL中发送。当使用post方法时,需要调用XMLHttpRequest对象的send()方法时发送字符串。function doRequestUsingGET(){ createXMLHttpRequest(); var queryString = “请求地址?”; queryString = queryString + createQueryString() +“&timeStamp=”+new Date().getTime(); xmlHttp.onreadystatechange = handleStateChange; xmlHttp.open(“GET”,“queryString”,true); xmlHttp.send(null); } function doRequestUsingPOST(){ carterXMLHttpRequest(); var url = “请求地址?timeStamp=”+new Date().getTime(); var queryString = createQueryString(); xmlHttp.open(“post”,url,true); xmlHttp.onreadystatechange = handleStateChange;//触发判断状态方法。xmlHttp.setRequestHeader(“Content-type”“application/x-www-form-urlencoded;”);//确保服务器中知道请求体中有请求参数。xmlHttp.send(quweyString);调用send()方法将查询串作为参数传递。 }

为什么要把天数戳追加到目标URl:有时应用程序会把多个XMLHttpRequest请求的结果缓存在同两个URL,如果对每个请求的响应不同,就会带来好的结果,把当前天数戳追加到YR来的最终,就能保证URL的唯一性

请求参数作为XML发送

将请求参数以xml的格式作为请求体的一部分发送到服务器,与POST请求中将查询串作为请求体的一部分进行发送异曲同工,不同的是由XMLHttpRequest对象的send方法发送xml串。

结束记号中斜线后面的反斜线:xml = xml + “</pest>”;SGML规约中提供两个技巧,能识别出script元素中的结束记号,但其他文本不能识别,使用反斜线能避免把串解析为记号,根据严格的XHTML国际标准,应该使用反斜线。

entBuilderFactory对象方法转换为DOM对象,然后透过NodeList 对象解析获得数据。

protected voiddoPost(HttpServletRequest request, HttpServletResponse response) throws ServletException,IOException { doGet(request, response);String xml = readXMLFromRequestBody(request); Document xmlDoc = null; xmlDoc = DocumentBuilderFactory.newInstance().newDocumentBuilder() .parse(new ByteArrayInputStream(xml.getBytes())); }catch(ParserConfigurationException e) { e.printStackTrace(); }catch(SAXException e) { e.printStackTrace(); } NodeList selectedPetTypes = xmlDoc.getElementsByTagName(“type”); String type =null; String responseText = “Selectsd Pets”; for(int i =0;i< selectedPetTypes.getLength();i++) { type= selectedPetTypes.item(i).getFirstChild().getNodeValue(); responseText = responseText+” “+type; } response.setContentType(“text/xml”); response.getWriter().print(responseText); System.out.println(responseText); }private StringreadXMLFromRequestBody(HttpServletRequest request) { StringBuffer xml =new StringBuffer();//实例化两个字符缓存区对象; String line = null; try{ BufferedReader reader = request.getReader();//请求字符缓存输入流,从字符输入流中读取文件,一次读取一行。 while((line =reader.readLine())!=null) {//循环读取两个文本行 xml.append(line); } }catch( Exception e) { e.printStackTrace(); } returnxml.toString(); }

实现基本的Ajax控制技术

完成局部验证

function validate(){ createXMLHttpRequest(); var date = document.getElementById(“birthDate”); var url = “ValidationServlet?birthDate=” + escape(date.value); xmlHttp.open(“GET”,url,true); xmlHttp.onreadystatechange = callback; xmlHttp.send(null); } function callback(){ if(xmlHttp.readyState ==4){ if(xmlHttp.status == 200){ varmes = xmlHttp.responseXML.getElementsByTagName(“message”)[0].firstChild.data; var val = xmlHttp.responseXML.getElementsByTagName(“passed”)[0].firstChild.data; setMessage(mes,val); } } } function setMessage(message,isvalid){ var messageArea = document.getElementById(“dateMessage”); var fontColor = “red”; if(isvalid == “true”){ fontColor =“green”; } messageArea.innerHTML = “<font color = “+fontColor+“>”+message+“</font>”; } protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { PrintWriter out= response.getWriter(); boolean passed = validateDate(request.getParameter(“birthDate”)); response.setContentType(“text/xml;charset=UTF-8”); response.setHeader(“Cache-Control”, “no-cache”); String message = “You have entered an invalid date”; if(passed){ message =“You have entered an invalid date”; } out.println(“<response>”); out.println(“<passed>”+Boolean.toString(passed)+“</passed>”); out.println(“<message>”+message+“</message>”); out.println(“</response>”); out.close(); } private boolean validateDate(String date) {//判断字符串符合指定的日期格式boolean isValid=true; if(date!=null) { SimpleDateFormat formatter = new SimpleDateFormat(“MM/dd/YYYY”); try { formatter.parse(date); //解析字符串的文本,生成 Date, }catch(ParseException e) { e.printStackTrace(); isValid=false; } }else { isValid=false; } return isValid; } 读取响应首部当服务器对HEAD请求做出响应时,它只发送响应首部忽略响应文本。function handleStateChange(){ if(xmlHttp.readyState == 4){ if(requestType ==“allResponseHeaders”){ getAllRequestHeaders(); }else if(requestType ==“lastModified”){ getLastModified(); }else if(requestType ==“isResourceAvailable”){ getIsResourceAvailable(); } } }function getAllRequestHeaders(){ alert(xmlHttp.getAllResponseHeaders()); }function getLastModified(){ alert(“Last Modified:”+xmlHttp.getResponseHeader(“Last-Modified”)); } function getIsResourceAvailable(){ if(xmlHttp.status ==200){ alert(“Successful^_^”); }else if(xmlHttp.status == 404){ alert(“Resource is unavailable”); }else{ alert(“Unexpected response status :”+xmlHttp.status); }

Ajax在开发中有很多的应用场景,比如下面的一些场景

动态加载列表框建立自动刷新页面:建立工具提示:动态更新Web页面

jQuery对Ajax的实现:

透过jQuery Ajax方法,能够使数据HTTP GETHTTP POST请求从远程服务器上请求文本,HTML,XML,JSON,数据,同时能够把这些外部数据载入网页的被选元素中。

ajax()方法:jQuery的底层实现,$.ajax()方法返回其建立的XMLHttpReuqst对象,大多数无需操作该对象,特殊情况手动终止。只有两个参数:参数为key/value对象,$.ajax(options)。参数可选。

$.ajax({ url:/ExampleServlet, type:post, dataType:json, success:function(data){alert(成功!);alert(data);}, error:function(){alert(内部错误);} }); $.ajax({ async:false; type:post; url:“example.jsp”, data:“name=Jfn&location=boss” }).success(function(msg){alert(“Data Saved:”+msg) }).error(function(xmlHttpRequest,statusText,errorThrown){ alert(“You form submission failed.\n\n” +“XMLHttpRequest:” +JSON.stringify(xmlHttpRequest) +“,\nStatusText:”+statusText +“,\nErroeThrown:”+errorThrown); }); load()方法从服务器加载数据,并把返回的数据放入被选元素:url:必须参数,指定需要加载的URLdata:可选,规定与请求一同发送的查询字符串键/值对集合。callback:可选,请求成功完成的回调函数。get(),post():用于透过HTTP GET或POST请求从服务器请求数据,getJSON():透过HTTP GET 请求载入JSON数据,并尝试将其转为对应的JavaScript对象。

Promise 对象实现的 Ajax 操作

function ajax(URL) { return new Promise(function (resolve, reject) { var req = new XMLHttpRequest(); req.open(GET, URL, true); req.onload =function () { if (req.status === 200) { resolve(req.responseText); } else { reject(new Error(req.statusText)); } }; req.onerror = function () { reject(new Error(req.statusText)); }; req.send(); }); }var URL = “/try/ajax/testpromise.php”; ajax(URL).then(function onFulfilled(value){ document.write(文本是: + value); }).catch(function onRejected(error){ document.write(错误: + error); });

关于AJAX和爸爸妈妈们撷取到这儿

相关文章

发表评论
暂无评论
官方客服团队

为您解决烦忧 - 24小时在线 专业服务