2016-11-20 32 views
1

我试图将服务返回的数据分配给$ scope属性。不知何故,它不能正常工作。服务方法通过$ http.get正确获取数据,但是它没有被分配给控制器中的$ scope。

app.service('StoreService', ['$http', function ($http) { 

    this.getStoreNamesService = function() { 
     console.log('getStoreNames called'); 
     $http.get('http://localhost:8080/storys') 
      .success(function (response, status) { 
       console.log(response); 
       return response; 
      }) 
    }; 
}]); 

app.controller('ItemFormController', ['$scope', '$http', '$mdDialog', 'itemService', 'StoreService', function ($scope, $http, $mdDialog, itemService, StoreService) { 

    $scope.storeNames = StoreService.getStoreNamesService(); 
}]); 

在服务中打印响应会提供正确的数据。但是当我打印$ scope.storeNames时,它也给了我没有定义的视图没有数据。

app.js:

var app = angular.module('BlankApp', ['ngMaterial', 'ngRoute']) 
.config(function($mdThemingProvider) { 
    $mdThemingProvider.theme('default') 
     .primaryPalette('teal') 
     .accentPalette('red') 
     .warnPalette('red'); 
}); 

app.config(function ($routeProvider) { 
    $routeProvider 
     .when('/addItem', { 
      templateUrl: 'templates/addItemForm.html', 
      controller: 'ItemFormController' 
     }) 
     .when('/', { 
     templateUrl: 'templates/first.html' 
     }) 
     .when('/store', { 
      templateUrl: 'templates/itemsInStore.html', 
      controller: 'StoreController' 
     }) 
     .when('/item/:itemId', { 
      templateUrl: 'templates/itemView.html', 
      controller: 'ItemController' 
     }) 
     .otherwise({ 
      template: '<h1>otherwise template</h1>' 
     }) 
}); 

脚本标记的顺序:

<!-- Angular Material requires Angular.js Libraries --> 
<script src="js/angular-1.5.8/angular.js"></script> 
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.5.5/angular-animate.min.js"></script> 
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.5.5/angular-aria.min.js"></script> 
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.5.5/angular-messages.min.js"></script> 
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.5.5/angular-route.min.js"></script> 

<!-- Angular Material Library --> 
<script src="js/AngularMaterial/angular-material.js"></script> 

<!-- Your application bootstrap --> 


<script src="js/app.js"></script> 
<script src="js/service/itemService.js"></script> 
<script src="js/service/StoreService.js"></script> 
<script src="js/controller/testController.js"></script> 
<script src="js/controller/SideNavController.js"></script> 
<script src="js/controller/ItemFormController.js"></script> 

<script src="js/controller/sampleController.js"></script> 
<script src="js/controller/ItemController.js"></script> 
+1

这是发生,因为AJAX调用未完成,你的函数返回befote说。以$ scope作为参数发送回调,或者更好地使用Promise – bugwheels94

回答

1

这应该工作:

app.service('StoreService', ['$http', function ($http) { 

this.getStoreNamesService = function() { 
    console.log('getStoreNames called'); 
    return $http.get('http://localhost:8080/storys').then(
     function success(response, status) { 
      console.log(response); 
      return response; 
     }) 
    }; 
}]); 

app.controller('ItemFormController', ['$scope', '$http', '$mdDialog', 'itemService', 'StoreService', function ($scope, $http, $mdDialog, itemService, StoreService) { 
    StoreService.getStoreNamesService().then(function(result){ 
     $scope.storeNames = result; 
    }); 
}]); 

只能分配变量storeNames承诺解决后。你在做的方式,承诺被分配给变量。

另请注意,.success()已弃用。改为使用.then()

0

当使用角度,你最好回来一个承诺,在$ http服务返回一个承诺,你可以将成功回调移至范围:

app.service('StoreService', ['$http', function ($http) { 
    this.getStoreNamesService = function() { 
     return $http.get('http://localhost:8080/storys'); 
    }; 
}]); 

app.controller('ItemFormController', ['$scope', '$http', '$mdDialog', 'itemService', 'StoreService', function ($scope, $http, $mdDialog, itemService, StoreService) { 
    StoreService.getStoreNamesService().then(function (response, status) { 
     $scope.storeNames = response.data; 
    }); 
}]); 

或者您可以创建一个延迟对象,该对象在第在承诺返回,但它只是返回的数据,而不是$ HTTP状态代码等:

app.service('StoreService', ['$http', '$q', function ($http, $q) { 
    this.getStoreNamesService = function() { 
     var deferred = $q.defer(); 
     $http.get('http://localhost:8080/storys').then(function(response, status){ 
      deferred.resolve(response.data); 
     }); 
     return deferred; 
    }; 
}]); 

app.controller('ItemFormController', ['$scope', '$http', '$mdDialog', 'itemService', 'StoreService', function ($scope, $http, $mdDialog, itemService, StoreService) { 
    StoreService.getStoreNamesService().then(function (data) { 
     $scope.storeNames = data; 
    }); 
}]); 

$q

在这两种情况下,范围对象应在控制器内进行填充。

1

夫妇的事情,你弄错了

  1. 您应该返回从服务方法getStoreNames通过$ HTTP方法的承诺目标回报。
  2. 您不应该通过$scope(上下文)来服务修改它。
  3. 您应该使用.then函数从promise对象中获取值。

    app.service('StoreService', ['$http', function ($http) { 
        this.getStoreNamesService = function() { 
        //return promise here 
        return $http.get('http://localhost:8080/storys'); 
        }; 
    }]); 
    

控制器

StoreService.getStoreNamesService($scope).then(function(response){ 
    $scope.storeNames = response.data; 
}); 
相关问题