【问题标题】:Issue with validator function not setting error object on form control验证器功能问题未在表单控件上设置错误对象
【发布时间】:2016-08-30 14:39:25
【问题描述】:

我对以下验证器函数有疑问:

export function validateEmailKnownFactory(userAccountService: UserAccountService): {[key: string]: any} {
  return (control: AbstractControl) => {
    return control
      .valueChanges
      .debounceTime(1000)
      .switchMap(value => userAccountService.checkAvailability(value))
      .map(res => {
        if (res.json() === false) {
          return null;
        }
        //Control flow does get through here
        return {emailKnownValidator: {unknown: true}};
      });
  };
}

它没有在表单控件上设置错误对象(即{emailKnownValidator: {unknown: true}}),但控制流确实通过了正确的位置。

现在,如果我将上述函数替换为以下内容:

export function validateEmailKnownFactory(userAccountService: UserAccountService): {[key: string]: any} {
  return (control: AbstractControl) => {
    return userAccountService.checkAvailability(control.value)
      .map(res => {
        if (res.json() === false) {
          return null;
        }
        return {emailKnownValidator: {unknown: true}};
      });
  };
}

错误对象在表单控件上设置得很好,应用程序按预期运行。

注意区别:我从control.valueChanges 得到Observable,然后调用debounceTime,而另一个函数直接调用checkAvailability

为了完整起见,这里是 checkAvailability 方法:

  checkAvailability(email: string) {
    let body = 'email=' + email;
    return this.http.get(this.urls.USER_ACCOUNT.EMAIL_AVAILABLE + body);
  }

【问题讨论】:

    标签: angular rxjs angular2-forms rxjs5


    【解决方案1】:

    Angular 2 中的异步验证器函数可以返回 PromiseObservable。如果返回 Observable,它必须完成 - 作为 Angular converts the Observable to a Promise。也就是说,使用Observable 是为了验证可以是异步的,而不是验证器可以提供结果流。

    在您的第一个验证器中由 valueChanges 组成的 Observable 未完成 - 因为 valueChanges 不断抽出更改。这意味着Promise 无法解析,并且没有可应用于控件的验证结果。 (请注意,Angular 将为控件值的每次更改调用您的验证函数,并且每次调用都会看到一个 Observable 组合和订阅,因此 checkAvailability 将为每次更改调用。debounceTime 运算符是不会影响您似乎想要的行为。)

    checkAvailability 函数返回的 Observable 确实完成了,因此您的第二个验证器函数有效。

    【讨论】:

    • 感谢您的详细解释。最后一点我希望您澄清一下:您的意思是说debounceTime 不会达到我想要的效果是因为可观察对象是“订阅”吗?跨度>
    • 转换为Promise 将涉及订阅,但这并不是问题所在。事实上,对验证器的每次调用都会返回其自己的组合 Observable,它将 valueChangescheckAvailability 链接到基于 HTTP 的 Observable,因此每次调用总是会看到输入到 @987654343 的最新更改@。您可以使用debounceTime 组合Observable 来获得您想要的效果,但您不能在验证器中组合它,因为这样做会导致每个调用都组合一个单独的Observable
    • 我希望这是有道理的。这里有点晚了。
    • 谢谢。这是有道理的。
    猜你喜欢
    • 1970-01-01
    • 2020-02-26
    • 2011-07-02
    • 2012-07-12
    • 2018-06-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-02-09
    相关资源
    最近更新 更多