4

I have a directive that reacts to an Blur event fired from an input element, and then ultimately results in a call to the Angular $http service to make an appropriate HTTP request.

The $http service is being called correctly and generating the expected promise, however the actual HTTP request does not get made immediately. It is only triggered later after making other kinds of DOM interactions.

Why are the request not being made immediately? And how can I force them to be made immediately?

Angular v1.1.5

3 Answers 3

19

The reason

I eventually found the answer in the issues on GitHub (https://github.com/angular/angular.js/issues/2442):

v1.1.4... changed the way $http worked so that it was scheduled on nextTick instead of firing immediately. This means that if your $http is scheduled from something that doesn't cause a $digest to fire then your request won't be sent. You can verify that this is the behavior you're seeing by clicking on the page a few times (anywhere) and you should see your request go out.

A Solution

As the post suggested I triggered a $digest cycle, which caused my $http generated requests to be immediately fired.

scope.$apply();
Sign up to request clarification or add additional context in comments.

1 Comment

You should accept your own answer. This was happening to me as well, thanks!
2

In addition to the other reasons above ... If you used ...injector.get("$http") manually from code outside of angular, then you may have retrieved the $http service from the wrong injector instance.

This is what happened to us and it took a very long time to figure out. In this case the request is not sent even if the $http is wrapped within $apply.

Comments

1

This situation occurs when an event is triggered "outside" Angular, and Angular knows nothing about it.

The blur event is coming from the DOM, or maybe you have an AJAX callback that triggers an update. You will notice that nothing happens until you interact with the application in some way that causes Angular to wake up. George Thomas' answer is correct - you must poke the Angular $scope to make it aware of the event - but according to the Angular developers a more correct way is to wrap your code in the $apply() function like this:

$("#myElement").blur(function() {
  $scope.$apply(function() {
    $http({method: 'GET', url: '/someUrl'});
  });
});

This way, errors in the code are correctly propogated to Angular.

I found this information in an extremely good presentation on directives by Misko Hevery - the developer who created them: http://www.youtube.com/watch?v=WqmeI5fZcho. If you've been using Angular on a project for a while, but aren't quite sure what's really going on, this video is 50 minutes of your life well spent!

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.