AJAX缘由

  再次谈起这个话题,我深深的记得就在前几年,AJAX被炒的如火如荼,就好像不懂AJAX,就不会Web开发一样。要理解AJAX为什么会出现,就要先了解Web开发面临的问题。

  我们先来回忆一下Web页面的申请过程,这个咱们在第一篇中就介绍过了:Web页面开发就是在无连接和无状态的HTTP协议上管理页面的状态。每次申请页面的时候,服务器都会返回完整的HTML文本(当然还有其他的文本文件),浏览器就负责解析这个文本并在浏览器中显示。

  在这个过程中,不管当前页面的内容是不是都变化了,服务器都会重新给浏览器重发一份,这个操作对于原本就比较脆弱的网络来说,实在是比较耗时,比较低效,虽然时至今日,这种方式还是很多网站的工作模式,但是还有有很多玩家开始思考如何去优化这个过程。在编程语言的发展过程中,异步是解决用户响应问题的不二法宝,所以异步的申请与局部更新的方案就产生了,这个就是AJAX。

问题的本质 - 数据交互技术

  在详细总结Ajax的实践之前,我们先来深入的分析一下问题的核心。

  任何的软件程序基本上都可以分为界面(UI),逻辑,数据3个部分,Web程序也不例外,在Web程序中,JavaScript承担了完成逻辑功能的任务,也就是和后台数据打交道的任务,不管是用户输入,还是获取数据,最终都表现为使用JavaScript完成与服务器的交互,这样的操作说白了就是前端界面与后端数据之间的数据交互问题。

  数据交互的方式基本上也就是两种方式:同步和异步,前者会等待数据操作结束后继续执行下面的程序,后者不会等待数据操作完成,而是先执行下面的程序,在数据操作完成后再通过回调函数完成需要执行的一些工作。

  而在执行数据交互的过程中,前后端也可以采取不同的联系方式:持续连接和按需连接,前者前后端一直保持连接,后者前后端只在需要的时候连接一下。

  对于传统的桌面程序,由于前端与后端共存与一台机器上,所以访问比较方便,通常采用持续连接和同步访问的方式,而对于一些大数据量的操作才采用异步访问的方式(提高界面的可响应性)。

  对于Web程序而言,由于前后端通常不在一台机器上,而且最初网络环境并不是太好,所以最初采用的是按需连接(申请页面的时候建立连接)和同步的方式(数据接收完毕后更新整个页面)。但是随着Web程序需求(功能性和非功能性需求)的不断提高,网络软硬件技术的不断发展,数据访问方式就理所当然的出现了异步的方式和局部更新,这就是AJAX技术。而随着HTML5技术的逐渐发展,持续连接也成为了一种可能,这就是WebSocket技术,这个在前面的HTML5系列文章中已经总结过了。

  从上面的数据交互技术发展的核心脉络中我们可以更清楚的理解AJAX所处的历史地位和积极意义,下面我们就详细的看一下AJAX技术。

AJAX本质

AJAX = Asynchronous JavaScript and XML (异步的 JavaScript 和 XML)

  AJAX就是在客户端申请页面时,在不重新加载整个页面的情况下,只对网页的局部进行更新的技术。使用了AJAX后,浏览器与服务器只会进行少量数据交换,这样页面的执行效率就会大幅提升。

  AJAX实现的核心有两点:

1. 异步申请数据

2. 响应数据,更新局部页面

  更新页面比较简单,前面DOM部分已经总结过常见的CRUD(创建,检索,更新,删除)操作了。那个剩下的的就是如何异步的申请和响应服务端的数据了,这个是通过AJAX的核心对象XMLHttpRequest来完成的。

  总的来说,XMLHttpRequest对象很简单,下面来看个简单的例子:

