angular中的$http服务及promiseA+规范总结
来源:互联网 发布:邓云天觉知视频 编辑:程序博客网 时间:2024/06/05 21:51
我们可以使用内置的
1、链式调用
url:’data.json’,
method:’GET’
}).success(function(data,header,config,status){
//响应成功
}).error(function(data,header,config,status){
//处理响应失败
});
2、返回一个promise对象
var promise=$http({
method:’GET’,
url:”data.json”
});
由于$http方法返回一个promise对象,我们可以在响应返回时用then方法来处理回调。如果
使用then方法,会得到一个特殊的参数,它代表了相应对象的成功或失败信息,还可以接受两个
可选的函数作为参数。或者可以使用success和error回调代替。
promise.then(function(resp){
//resp是一个响应对象
},function(resp){
//带有错误信息的resp
});
或者这样:
promise.success(function(data,status,config,headers){
//处理成功的响应
});
promise.error(function(data,status,hedaers,config){
//处理失败后的响应
});
then()方法与其他两种方法的主要区别是,它会接收到完整的响应对象,而success()和error()则会对响应对
象进行析构。
3、快捷的get请求
①$http.get(‘/api/users.json’);
get()方法返回HttpPromise对象。
还可以发送比如:delete/head/jsonp/post/put 函数内可接受参数具体参照148页
②以再发送jsonp请求举例说明: 为了发送JSONP请求,其中url必须包含JSON_CALLBACK字样。
jsonp(url,config) 其中config是可选的
var promise=$http.jsonp(“/api/users.json?callback=JSON_CALLBACK”);
4、也可以将$http当做函数来使用,这时需要传入一个设置对象,用来说明如何构造XHR对象。
$http({
method:’GET’,
url:’/api/users.json’,
params:{
‘username’:’tan’
});
其中设置对象可以包含以下主要的键:
①method
可以是:GET/DELETE/HEAD/JSONP/POST/PUT
②url:绝对的或者相对的请求目标
③params(字符串map或者对象)
这个键的值是一个字符串map或对象,会被转换成查询字符串追加在URL后面。如果值不是字符串,会被JSON序列化。
比如这个:
//参数会转为?name=ari的形式
$http({
params:{‘name’:’ari’}
});
④data(字符串或者对象)
这个对象中包含了将会被当作消息体发送给服务器的数据。通常在发送POST请求时使用。
从AngularJS 1.3开始,它还可以在POST请求里发送二进制数据。要发送一个blob对象,你可以简单地通过使用data参数来传递它。
例如:
var blob=new Blob([‘Hello world’],{type:’text/plain’});
$http({
method:’POST’,
url:’/’,
data:blob
});
4、响应对象
AngularJS传递给then()方法的响应对象包含了四个属性。
◇data
这个数据代表转换过后的响应体(如果定义了转换的话)
◇status
响应的HTTP状态码
◇headers
这个函数是头信息的getter函数,可以接受一个参数,用来获取对应名字值
例如,用如下代码获取X-Auth-ID的值:
$http({
method: ‘GET’,
url: ‘/api/users.json’
}).then (resp) {
// 读取X-Auth-ID
resp.headers(‘X-Auth-ID’);
});
◇config
这个对象是用来生成原始请求的完整设置对象。
◇statusText(字符串)
这个字符串是响应的HTTP状态文本。
5、缓存HTTP请求
默认情况下,
$http.get(‘/api/users.json’,{ cache: true })
.success(function(data) {})
.error(function(data) {});
第一次发送请求时,
在这个例子里,由于设置了启用缓存,AngularJS默认会使用$cacheFactory,这个服务是AngularJS在启动时自动创建的。
如果想要对AngularJS使用的缓存进行更多的自定义控制,可以向请求传入一个自定义的缓存实例代替true。
6.
在谈论Promise之前我们要了解一下一些额外的知识;我们知道JavaScript语言的执行环境是“单线程”,所谓单线程,就是一次只能够执行一个任务,如果有多个任务的话就要排队,前面一个任务完成后才可以继续下一个任务。
这种“单线程”的好处就是实现起来比较简单,容易操作;坏处就是容易造成阻塞,因为队列中如果有一个任务耗时比较长,那么后面的任务都无法快速执行,或导致页面卡在某个状态上,给用户的体验很差。
当然JavaScript提供了“异步模式”去解决上述的问题,关于“异步模式”JavaScript提供了一些实现的方法。
回调函数(callbacks)
事件监听
Promise对象
关于回调函数,大家应该都不陌生,比如下面的代码(注:引用Leancloud上面的一点代码):
AV.User.logIn("myname", "mypass", { success: function(user) { // Do stuff after successful login. }, error: function(user, error) { // The login failed. Check error to see why. } });
用户通过用户名和密码来进行登录,如果登陆成功的话,会在success这个模块进行处理,如果登陆失败的话,就会在error这个模块进行处理。
当我们需要处理的任务不是很多的情况下,使用回调函数还是可以应付的,也没有太大的问题,但是当我们需要处理的任务比较多的时候,使用回调函数的弊端越来越明显了;首先,回调使得调用不一致,得不到保证;当依赖于其它回调时,它们篡改代码的流程,是调试变得异常艰难,每一步调用之后都需要显式的处理错误;最后,过多的回调使得代码的可读性和可维护性都变得很差,所以越来越多的程序员选择使用Promise去处理异步模式。
关于Promise我们会在下面进行详细的说明。
一 、Promise是什么
Promise是一种异步方式处理值(或者非值)的方法,promise是对象,代表了一个函数最终可能的返回值或者抛出的异常。
在与远程对象打交道时,Promise会非常有用,可以把它们看作远程对象的一个代理。
点击下面的链接可以查看Promise更多的信息
Promises/A+
Promises/A
二、使用Promise的理由
使用Promise可以让我们逃脱回调地狱,使我们的代码看起来像是同步的那样。
可以在程序中的任何位置捕捉错误,并且绕过依赖于程序异常的的后续代码,获得功能组合和错误冒泡的能力,最重要的是保持了异步运行的能力。
使我们的代码的可读性与可维护性都变得很好。
如何在AngularJS中使用Promise
要在AngularJS中使用Promise,要使用AngularJS的内置服务$q。
我们可以先使用$q的defer()方法创建一个deferred对象,然后通过deferred对象的promise属性,将这个对象变成一个promise对象;这个deferred对象还提供了三个方法,分别是resolve(),reject(),notify()。
下面我们来通过代码逐步地将上面的功能都实现,毕竟说得再多,不如你实实在在地把它们敲成代码去实现。
Test1
我们先通过一个同步的例子来创建一个promise对象。
HTML代码:
<div ng-app="MyApp"> <div ng-controller="MyController"> <label for="flag">成功 <input id="flag" type="checkbox" ng-model="flag" /><br/> </label> <hr/> <button ng-click="handle()">点击我</button> </div></div>
JS代码:
angular.module("MyApp", []).controller("MyController", ["$scope", "$q", function ($scope, $q) { $scope.flag = true; $scope.handle = function () { var deferred = $q.defer(); var promise = deferred.promise; promise.then(function (result) { alert("Success: " + result); }, function (error) { alert("Fail: " + error); }); if ($scope.flag) { deferred.resolve("you are lucky!"); } else { deferred.reject("sorry, it lost!"); } }}]);
我们来详细的分析一下上面的代码,我们在html页面上添加了一个checkbox,一个button目的是为了当我们选中checkbox和不选中checkbox时,点击下面的按钮会弹出不同的内容。
var deferred = $q.defer()这段代码创建了一个deferred对象,我们然后利用var promise = deferred.promise创建了一个promise对象。
我们给给promise的then方法传递了两个处理函数,分别处理当promise被执行的时候以及promise被拒绝的时候所要进行的操作。
下面的一个if(){}else{}语句块,包含执行和拒绝deferred promise,如果
现在回过头来看看,promise的then方法,如果promise被执行,那么它的参数中的第一个函数的result就代表了”you are lucky!”
我们暂时用的是同步的模式,为的是能够说明问题,后面将会使用异步的方法。
到这里我们可以了解一下$q的defer()方法创建的对象具有哪些方法
resolve(value):用来执行deferred promise,value可以为字符串,对象等。
reject(value):用来拒绝deferred promise,value可以为字符串,对象等。
notify(value):获取deferred promise的执行状态,然后使用这个函数来传递它。
then(successFunc, errorFunc, notifyFunc):无论promise是成功了还是失败了,当结果可用之后,then都会立刻异步调用successFunc,或者’errorFunc’,在promise被执行或者拒绝之前,notifyFunc可能会被调用0到多次,以提供过程状态的提示。
catch(errorFunc)
finally(callback)
通过使用then进行链式请求
我们通过使用then方法来进行链式调用,这样做的好处是,无论前一个任务或者说then函数是被执行或者拒绝了都不会影响后面的then函数的运行。
我们可以通过then创建一个执行链,它允许我们中断基于更多功能的应用流程,可以借此导向不同的的结果,这个中断可以让我们在执行链的任意时刻暂停后者推迟promise的执行。
html代码
<div ng-app="MyApp"> <div ng-controller="MyController"> <label for="flag">成功 <input id="flag" type="checkbox" ng-model="flag" /><br/> </label> <div ng-cloak> {{status}} </div> <hr/> <button ng-click="handle()">点击我</button> </div></div>
js代码
angular.module("MyApp", []) .controller("MyController", ["$scope", "$q", function ($scope, $q) { $scope.flag = true; $scope.handle = function () { var deferred = $q.defer(); var promise = deferred.promise; promise.then(function (result) { result = result + "you have passed the first then()"; $scope.status = result; return result; }, function (error) { error = error + "failed but you have passed the first then()"; $scope.status = error; return error; }).then(function (result) { alert("Success: " + result); }, function (error) { alert("Fail: " + error); }) if ($scope.flag) { deferred.resolve("you are lucky!"); } else { deferred.reject("sorry, it lost!"); } }}]);
我们在Part1代码的基础上添加了一些代码,在原来的promise的链条上新添加了一个then()处理函数,目的就是为了创建一个执行连,看看在这条执行连上,promise是如何被执行的。
需要注意的一点是,在第一个then()方法中,我们在第一个successFunc函数中将result的值进行了改变,在第二个errorFunc函数中对error的值也进行了改变。
因为这个promise对象是贯穿整个执行链条的,所以在第一个then()方法中对其值进行改变必然会反映到后面的then()方法中
一个异步模式的实例
js/app.js
angular.module("MyApp", ["ngRoute","MyController", "MyService"]).config(["$routeProvider", function($routeProvider){ $routeProvider .when('/',{ templateUrl: "views/home.html", controller: "IndexController" });}]);
js/controller.js
angular.module("MyController", []) .controller("IndexController", ["$scope", "githubService", function($scope, githubService){ $scope.name = "dreamapple"; $scope.show = true; githubService.getPullRequests().then(function(result){ $scope.data = result; },function(error){ $scope.data = "error!"; },function(progress){ $scope.progress = progress; $scope.show = false; }); }]);
js/service.js
angular.module("MyService", []) .factory('githubService', ["$q", "$http", function($q, $http){ var getPullRequests = function(){ var deferred = $q.defer(); var promise = deferred.promise; var progress; $http.get("https://api.github.com/repos/angular/angular.js/pulls") .success(function(data){ var result = []; for(var i = 0; i < data.length; i++){ result.push(data[i].user); progress = (i+1)/data.length * 100; deferred.notify(progress); } deferred.resolve(result); }) .error(function(error){ deferred.reject(error); }); return promise; } return { getPullRequests: getPullRequests };}]);
views/home.html
<h1>{{name}}</h1><h2>Progress: {{progress}}</h2><h3 ng-show="show">Please wait a moment...</h3><p ng-repeat="person in data">{{person.login}}</p>
index.html
<head> <meta charset="UTF-8"> <title>Route</title> <script src="http://cdn.bootcss.com/angular.js/1.4.0-rc.1/angular.js"></script> <script src="../node_modules/angular-route/angular-route.js"></script> <script src="js/app.js"></script> <script src="js/controller.js"></script> <script src="js/service.js"></script></head> <body ng-app="MyApp"> <header> <h1>Header</h1> <hr/> </header> <div ng-view> </div> <footer> <hr/> <h1>Footer</h1> </footer></body>
- angular中的$http服务及promiseA+规范总结
- angular中的$http服务(service)解析
- Angular核心服务$http
- angular的$http服务
- Angular中的自定义服务
- angular中的$controller服务
- angular中的自定义服务
- Angular中的$http
- angular服务——$http
- angular中的angular-ngSanitize模块-$sanitize服务
- 从HTML5与PromiseA+规范来看事件循环
- angular的服务小总结
- Angular中的$provide(自定义服务)
- angular中的http请求封装
- angular的http服务的常用方式
- Angular(四)内置服务$http
- angular指令实例及总结
- angular规范
- Nios ii软核程序烧写
- exists与in的区别以及exists在oracle与mysql中的语句写法
- Windows 2008R2 IIS7.5 下访问ASP网页报错的解决办法
- hdu 1530 Maximum Clique——最大团
- FJ的字符串
- angular中的$http服务及promiseA+规范总结
- Linux 内核clk 添加clk provider
- AS混淆打包和多渠道打包总结
- java中的消息转换器--HttpMessageConverter 分类:学习日记
- 利用navicat创建存储过程、触发器和使用游标的简单实例
- 浅谈原生JS和jQuery操作DOM
- 实现下拉框和搜索框一体功能
- caffe 01 win10 运行环境配置(不需要开发环境)
- 【Mysql】Mysql 各个版本区别