2017-09-14 50 views
1

我有兩個非常相似的異步驗證器。兩者都檢查唯一性的值:電子郵件和首字母縮寫。第一種是這樣的:如何將服務注入異步驗證程序?

public static createEmailUniqueValidator(userService: UserService, originalEmailAddressFn:() => string) { 
    return (control: AbstractControl): Observable<ValidationErrors> => { 
     const originalEmailAddress: string = originalEmailAddressFn(); 
     if (originalEmailAddress && originalEmailAddress === control.value) { 
      return Observable.of({}); 
     } 
     return Observable.timer(1000).switchMap(() => { 
      return userService 
       .isEmailAddressUnique(control.value) 
       .map(result => (result ? null : { 'This email address is already in use': true })); 
     }); 
    } 
} 

第二個幾乎相同的,除了它在userService調用該方法。 如何才能讓一個通用驗證工廠通過它應該調用的方法來進行實際檢查?

到目前爲止,我有這樣的:

public static createValidator(uniqueFn: (value: string) => Observable<Boolean>, originalEmailAddressFn:() => string, errorMessage: string) { 
     return (control: AbstractControl): Observable<ValidationErrors> => { 
      const originalEmailAddress: string = originalEmailAddressFn(); 
      if (originalEmailAddress && originalEmailAddress === control.value) { 
       return Observable.of({}); 
      } 
      return Observable.timer(1000).switchMap(() => { 
       return uniqueFn(control.value) 
        .map(result => (result ? null : { errorMessage: true })); 
      }); 
     } 
    } 

但我收到以下錯誤:

ERROR TypeError: Cannot read property 'restService' of undefined at webpackJsonp.../../../../../src/app/services/user/user.service.ts.UserService.isEmailAddressUnique (user.service.ts:108)

restService是在userService注入另一個服務。 它看起來依賴關係尚未解決。我該如何解決這個問題?

這是我userService:

// imports ... 

@Injectable() 
export class UserService { 

    // [...] 

    constructor(private restService: RestService) { } 

    isEmailAddressUnique(emailAddress: string): Observable<Boolean> { 
    return this.restService.get(this.usersUrl + '/validateUniqueEmailAddress/' + emailAddress); 
    } 
} 
+0

你能告訴其中'使用restService'的代碼? – amal

+0

當然。剛剛編輯我的問題 – Tim

回答

1

編輯: 雙方誤解的功能所需的數量,並沒有完全解釋。花時間創建一個粗略匹配你的設置的(稍微簡化的)plunker(而不是試圖檢查一個API,它只是檢查電子郵件是否有效,但是作爲一個Observable來檢查;它也刪除了幾個參數createValidator到關注基本工廠)。我創建了working versionnon-working version。後者成功再現了您在運行時看到的錯誤(Cannot read property 'restService' of undefined)。請參閱src/user.service.ts瞭解重大更改。我已經在下面進行了更新,以突出顯示使用胖箭頭聲明很重要的兩個功能,以便正確綁定this。如果有一些東西我已經過分簡化了,請讓我知道,我們可以一起工作。

使用脂肪箭頭聲明重要功能:

public static = createValidator(/*same parameters*/) => { 
    // same content 
} 

public isEmailAddressUnique = (/*same parameters*/) => { 
    // same content 
} 
+0

我不知道這是如何幫助我。我想結束一個單一的createValidator方法,該方法可以被賦予一個服務的方法引用。 – Tim

+0

你說的很對 - 這是一個很糟糕的解釋,我沒有正確理解你想要的工廠功能。我已經更新了我的答案,並且花了一些時間在上面鏈接的一個簡化的plunk上。查看非工作版本以查看您的錯誤,並在工作版本中查看我試圖突出顯示的函數聲明。 –