2014-10-08 60 views
1

執行的看來,工廠方法執行優先級是最高的,因此回調沒有數據來處理。做這項工作的最佳方式是什麼?

我得到了這樣的工廠

app.factory('jsonService', function($http) { 
    return { 
     getDistricts: function(callback) { 
      $http.get('data/districts.json').success(callback); 
     }, 
     getLocations: function(path,callback) { 
      $http.get('data/'+path+'.json').success(callback); 
     } 
    }; 
}); 

和控制器

var app = angular.module('sandbox', []); 
app.controller('sandboxCtrl',function ($scope,jsonService) { 

//This one works 
    $scope.init1= function(){ 
     jsonService.getDistricts(function(data){ 
      $scope.districts = data; 
      $scope.currentDistrict = $scope.districts[0].name; 

      jsonService.getLocations($scope.currentDistrict,function(data){ 
      $scope.locations1 = data; 

     }) 
     }); 

    }; 
    $scope.init1(); 

    //This one does not 
    $scope.init2= function(){ 
     jsonService.getDistricts(function(data){ 
      $scope.districts = data; 
      $scope.currentDistrict = $scope.districts[0].name; 
     }) 
     jsonService.getLocations($scope.currentDistrict,function(data){ 
      $scope.locations1 = data; 
     }); 

    }; 
    $scope.init2(); 

}); 

這裏的工作plunker

回答

1

角有一個名爲$ Q()承諾的實現,你應該在閱讀起來。

有一種競爭狀態,由於HTTP調用的異步性質。請查看下面鏈接的更新代碼,該代碼顯示了您的代碼正在運行(成功)使用承諾來連續處理您的兩個調用的示例。所以,在你的第一個成功

調用它會調用你的第二個服務方法都不用感謝回調承諾的力量。

jsonService.getDistricts() 
    .success(function(data) { 
    $scope.districts = data; 
    $scope.currentDistrict = $scope.districts[0].name; 
    jsonService.getLocations($scope.currentDistrict) 
     .success(function(locationData) { 
     $scope.locations = locationData; 
     }) 
    }); 

updated PLKR

承諾澄清: 原始實施基本承諾使用then來處理響應和承諾從$http返回添加其他方法(successerror)將從響應對象解壓您的數據你需要處理,如果你只是使用then

+1

+1 OP:我認爲你應該接受這個答案,它比我的好得多。然而,看看我在答案中給出的例子,它們可能是這個例子的一個很好的補充。 – Josep 2014-10-08 14:09:54

+0

另外,請注意,打開服務中的承諾並不是一個好主意,因爲這增加了不必要的耦合到您的工廠。 – Josep 2014-10-08 14:14:09

+0

非常感謝這些信息。但是,我仍然可以使用這種方法在分離函數中調用.getLocations,還是必須將它綁定到.success()或.then()方法? – 2014-10-08 14:28:23

1

init1()是這樣做的正確方法。 init2()確實有效,因爲在jsonService.getDistritcs()完成之前jsonService.getLocations()正在調用。角度$http服務是異步的。由於jsonService.getLocations()依賴於從jsonServicd.getDistricts()數據,你必須等待,直到.getDistricts()調用.getLocations()之前完成。要做到這一點的方法之一是在.getDitricts()回調中調用.getLocations(),就像你在init1()一樣。

+0

init1()是這樣做的正確方法嗎?我不同意,我認爲服務應該返回承諾而不是解開它們。 – Josep 2014-10-08 14:15:15

+0

有多種方法可以做到這一點。當我說'init1()'是這樣做的正確方法時,我的意思是與'init2()'相比。他是否想要使用回調或承諾是他的選擇。 – JME 2014-10-08 14:20:42

+0

我並不是說你的回答是錯誤的,因爲它不是,實際上你指出$ http服務的調用是異步的,因此如果你想要使用由其中一個,你將不得不等待,直到數據回來...所以,+1。然而我認爲問題的根源在於OP不知道承諾如何在角度上工作。 – Josep 2014-10-08 14:34:37