Adam Zerner
Adam Zerner

Reputation: 19228

At what point does $http trigger the digest cycle to start?

My hypothesis is that it happens after the .success callback finishes executing. As opposed to


Consider this code:

notes.service.js

angular.module('notes').service('notes', ['$http', 
function($http) {
    var obj = {};

    this.getNotes = function() {
        $http.get('/notes').success(function(notesResponse) {
            obj.notes = notesResponse;
        });
        return obj;
    };
}]);

notes.controller.js

angular.module('notes').controller('NotesCtrl', ['notes', 
function(notes) {
    /* 
        $scope.$$watchers = [
            'notesCtrl.obj', cb
        ];
    */

    this.obj = notes.getNotes();    
}]);

list.html

<div class='page-header'>
    <h1>List of Notes</h1>
</div>

<ul>
    <li ng-repeat='note in notesCtrl.obj.notes track by note.id'>{{note | json}}</li>
</ul>

Imagine that the GET request takes an hour before it sends back a response.

Is this correct?

Also, does $http trigger $digest or $apply? If it triggers $digest, how does it know which $scope to call it on? For example, the $http in the service isn't associated with a $scope (is it?).

Upvotes: 3

Views: 1016

Answers (2)

squiroid
squiroid

Reputation: 14027

I looked into the docs(Line:1083) of $http Find this line below

/**
* Callback registered to $httpBackend():
* - caches the response if desired
* - resolves the raw $http promise
* - calls $apply
*/

It says callback is registered to $httpBackend() which do the following things in the order cache the response if desired(depending on you provide true in $http and it will cache it).Then it resolves the $httppromise which means call to success or error (it can also be then()) depending on the response.Then it finally call $apply for digest cycle.

And as far as i come to know from documentation $http service bind with $rootScope.

And if you are thinking then how inside sucess $apply is throwing an error if $apply is starting after it then the answer is in doc itself $rootScope.$applyAsync which is running always and resolve the httppromise and then then after this $rootScope.$apply() runs.(Line:1102-1106)

Hope this clears your doubt.

Upvotes: 0

Michal Charemza
Michal Charemza

Reputation: 27012

It's amost correct: the success callback is in fact called during the digest cycle. You can see this if you try the following

$http.get('test.json').success(function(result) {
  $scope.$apply();
});

Then (assuming the GET to test.json is a success), Angular will throw an error that can be seen in the console:

 Error: [$rootScope:inprog] $digest already in progress

This can be seen at http://plnkr.co/edit/wj4z1hDRXtK2GJnrkKuV?p=preview

Also, does $http trigger $digest or $apply?

$apply, as it indeed doesn't know which scopes need to be checked, it triggers a global digest to check them all.

Upvotes: 2

Related Questions