最近在做公司QA系统改造时,有这样的一个场景.

QA系统中有些数据项需要从JIRA平台(一个国外项目与事务跟踪工具)中获取,JIRA平台提供了很完善的Rest API.

现在的要求是,在QA系统中提交项目时,必须先从JIRA平台获取很多的数据项,每次请求的Rest API都不一样,

同时必须等所有请求都成功返回数据后才能提交项目.

因为之前对Jquery Deferred有过研究,发现这个场景用它来实现再合适不过了.

这里对Jquery Deferred不做过多讲解了,不了解的同学可以先看下面的文章.

http://www.ruanyifeng.com/blog/2011/08/a_detailed_explanation_of_jquery_deferred_object.html

http://www.cnblogs.com/justany/archive/2013/01/20/2867444.html

好了,现在让我们来模拟上面的场景.(文章最后有完整DEMO下载)

假设我们获取数据项的请求全都由JqueryHandler.ashx来处理,在handler里面用Thread.Sleep()来模拟请求Rest API时的网络延迟.

 public void ProcessRequest(HttpContext context)
{
context.Response.ContentType = "application/json"; string action = context.Request.Form["Action"];
//用Thread.Sleep()模拟请求Rest API时的网络延迟
switch (action)
{
case "delay1Seconds":
Thread.Sleep();
WriteSuccess(context, action, "");
break;
case "delay2Seconds":
Thread.Sleep();
WriteSuccess(context, action, "");
break;
case "delay3Seconds":
Thread.Sleep();
WriteSuccess(context, action, "");
break;
default:
break;
}
} public void WriteSuccess(HttpContext context, string action, string seconds)
{
//输出JSON结果
string index = context.Request.Form["Index"];
string json = "{\"flag\":0,\"msg\":" + seconds + ",\"Index\":" + index + "}";
context.Response.Write(json);
}

数据服务端模拟好了之后,接下来让我们来发出获取数据项的请求.

    <script src="Scripts/jquery-1.7.2.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(function () { $("#btn_Request").click(
function () {
$("#div_Content").html(""); //模拟请求Handler地址
var requestUrl = "JqueryHandler.ashx"; //ajax请求 action名称数组
var requestInfoArr =
[
{ Action: "delay1Seconds" },
{ Action: "delay2Seconds" },
{ Action: "delay3Seconds" }
]; //用于保存Jquery Defered对象
var deferredOBJ = []; //创建3个 Jquery Deferred 对象
//与3个对 JqueryHandler.ashx 的异步请求一 一对应
for (var i = 0; i < requestInfoArr.length; i++) {
deferredOBJ[i] = $.Deferred(); var jsonData = requestInfoArr[i]; //记录当前ajax请求的索引,方便后面找到对应的Jquery Deferred对象
jsonData.Index = i; //发出ajax请求
$.ajax({
type: "POST",
dataType: "json",
url: requestUrl,
data: jsonData,
success: function (data, statu) {
//flag为0时表示请求成功
if (data.flag == 0) {
var result = requestInfoArr[data.Index].Action + " 请求成功,耗时:" + data.msg + "秒";
$("#div_Content").append($("<p/>").text(result)); //根据前面传过去的索引找到对应Deferred对象,将状态改成resolve(表示成功)
deferredOBJ[data.Index].resolve();
} else {
// 如果请求出错,将状态改成reject (表示失败)
//这里调用reject()后,会立即执行下面的fail()函数
deferredOBJ[data.Index].reject(data.msg);
}
},
error: function (data, statu) {
alert("ajax请求获取数据失败!");
}
});
} //使用$.when() 来控制3个异步请求的流程,保证所有异步请求都完成后再执行done函数
$.when(deferredOBJ[0], deferredOBJ[1], deferredOBJ[2])
.done(function () {
var result = "所有请求完成...";
$("#div_Content").append($("<p/>").text(result));
})
.fail(function (error) {
alert("从JIRA获取度量项数据失败, 请重试");
}); }); });
</script>

这里的巧妙之处在于 jsonData.Index = i;  这句代码,不然要就要写3个ajax请求,代码会显得臃肿.

如果不记录当前请求索引的话,后面的success,error函数就无法找到对应的Deferred对象来改变状态.

可能大家会问,为什么不用deferredOBJ[i]来获取,这是因为请求都是异步的,在success,error函数里来获取 i 永远都是2(因为requestInfoArr.length是2).

让我们来验证一下这3个ajax请求是不是都是异步执行的.

用firebug可以看到3个ajax请求是同时发出的,这样3个请求只花了3.09s.

如果3个ajax请求是顺序执行的话就需要花费 2.03s+1.06s+3.09s=6.18s, 使用jquery deferred节约了一倍的时间.

最后附上程序运行截图和DEMO程序:

完整DEMO下载:Jquery Deferred

 