<html>
<head>
<script type="text/javascript">
var xmlhttp;
function loadXMLDoc(url)
{
xmlhttp = null;
// 1. 创建XMLHttpRequest对象
if (window.XMLHttpRequest){
// 适用于浏览器IE7, Firefox, Opera, Chrome等
xmlhttp = new XMLHttpRequest();
}
else if (window.ActiveXObject) {
// 适用于浏览器 IE6, IE5
xmlhttp = new ActiveXObject("Microsoft.XMLHTTP");
} if (xmlhttp != null) {
// 2. 挂接响应函数/回调函数
xmlhttp.onreadystatechange = stateChange;
// 3. 设置申请方法
xmlhttp.open("GET",url,true);
// 4. 发送申请
xmlhttp.send();
} else {
alert("你的浏览器不支持XMLHTTP");
}
}
function stateChange() {
// readyState = 4(loaded)并且status = 200(OK)代表申请数据成功
if (xmlhttp.readyState == 4 && xmlhttp.status == 200) {
// 获取响应的状态,返回的数据(XML格式)
document.getElementById('A1').innerHTML = xmlhttp.status;
document.getElementById('A2').innerHTML = xmlhttp.statusText;
document.getElementById('A3').innerHTML = xmlhttp.responseText;
} else {
alert("获取XML时出错:" + xmlhttp.statusText);
}
}
</script>
</head>
<body>
<h2>使用HttpRequest对象</h2>
<p><b>状态:</b>
<span id="A1"></span>
</p>
<p><b>状态文本:</b>
<span id="A2"></span>
</p>
<p><b>返回的数据:</b>
<br /><span id="A3"></span>
</p>
<button onclick="loadXMLDoc('/example/xmle/note.xml')">获取XML</button>
</body>
</html>

  直接运行这个例子是不行的,需要自己配置个服务器,这个例子来源于W3C,地址:http://www.w3school.com.cn/tiy/t.asp?f=ajax_httprequest_js。我只不过是加了一下注释,下面就是例子的一些说明。

1. 创建XMLHttpRequest对象

  兼容性问题注意一下即可。

2. 向服务器发送请求

  申请时我们使用了XMLHttpRequest对象的open()和send()方法。

  open方法的第一个参数指定了请求的方式是GET或者是POST。与POST相比,GET更简单也更快,并且在大部分情况下都能用。

  然而,在以下情况中,则需要使用POST请求:

1).无法使用缓存文件(更新服务器上的文件或数据库)

2).向服务器发送大量数据(POST没有数据尺寸限制)

3).发送包含未知字符的用户输入时,POST比GET更稳定也更可靠(其实还是考虑数据尺寸的限制问题)

  其实说白了POST主要用于携带数据更新服务器然后返回。

  open方法的第二个参数是申请的数据url,这个没什么好说的。

  open方法的第三个参数是指定申请时异步(true)还是同步(false),这个其实不用考虑,估计没什么人使用同步方式。如果有些兄弟想试验一下同步的方式的话,也可以,不过响应的函数就不用挂到onreadystatechange上了,而是直接在send方法后面写上更新HTML的代码即可。

  send方法发送请求,这个方法可以携带一个字符串作为参数,这个参数存储了发送给服务器的数据,简单的申请都不用给服务器发送数据,所以用法都很简单:

xmlhttp.open("POST","demo_post.asp",true);
xmlhttp.send();

  如果要像HTML表单那样POST数据的话,一般还要设置HTTP头,所以复杂一点的POST申请的代码大概像是这样:

xmlhttp.open("POST","ajax_test.asp",true);
xmlhttp.setRequestHeader("Content-type","application/x-www-form-urlencoded");
xmlhttp.send("fname=Bill&lname=Gates");

  这其实是更新服务器数据的操作。

3. 响应服务器端的数据

  这个响应函数对于同步的申请来说很简单,直接把代码写到send方法的后面就可以了。异步申请的话要挂接到onreadystatechange事件上。

  在回调函数中,我们首先需要判断服务器的处理状态,这就是通过判断例子中的readyState和status来实现的。只有readyState等于4并且status等于200的时候才表明服务器正确的返回了申请的数据,这个时候我们通过responseText或者responseXML获取到字符串格式或者XML格式的数据,然后解析处理就行了。

