1

I have the problem that my function doesn't wait for the response of http request and go further. I know that I can use promise to wait but I don't understand the concept.

I have a data service that have all http request :

function GetGroupIdFromBakery(bakeryId, successCallback, errorCallback) {
        $http.get(service.baseUrl + "BakeriesGroup/Bakeries/" + bakeryId)
            .then(function (result) { successCallback(result.data); }, errorCallback);
    }

From another service, I call the data service :

var hasPermission = function (permission, params) {
            permissionRoute = permission;
            setIdEntity(params);
            for (var i = 0; i < permissions.length; i++) {
                if (permissionRoute.Name === permissions[i].Name) {
                    if (permissions[i].Scope == "System")
                        return true;
                    else if (permissions[i].Scope == permissionRoute.Scope && permissions[i].IdEntity == permissionRoute.IdEntity) 
                        return true;
                }
            }
            return false;
        }



var setIdEntity = function (params) {
            if (permissionRoute.Scope == "Bakery")
                permissionRoute.IdEntity = parseInt(params.bakeryId);
            else if (permissionRoute.Scope == "Group") {
                if (params.bakeriesGroupId)
                    permissionRoute.IdEntity = parseInt(params.bakeriesGroupId);
                else {
                    getGroupOfBakery(parseInt(params.bakeryId));   
                }

                console.log(permissionRoute.IdEntity);
            }
        }

var getGroupOfBakery = function (bakeryId) {
            DataService.GetGroupIdFromBakery(bakeryId, function (groupId) {
                permissionRoute.IdEntity = groupId;
            }, function (error) {
                console.error("something went wrong while getting bakery");
                alert("Une erreur s'est produite lors de la récupération de la boulangerie");
            });

        }

I must wait for the response of DataService.GetGroupIdFromBakery(). With this code, permission.EntityId is undefined when I call getGroupByBakery().

Can somebody help me, please?

3
  • 2
    You can't do that. You need to use promises. Commented Jul 25, 2017 at 14:24
  • 1
    Is it possible to use callback? Commented Jul 26, 2017 at 8:05
  • Maybe I am wrong, but, to me, a promise is a callback. I am sure that they are the same under the hood. Anyway, you say "I know that I can use promise to wait but I don't understand the concept"; nor did i at first, then I started thinking of them as fucntionallly identical, and it clciked. Purists may well disagree ;-) but, if it helps you, think of pronises as callbacks Commented Nov 15, 2020 at 11:12

3 Answers 3

1

You can add a watcher to your response data. I think it is EntityId in your case. It get executed as soon as your EntityId changes. After getting the response data you can call the function, this time EntityId will not be undefined.

$scope.$watch(function () {
            return EntityId  
        }, function (newEntityId) {
            if(newEntityId != undefined {
                // now you can call your function
             }
            }
        }, true);
Sign up to request clarification or add additional context in comments.

Comments

0

Exactly, you have to use promises, because $http module is asynchronus. I built a service for that:

.service('RequestService', function($q, $http){
  return {
    call: function(htmlOptions){
      var d = $q.defer();
      var promise = d.promise;
      $http(htmlOptions)
        .then(function(response){
          d.resolve(response.data);
         }, function(response){
          d.reject(response.data);
        });
      promise.success = function(fn) {
       promise.then(fn);
        return promise;
      };
      promise.error = function(fn) {
       promise.then(null, fn);
       return promise;
      };
      return promise;
    }
  }
})

And then:

RequestService.call({
   method: 'POST' //GET, DELETE ...
   data: data,
   url: 'http://someurl.com/'
  });

1 Comment

Just be aware, this is the deferred promise antipattern. See stackoverflow.com/a/30757201/4735725
0

you should use defer. create a new defer object in GetGroupIdFromBakery method,in success part resolve the defer and in failed part reject it, and return the promise of defer at the end.

function GetGroupIdFromBakery(bakeryId, successCallback, errorCallback, $q) {
    var defer = $q.defer();
    $http.get(service.baseUrl + "BakeriesGroup/Bakeries/" + bakeryId)
        .then(function (result) { 
           successCallback(result.data);
              defer.resolve(result.data); 
           }, function(){
              defer.reject(); 
           });
   return defer.promise;
}

This successfully return you a promise that you can call with .then() and receive as a value in the service where you need to have the data of GetGroupIdFromBakery.

getGroupOfBakery(parseInt(params.bakeryId), $q).then(function(data){
    // here you have data
})

Be aware you should inject $q, here I supposed that we have $q in service and I passed it to method.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.