6.5 jQuery中的Ajax

6.5 jQuery中的Ajax

jQuery对Ajax操作进行了封装,在jQuery中$.ajax()方法属于最底层的方法,第2层是load()、$.get()$.post()方法,第3层是$.getScript()$.getJSON()方法。首先介绍第2层的方法,因为其使用频率很高。

6.5.1 load()方法

1.载入HTML文档

load()方法是jQuery中最为简单和常用的Ajax方法,能载入远程HTML代码并插入DOM中。它的结构为:

[插图]

load()方法参数解释如表6-1所示。

表6-1 load()方法参数解释

[插图]

首先构建一个被load()方法加载并追加到页面中的HTML文件,名字为test.html,HTML代码如下:

[插图]

然后新建一个空白页面,在上面添加两个元素:<button>按钮用来触发Ajax事件,id为“resText”的元素用来显示追加的HTML内容。HTML代码如下:

[插图]

接下来就可以开始编写jQuery代码了。等DOM元素加载完毕后,通过单击id为“send”的按钮来调用load()方法,然后将test.html的内容加载到id为“resText”的元素里。

jQuery代码如下:

[插图]

当按钮被单击后,出现图6-3所示的界面。

[插图]

图6-3 load()方法调用成功

显然,load()方法完成了原本很繁琐的工作。开发人员只需要使用jQuery选择器为HTML片段指定目标位置,然后将要加载的文件的URL 作为参数传递给 load()方法即可。当单击按钮后, test.html页面的HTML内容就会被加载并插入主页面<divid="resText"></div>的元素中。

注意:test.html页面里并没有添加样式,但现在加载的内容有样式了。这些样式是在主页面中添加的,即主页面相应的样式会立即应用到新加载的内容上。

2.筛选载入的HTML文档

上个例子是将 test.html 页面中的内容都加载到 id 为“resText”的元素里。如果只需要加载test.html页面内的某些元素,那么可以使用load()方法的URL参数来达到目的。通过为URL参数指定选择符,就可以很方便地从加载过来的HTML文档里筛选出所需要的内容。

load()方法的URL参数的语法结构为:”url selector”。注意,URL和选择器之间有一个空格。

例如只需要加载test.html页面中class为“para”的内容,可以使用如下代码来完成:

[插图]

运行效果如图6-4所示。

[插图]

图6-4 用load()方法加载一部分HTML元素

3.传递方式

load()方法的传递方式根据参数data来自动指定。如果没有参数传递,则采用GET方式传递;反之,则会自动转换为POST方式。关于GET和POST传递方式的区别,将在后面进行讲解。

[插图]

4.回调参数

对于必须在加载完成后才能继续的操作,load()方法提供了回调函数(callback),该函数有 3个参数,分别代表请求返回的内容、请求状态和XMLHttpRequest对象,jQuery代码如下:

[插图]

注意:在load()方法中,无论Ajax请求是否成功,只要当请求完成(complete)后,回调函数(callback)就被触发。对应下面将介绍的$.ajax()方法中的complete回调函数。

6.5.2 $.get()方法和$.post()方法

load()方法通常用来从 Web 服务器上获取静态的数据文件,然而这并不能体现Ajax的全部价值。在项目中,如果需要传递一些参数给服务器中的页面,那么可以使用$.get()或者$.post()方法(或者是后面要讲解的$.ajax()方法)。

