角2自定义验证(模板形式)验证
我想实现一个自定义验证程序,检查是否存在键控用户名。但是,我遇到了一个控制总是无效的问题。我已经确认webApi正在返回正确的值,并且验证器函数正在进入正确的返回语句。角2自定义验证(模板形式)验证
我的自定义验证如下:
import { Directive, forwardRef } from '@angular/core';
import { AbstractControl, ValidatorFn, NG_VALIDATORS, Validator, FormControl } from '@angular/forms';
import { UsersService } from '../_services/index';
import { Users } from '../admin/models/users';
function validateUserNameAvailableFactory(userService: UsersService): ValidatorFn {
return (async (c: AbstractControl) => {
var user: Users;
userService.getUserByName(c.value)
.do(u => user = u)
.subscribe(
data => {
console.log("User " + user)
if (user) {
console.log("Username was found");
return {
usernameAvailable: {
valid: false
}
}
}
else {
console.log("Username was not found");
return null;
}
},
error => {
console.log("Username was not found");
return null;
})
})
}
@Directive({
selector: '[usernameAvailable][ngModel]',
providers: [
{ provide: NG_VALIDATORS, useExisting: forwardRef(() => UserNameAvailableValidator), multi: true }
]
})
export class UserNameAvailableValidator implements Validator {
validator: ValidatorFn;
constructor(private usersService: UsersService) {
}
ngOnInit() {
this.validator = validateUserNameAvailableFactory(this.usersService);
}
validate(c: FormControl) {
console.log(this.validator(c));
return this.validator(c);
}
}
而且形式如下:
<form #userForm="ngForm" (ngSubmit)="onSubmit()" novalidate>
<div class="form form-group col-md-12">
<label for="UserName">User Name</label>
<input type="text" class="form-control" id="UserName"
required usernameAvailable maxlength="50"
name="UserName" [(ngModel)]="user.userName"
#UserName="ngModel" />
<div [hidden]="UserName.valid || UserName.pristine" class="alert alert-danger">
<p *ngIf="UserName.errors.required">Username is required</p>
<p *ngIf="UserName.errors.usernameAvailable">Username is not available</p>
<p *ngIf="UserName.errors.maxlength">Username is too long</p>
</div>
<!--<div [hidden]="UserName.valid || UserName.pristine" class="alert alert-danger">Username is Required</div>-->
</div>
</form>
我跟了几个教程证明这种结构的作品,所以我假设我可能搞乱从验证器功能中返回。
另外,有没有一种方法,我可以提出的错误列表(我曾尝试使用li与ngFor,但我从中得不到什么)?
申报表true
应该是:
{usernameAvailable: true}
false
或null
。
我正在玩耍看看我是否已经搞清楚了回报,并意识到它与尝试从订阅内返回值有关。如果我对返回语句进行硬编码并对服务调用发表评论,则会错误地填充错误。我只是没有理解才知道我在订阅活动中做错了什么。 –
所以,使用.subscribe我的方式有问题。我发现了一个解决方案通过以下2个链接:
https://netbasal.com/angular-2-forms-create-async-validator-directive-dd3fd026cb45 http://cuppalabs.github.io/tutorials/how-to-implement-angular2-form-validations/
现在,我的验证程序是这样的:
import { Directive, forwardRef } from '@angular/core';
import { AbstractControl, AsyncValidatorFn, ValidatorFn, NG_VALIDATORS, NG_ASYNC_VALIDATORS, Validator, FormControl } from '@angular/forms';
import { Observable } from "rxjs/Rx";
import { UsersService } from '../_services/index';
import { Users } from '../admin/models/users';
@Directive({
selector: "[usernameAvailable][ngModel], [usernameAvailable][formControlName]",
providers: [
{
provide: NG_ASYNC_VALIDATORS,
useExisting: forwardRef(() => UserNameAvailableValidator), multi: true
}
]
})
export class UserNameAvailableValidator implements Validator {
constructor(private usersService: UsersService) {
}
validate(c: AbstractControl): Promise<{ [key: string]: any }> | Observable<{ [key: string]: any }> {
return this.validateUserNameAvailableFactory(c.value);
}
validateUserNameAvailableFactory(username: string) {
return new Promise(resolve => {
this.usersService.getUserByName(username)
.subscribe(
data => {
resolve({
usernameAvailable: true
})
},
error => {
resolve(null);
})
})
}
}
这是现在的工作。但是,现在我有一个问题,在异步验证程序正在运行时,控件暂时使自身失效。
也许保持字段无效,直到异步调用完成? –
https://angular.io/guide/form-validation#custom-validation和https://stackoverflow.com/documentation/angular2/6284/angular2-custom-validations#t=201707261704537121485 – JGFMK