How to deep watch an array in angularjs? How to deep watch an array in angularjs? angularjs angularjs

How to deep watch an array in angularjs?


You can set the 3rd argument of $watch to true:

$scope.$watch('data', function (newVal, oldVal) { /*...*/ }, true);

See https://docs.angularjs.org/api/ng/type/$rootScope.Scope#$watch

Since Angular 1.1.x you can also use $watchCollection to watch shallow watch (just the "first level" of) the collection.

$scope.$watchCollection('data', function (newVal, oldVal) { /*...*/ });

See https://docs.angularjs.org/api/ng/type/$rootScope.Scope#$watchCollection


There are performance consequences to deep-diving an object in your $watch. Sometimes (for example, when changes are only pushes and pops), you might want to $watch an easily calculated value, such as array.length.


If you're going to watch only one array, you can simply use this bit of code:

$scope.$watch('columns', function() {  // some value in the array has changed }, true); // watching properties

example

But this will not work with multiple arrays:

$scope.$watch('columns + ANOTHER_ARRAY', function() {  // will never be called when things change in columns or ANOTHER_ARRAY}, true);

example

To handle this situation, I usually convert the multiple arrays I want to watch into JSON:

$scope.$watch(function() {   return angular.toJson([$scope.columns, $scope.ANOTHER_ARRAY, ... ]); },function() {  // some value in some array has changed}

example

As @jssebastian pointed out in the comments, JSON.stringify may be preferable to angular.toJson as it can handle members that start with '$' and possible other cases as well.