Jakemmarsh
Jakemmarsh

Reputation: 4661

Update nested object within ng-repeat

I have an array of "activities" stored as $scope.activities. I'm iterating over these in an ng-repeat, accessing nested values and objects along the way.

Some of these nested objects have actions associated with them, such as "liking" and "rsvp'ing", when then makes a call to my backend and should update the value within the ng-repeat. That logic looks like this:

$scope.rsvpToEvent = function(eventId) {
            eventService.rsvp(eventId, $rootScope.user._id).then(function (data) {
                for (var i = 0; i < $scope.activities.length; i++) {
                    if($scope.activities[i].event) {
                        if($scope.activities[i].event._id == data._id) {
                            $scope.activities[i].event = data;
                            break;
                        }
                    }
                }
            },
            function (errorMessage) {
            });
        };

I've also tried passing $index to the function and accessing that activity directly, rather than having the for loop.

This executes successfully and updates the value if I console.log it, but it's not updating the dom or the values of the ng-repeat. I'm using similar logic on another page and it's working fine, so I'm assuming it's due to the fact that I'm trying to update a nested object like this (the other page's logic isn't on nested objects).

Other similar questions have said it's a problem with the scope not getting updated. However, if I wrap this in $scope.$apply() or call it afterwards, I get the "digest already in progress" error. If I try to do a "safe" scope apply by checking the phase, it just doesn't get called at all since a digest is already in progress. Is there another approach to this to ensure that the dom/ng-repeat will get updated?

Upvotes: 2

Views: 714

Answers (1)

Jonathan Rowny
Jonathan Rowny

Reputation: 7588

You can just pass the whole activity into the function if it's easier.

<div ng-repeat="activity in activities" ng-click="rsvpToEvent(activity)"> 

Then you don't need the loop or anything like that.

$scope.rsvpToEvent = function(activity) {
        eventService.rsvp(activity.event._id, $rootScope.user._id).then(function (data) {
           activity.event = data;
        },
        function (errorMessage) {
        });
    };

Upvotes: 2

Related Questions