Loading json data with AngularJS factory

I have a huge json object in my controller that I would like to pass into a separate file. While I am doing this:

myApp.controller('smController', ['$scope', function($scope) {
  ...
  var stadtmobilRates = {
    classic: {
      A: {
        night: 0,
        hour: 1.4,
        day: 21,
        week: 125,
        km000: 0.2,
        km101: 0.18,
        km701: 0.18
      },
      ...
    }
  };

      

I used factory and promises as described here on Stackoverflow:

myApp.factory('stadtMobilRates', function($http) {
  var promise = null;

  return function() {
    if (promise) {
      // If we've already asked for this data once,
      // return the promise that already exists.
      return promise;
    } else {
      promise = $http.get('stadtmobilRates.json');
      return promise;
    }
  };
});

myApp.controller('smController', ['$scope', function($scope, stadtMobilRates) {
  var stadtmobilRates = null;
  stadtMobilRates().success(function(data) {
    stadtmobilRates = data;
  });

      

Now I am getting TypeError: undefined is not a function

in line stadtMobilRates().success(function(data) {

. Why is stadtMobilRates

n't the factory accepted even though I injected it into the controller?

Edit # 1: I added the factory name to the array as suggested by shrimp.

myApp.controller('smController', ['$scope', 'stadtMobilRates', function($scope, stadtMobilRates) {
  var stadtmobilRates = null;
  stadtMobilRates().success(function(data) {
    stadtmobilRates = data;
  });

  console.log(stadtmobilRates);

      

However stadtmobilRates null

?

Edit # 2: I created a simplified version of my application in Plunker . Well it works. In a full app I work with different routes where stadtMobilRates

it still remains null

. I am unable to create Plunker from complete routes app. So here's the complete code on GitHub . The code above is from line 159 . I guess it has something to do with my routes?

+3


source to share


1 answer


You forgot to pass the factory name in the array. Typically, you pass in an array whose elements are made up of a list of strings followed by the function itself. Don't forget to store the array according to the parameters in the function declaration. Thus, the injector knows what services to inject into the function.

myApp.controller('smController', ['$scope', 'stadtMobilRates', function($scope, stadtMobilRates) {

      

EDIT

This is how I would do it ... When using routes I like to use resolve

that the data is loaded once and saved. So in $routeProvider

I would change the smController part to the following ...

 when('/sm', {
      templateUrl: 'partials/sm.html',
      controller: 'smController',
      resolve:{
              load:function(stadtMobilRates){
                  return stadtMobilRates.LoadData();
          }
    }).

      



I also changed the factory

myApp.factory('stadtMobilRates', function ($q, $http) {
var mobilRates = null;

function LoadData() {
    var defer = $q.defer();
    $http.get('stadtmobilRates.json').success(function (data) {
        mobilRates = data;
        defer.resolve();
    });
    return defer.promise;
}

return {
    GetData: function () { return mobilRates ; },
    LoadData:LoadData
}
});

      

So, before this route is loaded, it will call a function LoadData

in the factory. Once the data is loaded, it resolves the promise, so this function LoadData

will only be called once. Once the promise is resolved, it will continue and load the view.

So now in your controller, when you want to get data, all you have to do is call the function GetData

myApp.controller('smController', ['$scope', 'stadtMobilRates', function($scope, stadtMobilRates) 
{
     var stadtmobilRates = stadtMobilRates.GetData();
});

      

+6


source







All Articles