1. 程式人生 > >AngularJS 中的Promise --- $q服務詳解

AngularJS 中的Promise --- $q服務詳解

eject 標準 resolv ise comment 失敗 實例 方法 狀態

什麽是Promise

Javascript中異步的實現方式有很多,延時函數、回調函數、以及es6新增的生成器函數,其中Promise也是實現異步的方式之一。
關於javascript中的異步實現方式的詳解以及區別,後期會更新博客,敬請期待,此處不再贅述。

$q服務

簡言之$q服務是AngularJS中自己封裝實現的一種Promise實現。先介紹一下$q常用的幾個方法:

  • defer() 創建一個deferred對象,這個對象可以執行幾個常用的方法,比如resolve,reject,notify等
  • all() 傳入Promise的數組,批量執行,返回一個promise對象
  • when() 傳入一個不確定的參數,如果符合Promise標準,就返回一個promise對象。
需要註意的是在Promise中,定義了三種狀態:等待狀態,完成狀態,拒絕狀態。
關於狀態有兩個規定:
1.狀態的變更是不可逆的
2.等待狀態可以變成完成或者拒絕

defer()方法

在$q中,可以使用resolve方法,變成完成狀態;使用reject方法,變成拒絕狀態。
其中defer()用於創建一個deferred對象,defer.promise用於返回一個promise對象,來定義then方法。then中有三個參數,分別是成功回調、失敗回調、狀態變更回調。
下面看一個公司項目遇到的實例:

‘use strict‘;

angular.module(‘app‘)
    .controller(‘positionCtrl‘,[‘$scope‘,‘$state‘,‘$q‘,‘$stateParams‘,‘$http‘,function ($scope,$state,$q,$stateParams,$http) {
        var vm = this;
        vm.position;
        vm.company;
        vm.isLogin = false;
        function getPosition() {
            var def = $q.defer();
            $http.get(‘/data/position.json?id = ‘ + $stateParams.id)
                .then(function (resp) {
                    vm.position = resp.data;
                    // console.log(resp.data);
                    // console.log(vm.position);
                    def.resolve(resp);
                }).catch(function () {
                def.reject(err);
            });
            return def.promise;
        };
        function getCompany(id) {
            $http.get(‘data/company.json?id=‘+id)
                .then(function (resp) {
                    vm.company = resp.data;
                    // console.log(vm.company);
                })
                .catch(function (err) {
                    console.log(err);
            });
        };
        getPosition().then(function (obj) {
            getCompany(obj.companyId);
        });
    }]);

上述代碼業務邏輯其實很簡單,首先要獲取公司職位vm.position,根據職位信息中的companyId來獲取公司vm.company。
在第一個函數中getPosition中,首先調用$q.defer()方法得到一個deferred對象。 return def.promise;語句很顯然使得函數getPosition返回一個Promise對象,這樣在調用 getPosition()函數之後可以直接使用.then()方法。

 getPosition().then(function (obj) {
            getCompany(obj.companyId);
        });

這樣就把兩個函數的同步執行,變成了異步執行。

all()方法

這個all()方法,可以把多個primise的數組合並成一個。當所有的promise執行成功後,會執行後面的回調。回調中的參數,是每個promise執行的結果。
當批量的執行某些方法時,就可以使用這個方法。

 var funcA = function(){
                var def = $q.defer();
                console.log("funcA");
                //some code
                return def.promise;
            }
var funcB = function(){
                var def = $q.defer();
                console.log("funcA");
                //some code
                return def.promise;
            }
$q.all([funcA(),funcB()])
            .then(function(result){
                console.log(result);
            });


作者:大闖仔
鏈接:https://www.jianshu.com/p/5dc90b5e62c2
來源:簡書
著作權歸作者所有。商業轉載請聯系作者獲得授權,非商業轉載請註明出處。

AngularJS 中的Promise --- $q服務詳解