dominic
dominic

Reputation: 405

Angular save http.data to array

I'm trying to save my data comming from a $http request to an array. So I haven't call the api each time I need this list.

For now I have a service looking like this:

angular.module('schwimmfestivalApp')
  .service('httpService', function($http) {
    // AngularJS will instantiate a singleton by calling "new" on this function
    var articleList = [];
    var food = [];


    this.getArticles = function() {
      if (articleList < 1) {
        $http.get('https://www.anmeldung.schwimmfestival.de/server/func/getArtikel.php').then(response => {
          articleList = response.data;
          console.log(articleList);
        });
      }
      return articleList;
    };

    this.getArticleByCategory = function(category) {
      if (food.length < 1) {
        for (var i = 0; i < this.getArticles().length; i++) {
          if (this.getArticles()[i].kategorie == category) {
            food.push(this.getArticles()[i]);
          }
        }
      }

      return food;
    };

    this.getFood = function() {
      console.log('Food: '+ food);
      return this.getArticleByCategory('TN Essen')
    };
  });

I read something about async calls and so my code will go on before the array is filled. Can you help me how to build this service so I can work with this array ?

Thanks in advance

Upvotes: 1

Views: 1199

Answers (1)

Mickael
Mickael

Reputation: 5736

It seems that you try to return a synchronous result with an asynchronous operation.

See this code :

this.getArticles = function() {
    if (articleList < 1) {
        $http.get(url).then(response => {
            articleList = response.data;
        });
    }
    return articleList;
};

When your function is evaluated, you first call an http URL and return an empty array. Then, your http service respond (maybe few secondes later) and you set response.data to articleList. When you do this, the previous empty array you returned before is lost, so the caller will always get the empty array.

What you want to do is handled by ngResource module, but you can simulate this behavior :

this.getArticles = function() {
    if (articleList < 1) {
        $http.get(url).then(response => {
            articleList.push(...response.data);
        });
    }
    return articleList;
};

Note that the best way to solve your problem is probably to return the promise instead of using the hack below :

// Your service :
this.getArticles = function() {
    return $http.get(url).then(response => {
        return response.data;
    });
}

// Your controller :
myService.getArticles().then(response => {
    $scope.articles = response;
});

And if you do not want to call your http method each time, you can use the http cache available with angular :

// Your service :
this.getArticles = function() {
    return $http.get(url, { cache: true }).then(response => {
        return response.data;
    });
}

Upvotes: 3

Related Questions