Angular自定义验证器未触发,如何正确注册自定义验证器?
解决自定义验证器未被调用的问题
问题根源
你用的是模板驱动表单,但自定义验证器仅写成了函数,没有封装成Angular指令,框架无法识别模板中的notInSet属性;同时模板里的绑定方式也错误,传递的是字符串而非目标集合。按以下步骤修复:
1. 将验证器封装为指令
修改你的验证器文件,把函数包装成实现Validator接口的指令,让Angular能识别模板中的验证器属性:
import { AbstractControl, ValidationErrors, ValidatorFn, Validator, NG_VALIDATORS, Directive, Input } from "@angular/forms"; // 保留原验证器逻辑 export function notInSet(theSet: Set<string>): ValidatorFn { return (control: AbstractControl): ValidationErrors | null => { const val = control.value; return theSet.has(val) ? { InSet: true } : null; } } // 新增验证器指令 @Directive({ selector: '[notInSet]', providers: [{ provide: NG_VALIDATORS, useExisting: NotInSetValidatorDirective, multi: true }] }) export class NotInSetValidatorDirective implements Validator { @Input('notInSet') targetSet!: Set<string>; validate(control: AbstractControl): ValidationErrors | null { return notInSet(this.targetSet)(control); } }
2. 在模块中声明指令
打开组件所属的模块(比如AppModule),把指令添加到declarations数组,同时确保引入FormsModule(模板驱动表单必备):
import { NgModule } from '@angular/core'; import { BrowserModule } from '@angular/platform-browser'; import { FormsModule } from '@angular/forms'; import { AppComponent } from './app.component'; import { NotInSetValidatorDirective } from './path-to-your-validator-file'; // 替换为你的验证器文件路径 @NgModule({ declarations: [ AppComponent, NotInSetValidatorDirective // 注册验证器指令 ], imports: [ BrowserModule, FormsModule // 必须引入此模块 ], providers: [], bootstrap: [AppComponent] }) export class AppModule { }
3. 修正模板绑定
把模板里的字符串绑定改成属性绑定,传递实际的existingNames集合,同时优化错误判断逻辑:
<form #myForm novalidate> <input pInputText [(ngModel)]="name" name="name" [notInSet]="existingNames" #theName="ngModel"/> <div *ngIf="theName.hasError('InSet')" class="text-error"> Please provide a unique name for this api </div> </form>
内容的提问来源于stack exchange,提问作者Fraser Orr
相关产品推荐
相关产品推荐

