2015-10-19 114 views
0

功能getIdentityTokenDecrypted給我很難。我想從decryptToken SERVICE B返回承諾getToken服務A,以檢索令牌。如何從函數返回承諾?

這裏是我所需要的步驟:

  1. 獲取outlookService.mailbox.getUserIdentityTokenAsync結果。 (給出加密令牌)
  2. 通過$http路由/api/exchange/createAndValidateIdentityToken解密令牌。此請求返回我在SERVICE A中需要的令牌。

我該如何獲得此工作?

/*** SERVICE A ***/ 

var service = { 
    /*...*/ 
    token: getToken() 
}; 

return service; 

function getToken() { 
    var token; 

    serviceB.getIdentityTokenDecrypted() 
     .then(function successCallback(response) { 
      token = response.data.UniqueUserIdentification; 
      return token; 
     }, function errorCallback(response) { 
      return null; 
     }); 
} 

/*** SERVICE B ***/ 

function getIdentityTokenDecrypted() { 
    var token = null; 
    var promise; 

    // This async call does not return a promise, 
    // I don't think I can chain after it. 
    outlookService.mailbox.getUserIdentityTokenAsync(function (res) { 
     token = res; 
    }); 

    // That's why I use an interval 
    promise = $interval(function() { 
     if (token != null) { 
      $interval.cancel(promise); 
      return decryptToken(); 
     } 
    }, 100); 

    function decryptToken() { 
     var location = window.location.href; 

     // I need to get the 'data' from the success 
     // of this request to retrieve the token 
     return $http({ 
      method: "POST", 
      url: "/api/exchange/createAndValidateIdentityToken", 
      data: JSON.stringify({ 
       userIdentityToken: token, 
       location: location 
      }) 
     }); 
    }; 
    return promise; 
}; 
+0

有第一個參數是回調方法:https://msdn.microsoft.com/en-us/library/office/fp142236.aspx雖然它導致了同樣的問題,我不知道如何從此回調函數返回$ hhtp調用的承諾。 – Elfayer

回答

4

由於outlookService.mailbox.getUserIdentityTokenAsync提供了一個回調,你不需要$interval。您可以承諾 - 通過創建您自己的承諾(如果不可避免的話,這是很好的),然後用您從$http得到的承諾來承諾 - 通過創建您自己的承諾,您可以承諾任何異步函數,回調getUserIdentityTokenAsync被觸發)。

我不「做」角,但顯然$q has a "streamlined" syntax很像ES2015的:

promise = $q(function(resolve, reject) { 
    outlookService.mailbox.getUserIdentityTokenAsync(function (res) { 
     if (/*...presumably there's some failure condition...*/) { 
      reject(/*...*/); 
     } else { 
      token = res; 
      resolve(decryptToken()); 
     } 
    }); 
}); 

(我可能還修改decryptToken接受令牌作爲參數,而不是讓token變量)。

關鍵的一點是,如果你用另一個承諾解決承諾,那將通過鏈傳播。

+1

「使用回調,而不是$間隔」,你是對的,沒有任何意義。^^ – Elfayer

+0

@Elfayer:我很尷尬地說,我沒有注意到你使用的回調,直到我已經寫了大部分的答案,其中以同樣的段落開頭,然後是「但這並不改變你必須以某種方式得到回報情況下的承諾」,然後顯示上述情況,但是間隔時間。幸運的是,我趕上了它。 :-)但是現在我剛剛刪除了第一段,它沒有任何用處。 –

+0

由於這是AngularJS OP的討論,最好使用[$ q service](https://docs.angularjs.org/api/ng/service/$q)代替。這幾乎是相同的語法,但包裹在一個'$ watch'中。@ – Guilherme