如何在Angular 2.0中创建自定义验证指令(即验证属性)?

时间:2015-12-04 22:08:23

标签: angular typescript

我正在使用TypeScript为Angular 2.0开发一个小项目。现在根据我的理解,Angular 2.0没有内置的“min”和“max”标签验证器。我了解如何构建自定义验证器并使用FormBuilder附加它但我希望看到如何创建我可以附加在属性上的自定义验证器指令。 HTML看起来像这样:

 <div class="unit">
<div class="label">Age (13 - 120):</div>
<div class="labelTarget">
    <input id="ageFrm" min="13" max="120" type="number" required=""
    ng-control="age" #age="form" [class.error]="!age.valid"
    [(ng-model)]="ageValue"/> {{age.valid}}
</div>
</div>

目前age.valid始终为true,因为minmax没有验证器。我尝试创建自己的。首先是自定义验证功能:

import {Control} from "angular2/angular2";

export class HealthAppCustomValidators {

static min(min: number): Function {
  return (control: Control): {[key: string]: any} => {
    var v: number = Number(control.value);
    console.log("validating " + v + " against " + min);
    return v < min ?
              {"min": {"requiredMin": min, "actualMin": v}} :
              null;
  };
  }

static max(max: number): Function {
  return (control: Control): {[key: string]: any} => {
var v: number = Number(control.value);
    return v > max ?
              {"max": {"requiredMax": max, "actualMax": v}} :
              null;
  };
   }
}

接下来的指令(这是基于检查源代码):

import {Attribute, Control, Directive, forwardRef, Provider, NG_VALIDATORS}   from "angular2/angular2";
import {HealthAppCustomValidators} from "./customValidators";

const MIN_VALIDATOR = new Provider(NG_VALIDATORS, {useExisting: 
forwardRef(() => MinValidator), multi:true});

@Directive({
  selector: '[min][ng-control],[min][ng-form-control],[min][ng-model]',
  providers: [MIN_VALIDATOR]
})
export class MinValidator {

  private _validator: Function;

  constructor(@Attribute("min") min: string) {
    console.log(min);
    this._validator = HealthAppCustomValidators.min(Number(min));
  }
  validate(c: Control): {[key: string]: any} { 
    console.log("validate");
    return this._validator(c); 
 }
}

但是,每当我实际导入指令时,页面加载失败并出现以下错误:

TypeError: validator is not a function
at     http://127.0.0.1:8080/node_modules/angular2/bundles/angular2.dev.js:12990:24
at Array.reduce (native)
at Function.ListWrapper.reduce (http://127.0.0.1:8080/node_modules/angular2/bundles/angular2.dev.js:4206:19)
at http://127.0.0.1:8080/node_modules/angular2/bundles/angular2.dev.js:12989:44
at http://127.0.0.1:8080/node_modules/angular2/bundles/angular2.dev.js:12990:24
at Array.reduce (native)
at Function.ListWrapper.reduce (http://127.0.0.1:8080/node_modules/angular2/bundles/angular2.dev.js:4206:19)
at Control.validator (http://127.0.0.1:8080/node_modules/angular2/bundles/angular2.dev.js:12989:44)
at Control.AbstractControl.updateValidity (http://127.0.0.1:8080/node_modules/angular2/bundles/angular2.dev.js:18871:27)
at  http://127.0.0.1:8080/node_modules/angular2/bundles/angular2.dev.js:14097:14

非常感谢在没有FormBuilder的情况下正确执行此操作的任何帮助:

1 个答案:

答案 0 :(得分:2)

正如杰里米所说,

问题解决了,因为alpha 45他们添加了support for Validator。错误消息可能会令人困惑(您提供的功能,为什么没有工作?)但提交消息提供了线索

  

目前,指令导出验证器的唯一方法是提供一个函数。这使得编写依赖于指令输入的验证器变得很困难。除了支持函数作为验证器之外,还支持实现Validator接口的类。

我无法在alpha 44或更低版本中找到自定义验证器的示例,因此我无法说明它们在那一刻是如何工作的。并且他们最有可能更新了他们的所有示例和工作验证器以使用alpha 45 +。

无论如何,这是通过将angular2升级到最新版本来解决的(顺便提一下,alpha 48是最新的版本,我在评论中说alpha 47,我的不好)虽然它至少需要alpha 45。