利用 Jquery Deferred 异步你的程序的更多相关文章

  1. 利用jQuery.validate异步验证用户名是否存在

    转:http://www.cnblogs.com/linzheng/archive/2010/10/14/1851781.html HTML头部引用: <script type="te ...

  2. 使用 jQuery Deferred 和 Promise 创建响应式应用程序

    这篇文章,我们一起探索一下 JavaScript 中的 Deferred 和 Promise 的概念,它们是 JavaScript 工具包(如Dojo和MochiKit)中非常重要的一个功能,最近也首 ...

  3. jquery.Deferred promise解决异步回调

    我们先来看一下编写AJAX编码经常遇到的几个问题: 1.由于AJAX是异步的,所有依赖AJAX返回结果的代码必需写在AJAX回调函数中.这就不可避免地形成了嵌套,ajax等异步操作越多,嵌套层次就会越 ...

  4. 利用jquery.form实现异步上传文件

    实现原理 目前需要在一个页面实现多个地方调用上传控件上传文件,并且必须是异步上传.思考半天,想到通过创建动态表单包裹上传文件域,利用jquery.form实现异步提交表单,从而达到异步上传的目的,在上 ...

  5. 异步提交form的时候利用jQuery validate实现表单验证

    异步提交form的时候利用jQuery validate实现表单验证相信很多人都用过jquery validate插件,非常好用,并且可以通过下面的语句来自定义验证规则    // 电话号码验证    ...

  6. javascript异步代码的回调地狱以及JQuery.deferred提供的promise解决方式

    我们先来看一下编写AJAX编码常常遇到的几个问题: 1.因为AJAX是异步的,全部依赖AJAX返回结果的代码必需写在AJAX回调函数中.这就不可避免地形成了嵌套.ajax等异步操作越多,嵌套层次就会越 ...

  7. jQuery异步框架探究2:jQuery.Deferred方法

    (本文针对jQuery1.6.1版本号)关于Deferred函数的描写叙述中有一个词是fledged,意为"羽翼丰满的",说明jQuery.Deferred函数应用应该更成熟. 这 ...

  8. jQuery Deferred和Promise的使用介绍:

    deferred对象是从jquery1.5.0引入的一个新对象,ES6也引入了Promise的正式规范. 抽象来说,deferreds 可以理解为表示需要长时间才能完成的耗时操作的一种方式,相比于阻塞 ...

  9. 使用jQuery+PHP+Mysql实现抽奖程序

    抽奖程序在实际生活中广泛运用,由于应用场景不同抽奖的方式也是多种多样的.本文将采用实例讲解如何利用jQuery+PHP+Mysql实现类似电视中常见的一个简单的抽奖程序. 查看演示 本例中的抽奖程序要 ...

随机推荐

  1. CentOS下判断自己的VPS是OpenVZ的还是Xen的

    一般来说,VPS的虚拟化技术,有Xen.OpenVZ.Xen HVM和VMware这几种,那么,如何判断自己的VPS是基于哪种虚拟化技术的呢? 1.执行:ls /proc/命令,一般Xen的VPS,/ ...

  2. c# 将字符串转换为逻辑表达式(字符串转换布尔)

    比如:string str="6>5"; 要的效果是:bool result=6>5 方案一: 命名空间:System.Data: DataTable dt = new ...

  3. 无开发经验,初学python

    1.无开发经验,初学python   如果你不会其他语言,python是你的第一门语言: A Byte of Python (简明python教程,这个有中文版简明 Python 教程)是非常好的入门 ...

  4. linux系统更改目录和文件的权限总结

    对于属于你的文件,可以按照自己的需要改变其权限位的设置.在改变文件权限位设置之前,要仔细地想一想有哪些用户需要访问你的文件(包括你的目录).可以使用c h m o d命令来改变文件权限位的设置.这一命 ...

  5. [原]poj-1611-The Suspects(水并查集)

    题目链接:http://poj.org/problem?id=1611 题意:输入n个人,m个组.初始化0为疑似病例.输入m个小组,每组中只要有一个疑似病例,整组人都是疑似病例.相同的成员可以在不同的 ...

  6. poj-3616 Milking Time (区间dp)

    http://poj.org/problem?id=3616 bessie是一头工作很努力的奶牛,她很关心自己的产奶量,所以在她安排接下来的n个小时以尽可能提高自己的产奶量. 现在有m个产奶时间,每个 ...

  7. Tyvj 1085 派对

    这道题和HDU 1016的素数环那道题很相似. 虽然1A了,但写代码的过程中还是丢三落四的. 贴完代码闪人,嘿嘿 //#define LOCAL #include <iostream> # ...

  8. 二、CSS 基本介绍

    [ 显示目录 ] [ 隐藏 ] 目录 基本概念 CSS组成部分 CSS的规则 引入CSS样式的方法 颜色的表示 CSS Reset 选择器分类 浮动 盒子模型 box-sizing属性 实例:实现“田 ...

  9. 事件对象event和计时器

    事件对象:event 属性: srcElement事件源对象 keyCode 键盘按键Ascii码 window方法: 定时器: 1)setTimeout();//n毫秒后执行一次 2)setInte ...

  10. Service完全解析(转)

    今天我们来讲一下Android中Service的相关内容. Service在Android中和Activity是属于同一级别上的组件,我们可以将他们认为是两个好哥们,Activity仪表不凡,迷倒万千 ...