问题
I have a object with categories, inside this object there is a object called items which contain objects with items.
now i want to do in a repeat to display the items like this:
<div ng-if="delivery_items" ng-repeat="(k, cat_item) in delivery_items">
<div class="item-cat-header">
<i class="fa fa-arrow-circle-right"></i> {{cat_item.item_category_name}}
</div>
<div class="item-rule" ng-repeat="item in cat_item.items">
<div class="item-info">
{{item.item_name}}
<p class="item-desc"></p>
</div>
<div class="item-price">
€
</div>
</div>
</div>
but for some reason it shows a error
Error: [ngRepeat:dupes] Duplicates in a repeater are not allowed. Use 'track by' expression to specify unique keys. Repeater: item in cat_item.items, Duplicate key: undefined:undefined, Duplicate value: undefined
the json object looks like this:

what am i doing wrong?
EDIT:
the array creation part:
//set menu list
if ($scope.categories_norm) {
$scope.delivery_items = {};
//get categories
angular.forEach(data.item_categories.normal_categories, function (v, k) {
//push categories
$scope.delivery_items[v.item_category_id] = v; //create empty catagory object
$scope.delivery_items[v.item_category_id]['items'] = [];
if ($scope.items) {
angular.forEach($scope.items, function (val, key) {
if (v.item_category_id == val.item_category_id) {
$scope.delivery_items[v.item_category_id]['items'][key] = val;
}
});
}
});
}
回答1:
Your issue is because of holes in the array (sparse array). I can see your first item
array is of length 39 but you really do not have 39 items in the array. It is quite visible by looking at your snapshot (0, 9, 16,22 etc..). ng-repeat
attaches a tracking id by default (unless you set a track by
) to each repeated item as a $hashkey
property, but when one of the items is not available it is literally undefined
(items[1]
) so that (undefined
) will be set as key, but then again it gets another undefined item (items[2]
) so it throws duplicate in repeater error. You can quick fix by doing a track by $index
.
<div class="item-rule" ng-repeat="item in cat_item.items track by $index">
But now it will show empty item-rule
sections. So you should look to fix the array itself by cleaning up or setting the values properly. Check your array creation part.
Update after array creation part was added into the question
Your problem lies in the second loop (see comment before if
).
angular.forEach($scope.items, function (val, key) {
//If the condition here is not met you basically skip that index in the array
//Remember key represents index of the original array you are iterating through
if (v.item_category_id == val.item_category_id) {
$scope.delivery_items[v.item_category_id]['items'][key] = val;
}
});
change
$scope.delivery_items[v.item_category_id]['items'][key] = val;
to use array.push
$scope.delivery_items[v.item_category_id]['items'].push(val);
回答2:
<div class="item-rule" ng-repeat="(key, item) in cat_item.items track by key" ng-if="item">
That is, if for some reason you have to work your way around a sparsed array in angular instead of reindexing it in the first place.
来源:https://stackoverflow.com/questions/30517500/ng-repeat-in-repeat-does-not-repeat-nested-object-angular