再论JSON与XML

  在AJAX中,名字中的异步XML确实是相当惊艳,在回调函数中,直接可以使用responseXML访问XML格式的内容。不过鉴于在JavaScript中解析XML实在有点不是太方便(感兴趣的同学百度一把就知道了),至少是比解析JSON要麻烦一点,所以就像在前面我们讨论的那样:WEB开发中,JSON是王道。虽然XML是AJAX内置的一种方式,而且现实世界中确实也存在很多构建在XML或者SOAP(一种轻量的、简单的、基于XML的协议)之上的服务方式,但是除了这些必须要使用XML的服务外,使用JSON确实能带来不少的方便。

REST思想

  每次看到介绍AJAX的文章,我总能在第一时间想到REST架构。

  REST是英文Representational State Transfer的缩写,中文翻译为“表述性状态转移”。这个又是当前炙手可热的一个概念。这种思想的核心就是使用单一的URI标示符去标识服务器上的任何的资源,客户端使用URI去对资源进行CRUD操作。这种想法与AJAX的做法配合起来(基于REST的Web服务及基于 Ajax的客户端)可以说是十分融洽。关于REST思想,后面会专门总结它,感兴趣的同学可以先看看这个链接中的例子:http://www.ibm.com/developerworks/cn/webservices/ws-restajax/

单页面的思想

  单页面就是只有一个页面的Web程序,所有的操作都在同一个页面中完成,所有的数据交互都通过AJAX或者WebSocket完成,使用这些程序的感觉就如同使用桌面程序一样。单页面程序开发也是近年来比较火的一种开发方式,很多的公司都针对这种方式开发了相应的类库,比如谷歌的AngularJS,AJAX是构建单页面程序的核心技术之一。

  单页面技术与REST模式并不是万能的,它们与AJAX紧密相关,但是又有很多的实际问题没有解决,所以大多时候,大家还是习惯把它们与别的技术,例如MVC结合起来使用。

参考资料:

一个完美的Web Ajax开发教程:https://www.ibm.com/developerworks/cn/views/xml/libraryview.jsp?sort_by=&show_abstract=true&show_all=&search_flag=&contentarea_by=%E6%89%80%E6%9C%89%E4%B8%93%E5%8C%BA&search_by=%E6%8E%8C%E6%8F%A1+Ajax&topic_by=-1&type_by=%E6%8A%80%E6%9C%AF%E6%96%87%E7%AB%A0&ibm-search=%E6%90%9C%E7%B4%A2

替代Ajax的一些技术:http://www.ibm.com/search/csass/search/?q=%E5%8F%8D%E5%90%91Ajax&dws=cndw&ibm-search.x=12&ibm-search.y=16&ibm-search=Search&sn=dw&lang=zh&cc=CN&ddr=&en=utf&lo=zh&hpp=20

最新文章

  1. MS SQL Server中数据表、视图、函数/方法、存储过程是否存在判断及创建
  2. MS SQL 统计信息浅析上篇
  3. JS常用语句
  4. META 标签的使用
  5. Qt Quick鼠标事件处理、键盘、计时器
  6. ESFramework 4.0 进阶(01)-- 消息
  7. JS中apply和call的区别和用法
  8. 服务器 Disk full
  9. Python内置函数(37)——sorted
  10. 原来你是这样的Promise
  11. Python播放、关闭音乐代码
  12. Consul 域名服务
  13. CAP原则
  14. Linux下jdk、Tomcat、MySQL的安装
  15. 使用Nexus搭建Maven服务器详细配置【转】
  16. (转)android系统架构及源码目录结构
  17. iis7错误提示An error occurred on the server when processing the URL...
  18. python 逐行读取文本
  19. FormData js对象的介绍和使用
  20. 【BZOJ】1636: [Usaco2007 Jan]Balanced Lineup(rmq+树状数组)

热门文章

  1. CUDA driver version is insufficient for CUDA runtime version 解决
  2. centos7配置apache服务
  3. 链表的创建(C语言实现)
  4. 使用First查找集合报错:序列不包含任何匹配元素
  5. CSS实现table固定宽度,超过单元格部分内容省略
  6. OpenStack 单元测试
  7. IdentityServer Token验证
  8. mysql 开发进阶篇系列 28 数据库二进制包安装(centos系统准备)
  9. eclipse svn 忽略 target目录
  10. 从零开始学 Web 之 Vue.js(一)Vue.js概述,基本结构,指令,事件修饰符,样式