问题
I'm having a hard time making distinctUntilChanged work in this next scenario. I made an asynchronous validator, which uses a service to check if a user exists with the given username. This validator is bound, as a directive, to an input.
class ValidateUniqueUsernameDirective implements AsyncValidator {
constructor(private userService: UserService) {}
validate(
control: AbstractControl
): Promise<ValidationErrors> | Observable<ValidationErrors> {
return control.valueChanges.pipe(
debounceTime(1000),
tap(value => {
debugger;
console.log(value);
}),
distinctUntilChanged(),
switchMap(value => {
return this.userService.getUserByUsername(value).pipe(
map(user => {
const usernameIsAvailable = user === undefined;
return usernameIsAvailable
? null
: { usernameAvailability: { value: control.value } };
})
);
})
);
}
}
Calling the service results in network requests, so I debounced the validation, and, to further lessen them, I tried adding distinctUntilChanged, so that, as user @Kld explains here, user changes within the debounce time back to the previous value wouldn't trigger a new request. However, that's not what's happening. I don't understand what's happening, as the tapped value seems to be the same.
I'm on Angular 6, using RxJS 6. Thank you for your help!
回答1:
Keep it simple:
class ValidateUniqueUsernameDirective implements AsyncValidator {
private lastValue=null;
private lastResult=null;
constructor(private userService: UserService) {}
validate(
control: AbstractControl
): Promise<ValidationErrors> | Observable<ValidationErrors> {
if(lastValue!==control.value){
//do your validation and save result
}else{
// return last result or clear error state
}
}
}
You can also add timeouts to perform request after user stops typing etc.
来源:https://stackoverflow.com/questions/51380618/formcontrol-distinctuntilchanged-not-working