Validador esperado para devolver Promise u Observable


104

Estoy tratando de hacer una validación personalizada en Angular 5 pero me enfrento al siguiente error

Expected validator to return Promise or Observable

Solo quiero devolver un error al formulario si el valor no coincide con el requerido, aquí está mi código:

Este es el componente donde esta mi forma

  constructor(fb: FormBuilder, private cadastroService:CadastroService) {
    this.signUp = fb.group({
      "name": ["", Validators.compose([Validators.required, Validators.minLength(2)])],
      "email": ["", Validators.compose([Validators.required, Validators.email])],
      "phone": ["", Validators.compose([Validators.required, Validators.minLength(5)])],
      "cpf": ["", Validators.required, ValidateCpf]
    })     
   }

Este código está en el archivo con la validación que quiero implementar:

import { AbstractControl } from '@angular/forms';

export function ValidateCpf(control: AbstractControl){
    if (control.value == 13445) {
        return {errorCpf: true}
    }
    return null;
}

¿Alguien me puede ayudar? ¿Ese tipo de validación solo funciona con observables o puedo hacerlo sin ser una promesa u observable? Gracias

Respuestas:


309

Significa que debe agregar varios validadores en una matriz

. Ejemplo:

Con error

profileFormGroup = {
  budget: [null, Validators.required, Validators.min(1)]
};

Por encima de uno arroja un error de que el validador devuelva Promesa u Observable

Reparar:

profileFormGroup = {
  budget: [null, [Validators.required, Validators.min(1)]]
};

Explicación:

En la validación de forma reactiva angular realizada mediante el uso de validadores incorporados que se pueden proporcionar en una matriz en la segunda posición, cuando se utilizan varios validadores .

FIELD_KEY: [INITIAL_VALUE, [LIST_OF_VALIDATORS]]


1
Curiosamente, me perdí por completo los corchetes alrededor de los validadores de la respuesta aceptada / popular. Hizo bien en señalar tanto el problema como la solución.
CPHPython

Su primer punto es la respuesta correcta. Esta respuesta debe marcarse correctamente.
Valentino Pereira

1
IMPRESIONANTES MUCHAS GRACIAS
Ravi Rajput

1
¡Qué vergüenza los chicos angulosos! el problema no es observable en absoluto, es una sintaxis de matriz
happyZZR1400

42

Lo siguiente debería funcionar:

  "cpf": ["", [Validators.required, ValidateCpf]]

los argumentos que espera el control de formulario son los siguientes:

constructor(formState: any = null, 
            validatorOrOpts?: ValidatorFn | ValidatorFn[] | AbstractControlOptions | null,
            asyncValidator?: AsyncValidatorFn | AsyncValidatorFn[] | null)

de https://angular.io/api/forms/FormControl


2

No está directamente relacionado con la pregunta del OP, pero obtuve el mismo error en un problema ligeramente diferente. Tenía un validador asíncrono, pero olvidé devolver un Observable (o Promesa) de él.

Aquí estaba mi validador asíncrono original

public availableEmail(formControl: FormControl) {
   if(formControl && formControl.value){
     return this.http.get('')
   }
}

La cuestión es, ¿qué pasa si la declaración if es falsa? No devolvemos nada y obtenemos un error de tiempo de ejecución. Agregué el tipo de retorno (asegurándome de que el IDE se queje si no devolvemos el tipo correcto), y luego lo devuelvo of(true)en caso de que falle la sentencia if.

Aquí está el validador asíncrono actualizado.

public availableEmail(formControl: FormControl): Observable<any> {
   if(formControl && formControl.value){
     return this.http.get('someUrl');
   }
   return of(true);
}

1

Validators.compose () es redundante;

Puede simplemente pasar una matriz. El problema de OP es causado por no envolver los validadores en [] para convertirlos en una matriz, por lo tanto, se asume que minLength () es asíncrono y el mensaje de error resultante.

Espero que esta solución te ayude. Gracias.


Si. Usé Validators.compose ([]). funcionó para mí
Kumaresan Perumal

1

error: userName: ['', [Validators.required, Validators.minLength (3)], forbiddenNameValidator (/ contraseña /)],

ans: userName: ['', [Validators.required, Validators.minLength (3), forbiddenNameValidator (/ contraseña /)]],

los validadores usan solo el segundo parámetro en la matriz interna. no para matriz exterior


“Esto puede no dar respuesta a la pregunta. Agregue una explicación adecuada. Una vez que tenga suficiente reputación, podrá comentar en cualquier publicación; en su lugar, proporcione respuestas que no requieran aclaración por parte del autor de la pregunta ".
Pushkr

1

Si agrega múltiples validadores, entonces necesita agregar otro tercer corchete '[]' y dentro de eso, debe poner sus validadores. Como abajo:

this.yourForm= this.formBuilder.group({
    amount: [null, [Validators.required, Validators.min(1)]],
});

1

Error: "cpf": ["", Validators.required, ValidateCpf]

Reparar: "cpf": ["", [Validators.required, ValidateCpf]]


0

Creo que es bueno aclarar además de la respuesta aceptada que el error ocurre porque cuando se usan formas reactivas para crear un FormControl, después del valor_inicial los siguientes argumentos son, respectivamente, validadores síncronos y validadores asíncronos agrupados en forma de matriz cada uno . P.ej:

myFormGroup = this.fb.group({
    myControl: ['', [ mySyncValidators ], [ myAsyncValidators ] ]
})

Si el control tiene solo uno de ambos, Angular lo acepta como un solo elemento. P.ej:

myFormGroup = this.fb.group({
    myControl: ['', mySyncValidator, myAsyncValidator ]
})

Por lo tanto, al olvidarse de los corchetes para agruparlos, Angular asume que el segundo elemento del validador es parte de los validadores Async y así obtenemos el Expected validator to return Promise or Observable

Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.