enguerranws
enguerranws

Reputation: 8233

Angular service calling another service

I'm making a simple Angular app to manage incomes. The incomes come from projects that I store in json (for testing purpose).

So, basically, I use a service in Angular to get this json and I would like to have another service that call Projects service and filter the incomes of each projects.

Here's the code :

facturateApp.service('Projects', function($http){     


 var Projects = {
      async: function() {

        var promise = $http.get('base.json').then(function (response) {            
          return response.data;
        });
        return promise;
      }
    };
    return Projects;


});

facturateApp.service('Incomes', function(Projects){    
    var incomes = []; 
    Projects.async().then(function(d) {
      var projects = d;

      angular.forEach(projects, function(project){

        if(typeof(project.account.accountAmount) == 'number' && project.account.accountAmount > 0){
            var newIncome = {};
            newIncome.projectName = project.projectName;
            newIncome.clientName = project.clientName;
            newIncome.typeIncome = "Accompte";
            newIncome.amount = project.account.amountAccount;
            newIncome.date = project.account.accountDate;
            newIncome.notes = project.account.accountType;
            incomes.push(newIncome);


        }



      });
      angular.forEach(projects, function(project){


        if (typeof(project.total.totalAmount) == 'number' && project.total.totalAmount > 0){
            var newIncome = {};
            newIncome.projectName = project.projectName;
            newIncome.clientName = project.clientName;
            newIncome.typeIncome = "Accompte";
            newIncome.amount = project.total.totalAmount;
            newIncome.date = project.total.totalDate;
            newIncome.notes = project.total.totalType;
            incomes.push(newIncome);


        }


      });

    });
    console.log(incomes); // still returns [];
    return incomes;

});

My problem is that the last log returns an empty array. Actually it works as supposed : incomes is returned before Projects.async().then(function(d) is executed.

But I don't know wait for this function to be executed before returning incomes in a service that call another service...

Any help ?

Upvotes: 4

Views: 4671

Answers (1)

Maxim Shoustin
Maxim Shoustin

Reputation: 77930

This is how async call works: If Incomes service data populates by async way, therefore it must return promise as well.

I would create some method buildAndGetIncomes that will call Projects.async() and when data is fetched -> return new promise to controller:

facturateApp.service('Incomes', function(Projects, $q){

    var self = this;

    var deferred = $q.defer();    
    var incomes = []; 

    self.buildAndGetIncomes = function(){

        Projects.async().then(function(d) {
      var projects = d;

      angular.forEach(projects, function(project){

        if(typeof(project.account.accountAmount) == 'number' && project.account.accountAmount > 0){
            var newIncome = {};
            newIncome.projectName = project.projectName;
            newIncome.clientName = project.clientName;
            newIncome.typeIncome = "Accompte";
            newIncome.amount = project.account.amountAccount;
            newIncome.date = project.account.accountDate;
            newIncome.notes = project.account.accountType;
            incomes.push(newIncome);
        }
      });

      angular.forEach(projects, function(project){


        if (typeof(project.total.totalAmount) == 'number' && project.total.totalAmount > 0){
            var newIncome = {};
            newIncome.projectName = project.projectName;
            newIncome.clientName = project.clientName;
            newIncome.typeIncome = "Accompte";
            newIncome.amount = project.total.totalAmount;
            newIncome.date = project.total.totalDate;
            newIncome.notes = project.total.totalType;
            incomes.push(newIncome);
        }
      });

     deferred.resolve(incomes);      
    });

    return deferred.promise;    
    };    
});

and from controller we call :

Incomes.buildAndGetIncomes().then(function(incomes) {
   // ...
}, function(error) {
  // ..
});

Upvotes: 3

Related Questions