访问父数组以在 ngMessages 中进行唯一键验证
Accessing parent array for unique key validation in ngMessages
对于键值对数组 ({ key: 'keyName', value: 'value' }
),我需要确保键在列表中是唯一的。我想利用 ngMessages
来显示消息。我将 Angular Material and ES6 与转译器一起使用,但这不应该影响问题的实质。
根本问题是我不知道如何在 $validators
管道中优雅地访问数组的 other 项。这是我当前自定义验证器的基本示例:
someModel.directive('unique', () => {
return {
restrict: 'A',
require: 'ngModel',
link: ($scope, elem, attrs, ngModel) => {
ngModel.$validators.unique = (currentKey) => {
const otherItems = scope.$parent.$ctrl.items.slice(); // <== KLUDGE
otherItems.splice($scope.$index, 1); // ignore current item
return !otherItems.some(item => item.key === currentKey);
};
},
};
});
视图模板如下所示:
<md-list ng-form="$ctrl.keyValuePairs">
<md-list-item ng-repeat="item in $ctrl.items track by $index">
<!-- key -->
<md-input-container>
<input type="text" name="key_{{::$index}}" ng-model="item.key" required unique />
<div ng-messages="$ctrl.keyValuePairs['key_'+$index].$error">
<div ng-message="required">Required</div>
<div ng-message="unique">Must be unique</div>
</div>
</md-input-container>
<!-- value -->
<md-input-container>
<input type="text" name="val_{{::$index}}" ng-model="item.value" ng-required="item.key" />
<div ng-messages="$ctrl.keyValuePairs['val_'+$index].$error">
<div ng-message="required">Required if key is present</div>
</div>
</md-input-container>
</md-list-item>
</md-list>
它 有效 ,但我不喜欢必须 1) 知道集合的名称 (items
),以及 2) 通过爬上去访问它通过 $scope
的父级。
simple yet effective解决方案是只传入父数组。
someModel.directive('unique', () => {
return {
restrict: 'A',
require: 'ngModel',
link: ($scope, elem, attrs, ngModel) => {
ngModel.$validators.unique = (currentKey) => {
const otherItems = $scope.$eval(attrs.unique); // <== FIX
otherItems.splice($scope.$index, 1); // ignore current item
return !otherItems.some(item => item.key === currentKey);
};
},
};
});
缩写HTML:
<input type="text" name="key_{{::$index}}" ng-model="item.key" unique="{{$ctrl.items}}" />
h/t @msarchet
对于键值对数组 ({ key: 'keyName', value: 'value' }
),我需要确保键在列表中是唯一的。我想利用 ngMessages
来显示消息。我将 Angular Material and ES6 与转译器一起使用,但这不应该影响问题的实质。
根本问题是我不知道如何在 $validators
管道中优雅地访问数组的 other 项。这是我当前自定义验证器的基本示例:
someModel.directive('unique', () => {
return {
restrict: 'A',
require: 'ngModel',
link: ($scope, elem, attrs, ngModel) => {
ngModel.$validators.unique = (currentKey) => {
const otherItems = scope.$parent.$ctrl.items.slice(); // <== KLUDGE
otherItems.splice($scope.$index, 1); // ignore current item
return !otherItems.some(item => item.key === currentKey);
};
},
};
});
视图模板如下所示:
<md-list ng-form="$ctrl.keyValuePairs">
<md-list-item ng-repeat="item in $ctrl.items track by $index">
<!-- key -->
<md-input-container>
<input type="text" name="key_{{::$index}}" ng-model="item.key" required unique />
<div ng-messages="$ctrl.keyValuePairs['key_'+$index].$error">
<div ng-message="required">Required</div>
<div ng-message="unique">Must be unique</div>
</div>
</md-input-container>
<!-- value -->
<md-input-container>
<input type="text" name="val_{{::$index}}" ng-model="item.value" ng-required="item.key" />
<div ng-messages="$ctrl.keyValuePairs['val_'+$index].$error">
<div ng-message="required">Required if key is present</div>
</div>
</md-input-container>
</md-list-item>
</md-list>
它 有效 ,但我不喜欢必须 1) 知道集合的名称 (items
),以及 2) 通过爬上去访问它通过 $scope
的父级。
simple yet effective解决方案是只传入父数组。
someModel.directive('unique', () => {
return {
restrict: 'A',
require: 'ngModel',
link: ($scope, elem, attrs, ngModel) => {
ngModel.$validators.unique = (currentKey) => {
const otherItems = $scope.$eval(attrs.unique); // <== FIX
otherItems.splice($scope.$index, 1); // ignore current item
return !otherItems.some(item => item.key === currentKey);
};
},
};
});
缩写HTML:
<input type="text" name="key_{{::$index}}" ng-model="item.key" unique="{{$ctrl.items}}" />
h/t @msarchet