1

New to Angular and trying to add a custom email validator that will go to my server and check if the email address is already in use.

But can't seem to get the error message displaying on form. Here is how I'm testing it before I attempt to hit the server.

FYI - the "emailMatchValidator()" is called but I can't get it to display any kind of error message on the form!

Maybe I should try something other than .touched!

ngOnInit() {
    this.createRegisterForm();
  }

createRegisterForm() {
  this.registerForm = this.fb.group({
    gender: ['male'],
    email: ['', [Validators.required, Validators.email]],
    username: ['', [Validators.required, Validators.minLength(4), Validators.maxLength(10)]],
    knownAs: ['', Validators.required],
    dateOfBirth: [null, Validators.required],
    city: ['', Validators.required],
    country: ['', Validators.required],
    password: ['', [Validators.required, Validators.minLength(4), Validators.maxLength(8)]],
    confirmPassword: ['', Validators.required]
  }, {
    validator: [this.passwordMatchValidator, this.emailMatchValidator]
  });
}

emailMatchValidator(g: FormGroup) {
  return g.get('email').value !== '[email protected]' ? null : {
    emailExists: true
  };
}
<div class="form-group">
                      <input type="email" 
                        [ngClass]="{'is-invalid': registerForm.get('email').errors && registerForm.get('email').touched}
                          || registerForm.get('email').touched && registerForm.hasError('emailExists')"
                        class="form-control" 
                        formControlName="email" 
                        placeholder="Email">
                        <div class="invalid-feedback" *ngIf="registerForm.get('email').touched && registerForm.get('email').hasError('required')">
                          Email is required
                        </div>
                        <div class="invalid-feedback" *ngIf="registerForm.get('email').touched && registerForm.get('email').hasError('email')">
                          Invalid email address
                        </div>
                        <div class="invalid-feedback" *ngIf="registerForm.get('email').touched && registerForm.get('email').hasError('emailExists')">
                            Email address already in use
                          </div>
                    </div>

1 Answer 1

2

Made some changes:

  • You had applied the validation to the complete form, i changed that to the email field only email: ['', [Validators.required, Validators.email, this.emailMatchValidator]],;

  • Added the email field value & email field status to the screen to see the validation in action

  • enter anything in the email field and move focus to get the validation in action

relevant HTML:

    <form class="form-group" [formGroup]='registerForm'>
        <input type="email" 
                        [ngClass]="{'is-invalid': registerForm.get('email').errors && registerForm.get('email').touched}
                          || registerForm.get('email').touched && registerForm.hasError('emailExists')"
                        class="form-control" 
                        formControlName="email" 
                        placeholder="Email">
                        <div class="invalid-feedback" *ngIf="registerForm.get('email').touched && registerForm.get('email').hasError('required')">
                          Email is required
                        </div>
                        <div class="invalid-feedback" *ngIf="registerForm.get('email').touched && registerForm.get('email').hasError('email')">
                          Invalid email address
                        </div>
                        <div class="invalid-feedback" *ngIf="registerForm.get('email').touched && registerForm.get('email').hasError('emailExists')">
                            Email address already in use
                          </div>
                    </form>

<hr/>
                    <b>email value:</b> {{registerForm.controls.email.value}} <br/>
                    <b>email status:</b> {{registerForm.controls.email.status}}

relevant TS:

import { Component } from '@angular/core';
import { FormBuilder, Validators, FormGroup, AbstractControl } from '@angular/forms'

@Component({
  selector: 'my-app',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.css']
})
export class AppComponent {
  name = 'Angular';
  constructor(private fb: FormBuilder) { }
  registerForm;

  ngOnInit() {
    this.createRegisterForm();
    console.log(this.registerForm);
  }

  createRegisterForm() {
    this.registerForm = this.fb.group({
      gender: ['male'],
      email: ['', [Validators.required, Validators.email, this.emailMatchValidator]],
      username: ['', [Validators.required, Validators.minLength(4), Validators.maxLength(10)]],
      knownAs: ['', Validators.required],
      dateOfBirth: [null, Validators.required],
      city: ['', Validators.required],
      country: ['', Validators.required],
      password: ['', [Validators.required, Validators.minLength(4), Validators.maxLength(8)]],
      confirmPassword: ['', Validators.required]
    }
      /*, {
          validator: [this.passwordMatchValidator, this.emailMatchValidator]
        }
        */
    );
  }

  passwordMatchValidator() {
    /* some implementation */
  }

  emailMatchValidator(control: AbstractControl) {
    if (control.value !== '[email protected]') {
      return false;
    } else {
      return { emailExists: true };
    }
  }

}

working stackblitz here

Sign up to request clarification or add additional context in comments.

1 Comment

thanks for the help! Quick question - as this project isn't mine, and I'm still learning, why did the developer use a "validator: this.passwordMatchValidator" on the complete form? Is it because he's attempting to validate accross multiple controls (password, confirmPassword) ?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.