簡體   English   中英

$ http承諾角度服務

[英]$http promise in angular service

我在角度服務中遇到了承諾的問題。 我有一個getArea方法的服務,它應該返回服務區域的名稱。 該服務從API獲取服務區域。 getArea獲取服務區域時,它會找到所請求區域的名稱,並應返回它。 但是,我的代碼不起作用 - 我進入了無限循環。 我想我誤解了如何使用承諾?

SupplierService:

var servicePromise;
var getServices = function(){
    if( !servicePromise ){
        servicePromise = $http.get('/api/services')
            .then(function(res){
                return res.data.data;
            });
    }
    return servicePromise;
};


var myService = {

    getServices : getServices,

    getArea : function(questionnaireId){
        getServices().then(function(services){
            // ...
            return "hello world";
        });
    }
};

return myService;

控制器:

$scope.supplierService = SupplierService;

視圖:

<div>
    <b>Area:</b> {{ supplierService.getArea(r.questionnaireId) }}
</div

我希望視圖顯示“Area:hello world”,但進入無限循環。


更新1:我已將getServices添加為服務中的公共函數,並可以從控制器訪問它,如下所示:

SupplierService.getServices().then(function(d){
    $scope.services = d;
});

因此我猜問題是在getArea方法中?


更新2:我受到了這個答案的啟發https://stackoverflow.com/a/12513509/685352 我想緩存結果。


更新3:這是一個plunker 如果您嘗試從視圖中訪問supplierService.getArea(100) - 瀏覽器將不會響應。

您的服務看起來應該更像這樣:

var getServices = function(){
    var deferred = $q.deferred();
    $http.get('/api/services')
            .then(function(res){
                deferred.resolve(res.data)
            });
    return deferred.promise;
};

請注意,在創建延遲時,必須返回deferred.promise(實際的promise),然后在異步調用返回時,必須根據需要調用deferred.resolve或deferred.rejected(分別觸發成功或錯誤函數)

輕微添加我有一個plunkr顯示從服務到控制器的數據的幾種方法,因為這是開發人員進入Angular的常見問題

http://plnkr.co/edit/ABQsAxz1bNi34ehmPRsF?p=info

這不是絕對的最佳實踐,因為我試圖盡可能簡單,但基本上顯示了三種不同的方式來“共享”您的數據,請記住這些方法中的一些依賴於angular.copy,這意味着您存儲的服務的屬性數據必須是Object或Array(原始類型不起作用,因為無法共享引用)。

這是一個重寫,包括內聯函數:

var myService = {
    var dataLoaded = false;
    var data = {}; //or = [];
    getServices : function(){
        var deferred = $q.defer();
        if( !dataLoaded ){
            $http.get('/api/services').then(function(res){
                angular.copy(res.data, myService.data);
                deferred.resolve(myService.data);
            }, function(err){
                deferred.reject("Something bad happened in the request");
            });
        }
        else
        {
            deferred.resolve(myService.data);
        }
        return deferred.promise;
    }
};

return myService;

為了解釋,我使用$ q服務創建了一個新的承諾,您需要將其注入服務功能。 這允許我使用我已經擁有的數據來解決該承諾,或者調用該服務並解析該數據,但在這兩種情況下使用它時,假設您將獲得一個承諾,因此處理異步操作。 如果要加載多個數據集,則可以使用對象來存儲標志而不是單個布爾值。

我想如果你返回$ http回調?

//$http.get('/someUrl').success(successCallback);


var getServices = function(){
    return $http.get('/api/services');

};

getServices.success(function(services){
// ...
           return "hello world";
        });
   }

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM