Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/angular/32.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Angular 如何向自定义角度验证器提供异步参数_Angular_Typescript_Validation_Asynchronous - Fatal编程技术网

Angular 如何向自定义角度验证器提供异步参数

Angular 如何向自定义角度验证器提供异步参数,angular,typescript,validation,asynchronous,Angular,Typescript,Validation,Asynchronous,我正在设置表单验证程序,其中多个字段的最小值和最大值通过单个API获取。当尝试将其中一个异步值传递给自定义验证器参数时,应用程序崩溃,但当该值为硬编码时,应用程序将正常工作 传递异步值时收到的错误如下: 错误:formGroup需要一个formGroup实例。请把一个传进来 file.ts: export class PackageDimensionValidator { static validSize(min: number, max: number): ValidatorFn {

我正在设置表单验证程序,其中多个字段的最小值和最大值通过单个API获取。当尝试将其中一个异步值传递给自定义验证器参数时,应用程序崩溃,但当该值为硬编码时,应用程序将正常工作

传递异步值时收到的错误如下:

错误:formGroup需要一个formGroup实例。请把一个传进来

file.ts:

export class PackageDimensionValidator {
   static validSize(min: number, max: number): ValidatorFn {
      return (control: AbstractControl): { [key: string]: boolean } | null => {
      if (control.value !== undefined && (isNaN(control.value) || control.value < min || control.value > max)) {
        return { 'exceedRange': true };
      }
      return null;
    };
   }
}

// ... 

ngOnInit() {
   // Retrieve maximum package dimensions for input data validation.
   this.shipmentService.getMaxPackageSize()
      .subscribe(result => {
         this.packageRestrictions = new PackageRestrictions(result);
         console.dir(this.packageRestrictions);
         this.setupPackageValidators();
   });
}

setupPackageValidators() {
   const maxWidth = this.packageRestrictions.maxWidth; // Crashes on Async value.
   // const maxWidth = 5; // Works on hard-coded value.

   // Setup package dimension validators.
   this.packageSizeForm = this.formBuilder.group({
      maxWidth: new FormControl('', Validators.compose([
         PackageDimensionValidator.validSize(null, maxWidth),
         // Other validators ...
      ]))
   });
}
<form [formGroup]="packageSizeForm">
   <input formControlName="maxWidth" type="text" required />
</form>
导出类PackageDimensionValidator{
静态有效大小(最小值:编号,最大值:编号):验证器fn{
return(control:AbstractControl):{[key:string]:boolean}| null=>{
if(control.value!==未定义&(isNaN(control.value)| | control.valuemax)){
返回{'exceedRange':true};
}
返回null;
};
}
}
// ... 
恩戈尼尼特(){
//检索输入数据验证的最大包维度。
this.shipmentService.getMaxPackageSize()
.订阅(结果=>{
this.packageRestrictions=新的packageRestrictions(结果);
console.dir(此包限制);
这个.setupPackageValidators();
});
}
setupPackageValidators(){
const maxWidth=this.packageRestrictions.maxWidth;//异步值崩溃。
//const maxWidth=5;//用于硬编码值。
//设置包维度验证程序。
this.packageSizeForm=this.formBuilder.group({
maxWidth:new FormControl(“”,Validators.compose([
PackageDimensionValidator.validSize(null,maxWidth),
//其他验证器。。。
]))
});
}
file.html:

export class PackageDimensionValidator {
   static validSize(min: number, max: number): ValidatorFn {
      return (control: AbstractControl): { [key: string]: boolean } | null => {
      if (control.value !== undefined && (isNaN(control.value) || control.value < min || control.value > max)) {
        return { 'exceedRange': true };
      }
      return null;
    };
   }
}

// ... 

ngOnInit() {
   // Retrieve maximum package dimensions for input data validation.
   this.shipmentService.getMaxPackageSize()
      .subscribe(result => {
         this.packageRestrictions = new PackageRestrictions(result);
         console.dir(this.packageRestrictions);
         this.setupPackageValidators();
   });
}

setupPackageValidators() {
   const maxWidth = this.packageRestrictions.maxWidth; // Crashes on Async value.
   // const maxWidth = 5; // Works on hard-coded value.

   // Setup package dimension validators.
   this.packageSizeForm = this.formBuilder.group({
      maxWidth: new FormControl('', Validators.compose([
         PackageDimensionValidator.validSize(null, maxWidth),
         // Other validators ...
      ]))
   });
}
<form [formGroup]="packageSizeForm">
   <input formControlName="maxWidth" type="text" required />
</form>


理想情况下,将有多个
formControls
,每个控件都具有唯一的最小值和最大值,所有控件都由单个API同时获取。其思想过程是调用该API,在本地存储其结果,然后构建表单验证器。我现在质疑这个序列的顺序。

您可能需要使用异步验证器

asyncValidator
作为可选的第三个参数传递给
FormControl
构造函数:

class FormControl {
  ...
  constructor(
    formState: any = null,
    validatorOrOpts?: ValidatorFn | AbstractControlOptions | ValidatorFn[],
    asyncValidator?: AsyncValidatorFn | AsyncValidatorFn[]
  )
  ...
}

我不完全确定您收到的错误消息是否反映了您描述的问题。我首先在您的ngOnInit中启动
packageSizeForm
,不使用验证器:

ngOnInit() {
   this.packageSizeForm = new FormGroup({
          maxWidth: new FormControl('');
   });
   this.shipmentService.getMaxPackageSize()
      .subscribe(result => {
         this.packageRestrictions = new PackageRestrictions(result);
         console.dir(this.packageRestrictions);
         this.setupPackageValidators();
   });
}
然后在
this.setupPackageValidators()中设置验证器


我的验证器本身并没有执行异步任务,所以我觉得使用异步验证器是不正确的。问题是,我碰巧向它传递了一个异步参数。我认为更好的方法是在构建验证器之前等待API解析。我的方法是错误的还是逻辑错误?html中的
[formGroup]
指令需要创建formGroup实例。当视图初始化导致您等待
this.shipmentService.getMaxPackageSize()
解析时,您尚未创建它。我建议将此调用移动到异步验证器,并在nginit中同步创建表单。我知道在
ngOnInit
中初始化
FormGroup
可能是渲染所必需的,并且我无法在同一时刻分配maxWidth。我只是不知道如何区分这两个过程。这正是我需要的。