admin管理员组

文章数量:1389874

I am trying to initialize my applications services before the controller starts running.

I would have thought that i could achieve this by resolving a promise-returning function first:

va.config(['$routeProvider', function($routeProvider) {
$routeProvider.
    when('/', {templateUrl: '../partials/home.php',   controller: 'VaCtrl',resolve: {
        pp: vac.loadData
    }});
}]);


var  vac = va.controller('VaCtrl',function($scope,$http,$q,packingProvider){
    console.dir(packingProvider.data[2]); 
});


vac.loadData = function($http,$timeout,$q,packingProvider){

   $http.post('../sys/core/fetchPacking.php').then(function(promise){
        packingProvider.data = promise.data;

    });

    var defer = $q.defer();
    $timeout(function(){
        defer.resolve();
    },2000);
    return defer.promise;
};

However, the controller is still loaded before the promise has beenr esolved, resulting in the console yelling

Cannot read property '2' of undefined

at me.

What am i doing wrong?

Edit:

Also, the controller seems to get invoked twice, first time with the undefined pacingProvider.data object, and 2 secons later with everything fine.

I am trying to initialize my applications services before the controller starts running.

I would have thought that i could achieve this by resolving a promise-returning function first:

va.config(['$routeProvider', function($routeProvider) {
$routeProvider.
    when('/', {templateUrl: '../partials/home.php',   controller: 'VaCtrl',resolve: {
        pp: vac.loadData
    }});
}]);


var  vac = va.controller('VaCtrl',function($scope,$http,$q,packingProvider){
    console.dir(packingProvider.data[2]); 
});


vac.loadData = function($http,$timeout,$q,packingProvider){

   $http.post('../sys/core/fetchPacking.php').then(function(promise){
        packingProvider.data = promise.data;

    });

    var defer = $q.defer();
    $timeout(function(){
        defer.resolve();
    },2000);
    return defer.promise;
};

However, the controller is still loaded before the promise has beenr esolved, resulting in the console yelling

Cannot read property '2' of undefined

at me.

What am i doing wrong?

Edit:

Also, the controller seems to get invoked twice, first time with the undefined pacingProvider.data object, and 2 secons later with everything fine.

Share Improve this question edited Oct 10, 2013 at 14:56 user2422960 asked Oct 10, 2013 at 14:43 user2422960user2422960 1,5266 gold badges17 silver badges28 bronze badges
Add a ment  | 

2 Answers 2

Reset to default 3

Instead of using the promise returned by $timeout, you could directly use the promise returned by $http.

Rewrite your loadData fn this way -

vac.loadData = function($http,$timeout,$q,packingProvider){

    var promise = $http.post('../sys/core/fetchPacking.php').then(function(promise){
        packingProvider.data = promise.data;
    });

    return promise;
};

Read the first line in the General Usage section here - $http promise

Also, resolve is a map of dependencies.

resolve - {Object.=} - An optional map of dependencies which should be injected into the controller. If any of these dependencies are promises, the router will wait for them all to be resolved or one to be rejected before the controller is instantiated.

Hence, Angular will automatically expose the map for injection. So, you can do this -

var vac = va.controller('VaCtrl', function($scope, pp){
  // 'pp' is the name of the value in the resolve map for $routeProvider.
  console.dir(pp[2]);
});

NOTE: although this will solve your problem, this answer is probably the right solution.

Services are always initialized before controllers. The problem, as you stated, is that your promise hasn't resulted yet. The best option for that is to stick to the promises.

Instead of exposing the data object, expose the promise and use it:

vac.loadData = function($http,$timeout,$q,packingProvider){
  packingProvider.data = $http.post('../sys/core/fetchPacking.php');
  return packingProvider.data;
};

And in your controller, always attached to the promise, after the first resolval, it will get resolved in the next tick:

var  vac = va.controller('VaCtrl',function($scope,$http,$q,packingProvider){
  packingProvider.data.then(function(value) {
    console.dir(value[2]);
  }); 
});

本文标签: javascriptAngularJSInitialize services before controllerStack Overflow