1

I am trying to find the duplicate dealer name with custom validators. The dealers name data comes from web-service. I have dealer service to get the dealer data. And I am using it for dealer duplicate validation at validDelarName function inside component. And I am declaring it on FromGroup Validators but it's not being called.

Form Group Validator - declare

name: ['', Validators.compose([Validators.required, Validators.maxLength(128),Validators.pattern('[a-zA-Z0-9\\s\\-\\,\\.\\&\\(\\)]+'),(control:FormControl)=>this.validDelarName])],

Validation function. It's also present in component.

 validDelarName(FormControl){   
  const dealer = this.dealer.getviewdealer().subscribe( //getting data using webservices
  (data) => {       
     data.forEach(items => {
      for (var key in items) {
        if (items.hasOwnProperty(key)) {

          if(control.value == items['dealername']){
            return {valid:true;}
          }
          else{
            retrun null;
          }

        }
      }
     });
  }

);
 }
1
  • I have post it. Commented Jun 17, 2017 at 12:08

1 Answer 1

4

First of all, there are a lot of mistakes in your code, let's enumerate it:

1 - Since your custom validator validDelarName is async, it must go as the 3rd. parameter, like this:

name: [
  '', 
  [
    Validators.required, 
    Validators.maxLength(128),
    Validators.pattern('[a-zA-Z0-9\\s\\-\\,\\.\\&\\(\\)]+')
  ],
  (control: AbstractControl) => this.validDelarName // Fix later
]

2 - You have to pass the control or the context to your custom validator, like below:

(control: AbstractControl) => this.validDelarName(control)

or if you prefer:

this.validDelarName.bind(this)

3 - The validDelarName's signature is wrong, it must be like this:

validDelarName(control: AbstractControl) { ... }

4 - The async validator waits or a Promise or an Observable and you're returning only null | errorObj inside the forEach, which one isn't doing anything.

Solution:

Instead of subscribe you could use map operator (or if you want you can use a Promise) and let Angular do his job.

To search for a specific value in your array I'd suggest you to use Array#some. It'll returns true if it finds the typed text in the array and will automatically stop the loop, otherwise it'll return false.

Based on this, you can return the error object or null, like this:

validDelarName(control: AbstractControl) {
  return this.dealer.getviewdealer().map(data => {
    const hasItem: boolean = data.some(item => control.value === item['dealername']);

    return hasItem ? { valid: true } : null;
  });
}

5 - As you can see above, you don't need to iterate over all the keys of data object (as you're doing) since you only want to compare the dealername.

6 (Minor mistake) - You have a typo in retrun null;, should be return null; :).

7 (Credits to @yurzui) - return {valid:true;} should be return { valid: true };


Tips:

1 - The Validators.compose isn't needed, you can just pass an array, or if it's a single validator, the validator itself, in both parameters (2nd and 3rd).

2 - Validators.pattern accepts a RegExp, so you can use it.

Why? Instead of escaping the symbols with double slashes, you can escape only a single slash and IMO, it's more readable.

Sample:

Validators.pattern(/^[a-zA-Z0-9\s-\,\.&\(\)]+$/)

Also, note that not all symbols here needs to be escaped (I take out the unneeded escaping).

FULL DEMO

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

3 Comments

Good answer! 7. return {valid:true;} should be return {valid:true} :)
@yurzui Oh, I missed that one. I just added it, thanks. :)
Thanks, @developer033. It's really worked for me. You described it step by step. That thing is really helped me to understand very easily. Actually, I am beginner level in angular2. Once again thanks for your great answer and you too yurzi.

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.