Как настроить валидацию FormArray - PullRequest
0 голосов
/ 30 апреля 2020

Я создаю реактивную форму с FormArray, который имеет FormGroups внутри. Каждая FormGroup имеет 3 элемента управления, из которых два являются раскрывающимися. Я хотел бы запретить пользователю выбирать один и тот же параметр несколько раз в одном из раскрывающихся списков. Я написал специальный валидатор для достижения этой цели. Кажется, валидатор работает, потому что я ввожу условие if, в котором я возвращаю { 'subCategoryRepetition': true }, но форма остается действительной, массив ошибок элемента управления равен нулю.

Заранее спасибо за любую помощь!

Вот код:

component.ts

initEditUserDetialsForm() {
   this.editUserDetailsForm = this.formBuilder.group({
   ...
      categories: this.formBuilder.array(this.initSavedCategoryArray(this.merchantUserDetails.categories),
      checkSubCategoryRepetition.bind(checkSubCategoryRepetition))
   });
   this.categories = this.editUserDetailsForm.get('categories') as FormArray;
   this.removeCategoryDisabled = this.categories.length < 2;
}

initSavedCategoryArray(categories: CategoryDTO[]): FormGroup[] {
    let formGroupArray: FormGroup[] = [];
    categories.forEach((category, index) => {
        if (this.subCategories.length === 0) {
             this.subCategories.push(category.subCategory.mainCategory.subCategories);
        } else {
             this.subCategories.splice(index, 1, category.subCategory.mainCategory.subCategories);
        }
        formGroupArray.push(
             this.formBuilder.group({
                 mainCategory: [+category.subCategory.mainCategory.mainCategoryId, Validators.required],
                 subCategory: [+category.subCategory.subCategoryId, Validators.required],
                 donationPercentage: [category.donationPercentage, [Validators.required, Validators.min(1), Validators.max(100)]]
             })
         );
     });
     return formGroupArray;
}

custom.validator.ts

export function checkSubCategoryRepetition(formArray: FormArray) {
    let subCategoryIds: number[] = [];
    formArray.controls.forEach((formGroup: FormGroup) => {
        if (subCategoryIds.includes(+formGroup.controls.subCategory.value)) {
            console.log('repetition')
            return { 'subCategoryRepetition': true };
        }
        subCategoryIds.push(+formGroup.controls.subCategory.value);
    });
    return null;
}

1 Ответ

0 голосов
/ 30 апреля 2020

forEach внутри возврата не нарушит выполнение функции. Вот почему вы не работаете, попробуйте увеличить или уменьшить вместо forEach.

Попробуйте это:

export function checkSubCategoryRepetition(formArray: FormArray) {
    let subCategoryIds: number[] = [];
    const groups = formArray.controls;
    for(let i = 0; i < groups.length; i++){
      if (subCategoryIds.includes(+group[i].controls.subCategory.value)) {
            console.log('repetition')
            return { 'subCategoryRepetition': true };
        }
        subCategoryIds.push(+group[i].controls.subCategory.value);
    }
    return null;
}
...