我对于在指令中注入的共享数据未定义

时间:2018-05-19 22:59:39

标签: angular angular-directive

所以我试图将一个共享数据注入一个指令,供验证者用来验证用户输入的电子邮件。我的问题是我从指令内部获取了共享数据的值“未定义”。以下是片段:

registration.html

  div class="form-group md-form" [class.has-error]="email.touched && email.dirty && email?.errors?.emailExist">
    <i class="fa fa-envelope prefix grey-text"></i>
    <input type="email" name="email" id="email" email="true" appCheckEmail [(ngModel)]="dealerRegistrationInput.email" #email="ngModel" class="form-control" placeholder="Email Address">
     <div class="help-block alert alert-danger " *ngIf="email.errors && (email.dirty || email.touched) && email?.errors?.emailExist">
     <div [hidden]="!email.errors.email">
      A valid email is required.
     </div>
    <div [hidden]="email?.errors.emailExist">
      This email address already exist
    </div>
   </div>
  </div>

registration.ts

.......
 constructor(
    private router: Router,
    private route:  ActivatedRoute,
    private http: HttpClient,
    private sharedData: SharedDataService,
    private connectService: ConnectService,
    private modalService: BsModalService) { }

  ngOnInit() {
     this.connectService.getAllDealers().subscribe((dealers: Dealer[]) => {
      this.sharedData.dealers  = dealers;
      console.log('Dealers.....' + JSON.stringify(this.sharedData.dealers));
    });
  }
 ............
 .........
 .............

check-mail指令

    import {  Input, Directive, forwardRef } from '@angular/core';
    import { Validator, FormControl, AbstractControl, NG_VALIDATORS, ValidationErrors } from '@angular/forms';
    import { SharedDataService } from './shared-data.service';


    /* ......Functions.........................*/

      function appCheckEmail(dealersEmails: string[]) {
console.log('Dealers..:   ' + JSON.stringify(dealersEmails)); //THIS IS UNDEFINED
           return (control: AbstractControl) => {
  console.log('Dealers email addresses2:   ' + JSON.stringify(dealersEmails));
  console.log('Control value: ' + control.value)
  ...

  ...
      if (dealersEmails.indexOf(control.value) >= 0) {
                   return null;
           } else {
              return{  emailnotExist: true  };
           }
        };
       }

     /* -------------------------End of Functions.............*/

    @Directive({
      selector: '[appCheckEmail][ngModel], [appCheckEmail][ngModel]',
      providers: [{
        provide: NG_VALIDATORS,
        useExisting: forwardRef(() => CheckEmailDirective),
        multi: true
      }]
    })

    export class CheckEmailDirective implements Validator {
      validator: Function;

      constructor(private sharedData: SharedDataService) {

      this.validator = appCheckEmail(sharedData.dealers); /* sharedData.dealers is undefined */
         }
         validate(control: AbstractControl): ValidationErrors | null {
            return this.validator(control);
          }

        }

不管怎么说,尽管注入了指令中的共享数据并没有指向正确的引用或者值已被清除。 我还观察到一些非常奇怪的事情......一旦html被呈现,checkMail指令就被执行了...在输入任何数据之前,显然是在目标输入字段的每次击键之后....这种行为会导致问题吗? 我很感激能得到的任何帮助。

- EDIT-- 已将appCheckEmail参数更改为appCheckEmail(sharedData:SharedDataService)

和indexOf搜索到:

 if (sharedData.dealers.indexOf(control.value) >= 0){....}

搜索仍无法找到匹配项。我已经通过console.log确认sharedData.dealers数组实际上是一个字符串数组,而control.value是一个包含我期望值的字符串。我也试过简单的for循环:

if(sharedData.dealers [i] === control.value) 我甚至尝试过: if(sharedData.dealers [i] ==='emailinarray@mail.com')

两者都失败了。我知道我在这里缺少一些基本的东西,但我似乎无法找到它。可能是sharedData.dealers [i]仍然指向错误的位置,即使我在构造函数中传递了引用?

1 个答案:

答案 0 :(得分:1)

您应该将对服务的引用传递给函数,而不是将dealers传递给validate函数。您的解决方案存在的问题是dealers中不存在constructor。您是异步提取dealers中的Component,因此在Directive构造函数

中的构建时间内它们不存在

&#13;
&#13;
import {  Input, Directive, forwardRef } from '@angular/core';
import { Validator, FormControl, AbstractControl, NG_VALIDATORS, ValidationErrors } from '@angular/forms';
import { SharedDataService } from './shared-data.service';


/* ......Functions.........................*/

function appCheckEmail(sharedData: SharedDataService) {

  return (control: AbstractControl) => {
    console.log('Dealers email addresses2:   ' + JSON.stringify(sharedData.dealersEmails));
    console.log('Control value: ' + control.value)
    ...

    ...
    if (sharedData.dealersEmails.indexOf(control.value) >= 0) {
      return null;
     } else {
      return{  emailnotExist: true  };
    }
  };
}

/* -------------------------End of Functions.............*/

@Directive({
  selector: '[appCheckEmail][ngModel], [appCheckEmail][ngModel]',
  providers: [{
    provide: NG_VALIDATORS,
    useExisting: forwardRef(() => CheckEmailDirective),
    multi: true
  }]
})
export class CheckEmailDirective implements Validator {
  validator: Function;

  constructor(private sharedData: SharedDataService) {
    this.validator = appCheckEmail(sharedData); /* sharedData.dealers is undefined */
  }
  
  validate(control: AbstractControl): ValidationErrors | null {
    return this.validator(control);
  }

}
&#13;
&#13;
&#13;