注意:`$.get()`和`$.post(`)`方法是jQuery中的全局函数,而在此之前讲的jQuery方法都是对jQuery对象进行操作的。

1.$.get()方法

$.get()方法使用GET方式来进行异步请求。

它的结构为:

[插图]

$.get()方法参数解释如表6-2所示。

表6-2 $.get()方法参数解释

[插图]

下面是一个评论页面的HTML代码,通过该段代码来介绍$.get()方法的使用。

[插图]

本段代码将生成图6-5所示的页面。

[插图]

图6-5 评论初始化页面

将姓名和内容填写好后,就可以准备提交评论了。如图6-6所示。

[插图]

图6-6 填写好数据

(1)使用参数

首先,需要确定请求页面的URL地址。代码如下:

[插图]

然后,在提交之前,需要获取“姓名”和“内容”的值作为data参数传递给后台。

代码如下:

[插图]

如果服务器端接收到传递的data 数据并成功返回,那么就可以通过回调函数将返回的数据显示到页面上。

$.get()方法的回调函数只有两个参数,代码如下:

[插图]

data 参数代表请求返回的内容,textStatus 参数代表请求状态,而且回调函数只有当数据成功返回(success)后才被调用,这点与load()方法不一样。

(2)数据格式

服务器返回的数据格式可以有多种,它们都可以完成同样的任务。以下是几种返回格式的对比。

  • HTML片段

由于服务器端返回的数据格式是HTML片段,因此并不需要经过处理就可以将新的HTML数据插入到主页面中。jQuery代码如下:

[插图]

HTML 片段实现起来只需要很少的工作量,但这种固定的数据结构并不一定能够在其他的Web应用程序中得到重用。

  • XML文档

由于服务器端返回的数据格式是XML文档,因此需要对返回的数据进行处理,前面的章节已经介绍过jQuery强大的DOM处理能力,处理XML文档与处理HTML文档一样,也可以使用常规的attr()、find()、filter()以及其他方法。jQuery代码如下:

返回数据格式为XML文档的过程实现起来比HTML片段要稍微复杂些,但XML文档的可移植性是其他数据格式无法比拟的,因此以这种格式提供的数据的重用性将极大提高。例如 del.icio.us (http://del.icio.us),Flickr(http://flickr.com)和某些开放平台都是以XML格式输出数据,读者可以利用它们提供的API,将获得的内容整合到自己的网站中(Mashup应用)。不过,XML文档体积相对较大,与其他文件格式相比,解析和操作它们的速度要慢一些。

[插图]

注意:由于期待服务器端返回的数据格式是XML文档,因此需要在服务端设置Content-Type类型,代码如下:[插图]
  • JSON文件

之所以会出现这种数据格式的文件,很大程度上是因为XML 文档体积大和难以解析。JSON文件和XML文档一样,也可以方便的被重用。而且,JSON文件非常简洁,也容易阅读。想了解更多的JSON文档知识,可以访问http://json.org/ 网址。

由于服务器端返回的数据格式是JSON文件,因此需要对返回的数据进行处理之后,才可以将新的HTML数据添加到主页面中。jQuery代码如下:

[插图]

在上面的代码中,将$.get()方法的第4个参数(type)设置为“json”来代表期待服务器端返回的数据格式。

注意:(1)在不远的将来,新版的JavaScript中XML将会和JSON一样容易解析,相信到时候通用且容易解析的XML将会成为主流的数据交换格式。不过在它到来之前,JSON依然有很强的生命力。(2)JSON的格式非常严格,构建的JSON文件必须完整无误,任何一个括号的不匹配或者缺少逗号,都会导致页面上的脚本终止运行,甚至还会带来其他更加严重的负面影响。比如,我们返回的数据都必须要有双引号,必须是:{ "username" :"张三" },而不能是:{ username: "张三" }。

以上3种返回方式都可以达到图6-7所示的效果。

[插图]

图6-7 将返回的数据添加到页面上

通过对3种数据格式的优缺点进行分析,可以得知在不需要与其他应用程序共享数据的时候,使用HTML片段来提供返回数据一般来说是最简单的;如果数据需要重用,那么 JSON文件是不错的选择,它在性能和文件大小方面具有优势;而当远程应用程序未知时,XML 文档是明智的选择,它是 Web 服务领域的“世界语”。具体选择哪种数据格式,并没有严格的规定,读者可以根据需求来选择最适合的返回格式来进行开发。

2.$.post()方法

它与$.get()方法的结构和使用方式都相同,不过它们之间仍然有以下区别。

  • GET请求会将参数跟在URL后进行传递,而POST请求则是作为HTTP消息的实体内容发送给Web服务器。当然,在Ajax请求中,这种区别对用户是不可见的。
  • GET方式对传输的数据有大小限制(通常不能大于2KB),而使用POST方式传递的数据量要比GET方式大得多(理论上不受限制)。
  • GET 方式请求的数据会被浏览器缓存起来,因此其他人就可以从浏览器的历史记录中读取到这些数据,例如账号和密码等。在某种情况下,GET方式会带来严重的安全性问题,而POST方式相对来说就可以避免这些问题。
  • GET方式和POST方式传递的数据在服务器端的获取也不相同。在PHP中,GET方式的数据可以用$_GET[]获取,而 POST 方式可以用$_POST[]获取。两种方式都可以用$_REQUEST[]来获取。

由于 POST和GET 方式提交的所有数据都可以通过$_REQUEST[]来获取,因此只需要改变jQuery函数,就可以将程序在GET请求和POST请求之间切换。代码如下:

[插图]

另外,当load()方法带有参数传递时,会使用POST方式发送请求。因此也可以使用load()方法来完成同样的功能。代码如下:

[插图]

上面使用load()、$.get()$.post()方法完成了一些常规的Ajax程序,如果还需要编写一些复杂的Ajax程序,那么就要用到jQuery中的$.ajax()方法。$.ajax()方法不仅能实现与load()、$.get()$.post()方法同样的功能,而且还可以设定beforeSend(提交前回调函数)、error(请求失败后处理)、success(请求成功后处理)以及complete(请求完成后处理)回调函数,通过这些回调函数,可以给用户更多的Ajax提示信息。另外,还有一些参数,可以设置Ajax请求的超时时间或者页面的“最后更改”状态等。关于$.ajax()方法将在后面的章节中进行讲解。

6.5.3 $.getScript()方法和$.getJson()方法

1.$.getScript()

有时候,在页面初次加载时就取得所需的全部JavaScript文件是完全没有必要的。虽然可以在需要哪个JavaScript文件时,动态地创建<script>标签,jQuery代码如下:

[插图]

或者

[插图]

但这种方式并不理想。为此,jQuery 提供了$.getScript()方法来直接加载.js文件,与加载一个HTML片段一样简单方便,并且不需要对JavaScript文件进行处理,JavaScript文件会自动执行。

jQuery代码如下:

[插图]

当“加载”按钮被单击后,出现如图6-8所示的效果。

[插图]

图6-8 $.getScript('test.js')方法调用成功

与其他 Ajax 方法一样,$.getScript()方法也有回调函数,它会在 JavaScript文件成功载入后运行。例如想载入jQuery官方颜色动画插件(jquery.color.js),成功后给元素绑定颜色变化动画,就可以用到$.getScript()方法的回调函数。代码如下:

[插图]

当jquery.color.js动画插件加载完毕后,单击id为“go”按钮时,class为block的元素就有了颜色动画变化。

2.$.getJSON()

$.getJSON()方法用于加载JSON文件,与$.getScript()方法的用法相同。

jQuery代码如下:

[插图]

当单击“加载”按钮后,网页上看不到任何效果。虽然函数加载了JSON文件,但是并没有告诉JavaScript对返回的数据如何处理。为此,jQuery提供了回调函数,在回调函数里处理返回的数据。代码如下:

[插图]

可以在函数中通过 data 变量来遍历相应的数据,也可以使用迭代方式为每个项构建相应的HTML 代码。虽然在这里可以使用传统的for 循环来实现,但既然是讲解jQuery,那么还是使用jQuery里的方法。jQuery提供了一个通用的遍历方法$.each(),可以用于遍历对象和数组。

$.each()函数不同于jQuery对象的each()方法,它是一个全局函数,不操作jQuery对象,而是以一个数组或者对象作为第1个参数,以一个回调函数作为第2个参数。回调函数拥有两个参数:第1个为对象的成员或数组的索引,第2个为对应变量或内容。代码如下:

[插图]

在上面的代码中,当返回数据成功后,首先清空 id 为“resText”的元素的内容,以便重新构造新的HTML,然后通过$.each()循环函数依次遍历每个项,并将遍历出来的内容构建成HTML代码拼接起来,最后将构建好的HTML添加到id为“resText”的元素中。

当“加载”按钮被单击后,出现如图6-9所示的效果。

[插图]

图6-9 $.getJSON('test.json')函数执行成功

不仅如此,还能通过使用JSONP形式的回调函数来加载其他网站的JSON数据,例如从图片网站(http://Flickr.com)搜索汽车类别的4张最新图片。代码如下:

[插图]

上面的代码中再次用到全局函数$.each()来遍历数据,因为只需要 4 张图片,所以当 i=3的时候就需要退出循环。在$.each()函数中,如果需要退出each循环,只要返回false即可。

当“加载”按钮被单击后,从Flickr网站加载的4张最新的汽车图片就会被添加到页面中。效果如图6-10所示。

[插图]

图6-10 加载Flickr网站的图片
注意:(1)jQuery 将自动把 URL 里的回调函数,例如“url?callback=?”中的后一个“?”替换为正确的函数名,以执行回调函数。(2)JSONP(JSON with Padding)是一个非官方的协议,它允许在服务器端集成Script tags返回至客户端,通过JavaScript Callback的形式实现跨域访问。由于JSON只是一种含有简单括号结构的纯文本,因此许多通道都可以交换JSON消息。而由于同源策略的限制,开发人员不能在与外部服务器进行通信的时候使用 XMLHttpRequest。而 JSONP是一种可以绕过同源策略的方法,即通过使用JSON与<script>标记相结合的方法,从服务器端直接返回可执行的JavaScript函数调用或者JavaScript对象。目前JSONP已经成为各大公司的Web应用程序跨域首选,例如Youtube GData、GoogleSocial Graph、Digg、豆瓣、Del.icio.us等。

6.5.4 $.ajax()方法

$.ajax()方法是jQuery最底层的Ajax实现。

它的结构为:

[插图]

该方法只有1个参数,但在这个对象里包含了$.ajax()方法所需要的请求设置以及回调函数等信息,参数以key/value的形式存在,所有参数都是可选的,常用参数如表6-3所示。

表6-3 $.ajax()方法常用参数解释

[插图]

如果需要使用$.ajax()方法来进行 Ajax 开发,那么上面这些常用的参数都必须了解。此外,$.ajax()方法还有其他参数,读者可以参考附录D的具体介绍。

前面用到的$.load()$.get()$.post()$.getScript()$.getJSON()这些方法,都是基于$.ajax()方法构建的,$.ajax()方法是jQuery最底层的Ajax实现,因此可以用它来代替前面的所有方法。

例如,可以使用下面的jQuery代码代替$.getScript()方法:

[插图]

再例如,可以使用以下jQuery代码来代替$.getJSON()方法:

[插图]