【问题标题】:Angular 12: ngModel variable not updating after async get resultAngular 12:ngModel 变量在异步获取结果后未更新
【发布时间】:2021-12-09 14:34:54
【问题描述】:

我知道这个问题很常见,但我已经做了一些研究,但没有找到任何适合我的情况的解决方案,我尝试了一些类似 ngZone 和 setTimeout 的方法,但都不起作用。

我拥有的是一个使用 ngModel 的组件,该组件通过使用实用程序类的服务完成更新,您可以在下面查看:

component

ngOnInit(): void {
    this.init();
  }

  private async init() {
    this.initModel();
    this.initForm();
  }

  private async initModel() {
    await this.getId();
    this.getModel();
  }

  private async getId(): Promise<any> {
    return this.route.paramMap.subscribe((params) => {
      this._id = params.get('id'); 
    });
  }

  private async getModel() {
    console.log('getModel: '+this._id)
    if (this._id) {
      console.log('if')
      this.operationType = constants.COMPONENT.MAINTAIN.OPERATION_TYPE.PUT;
      
      (await this.session.apiManager.WorkerApi.getWorker(this._id)).subscribe(
        (response: any) => {
          this.worker = response
          console.log('await - ' + this.worker.name)
        }
      );
      
      console.log('after');
    }
    else 
      this.worker = new Worker("");
  }

我的服务类Session方法

public async getWorker(id: string): Promise<Observable<Worker>> {
    return await this.api.getData(this.REQUEST_URL + "/" + id);
}

我的实用程序API 类方法

public getData(request?: String): Observable<any> {
    const requestUrl = this.URL + request;
    
    return this.http.get(requestUrl);
}

“有趣”的是,我在另一个组件中为另一个模型使用了相同的代码并且它运行良好,但是在我的“get”回调之后它不会更新我的输入文本(如下)。

<input type="text" class="form-control" name="name" id="name" 
                required minlength="2" [(ngModel)]="this.worker.name">

你能帮我理解什么是错的吗?

提前致谢!

#编辑1

我将component 更改为使用toPromise,我的console.log 序列现在可以正常工作,尽管模型仍未更新。

getModel()

  private async getModel() {
    console.log('getModel: '+this._id)
    if (this._id) {
      console.log('if')
      this.operationType = constants.COMPONENT.MAINTAIN.OPERATION_TYPE.PUT;
      
      this.worker = (await (await this.session.apiManager.WorkerApi.getWorker(this._id)).toPromise());
      console.log('toPromise: '+this.worker.name);
      
      console.log('after');
    }
    else 
      this.worker = new Worker("");
  }

#编辑 2

我刚刚意识到我也无法通过我的 ts 代码获取输入值,它只是证明问题出在我的双向数据绑定上(我猜)。当我在 onSubmit 事件上调用 this.worker.name 时,即使输入已填充,模型也是空的。

这让我怀疑问题的标题是否错误......也许“双向 ngModel 数据绑定不起作用”更合适......

【问题讨论】:

  • 你试过了吗? [(ngModel)]="worker.name" 我很确定没有必要在任何模板 html 上使用 this
  • 你是不是碰巧在@Component指令中添加了changeDetection: ChangeDetectionStrategy.OnPush
  • 这个或没有这个对模板没有任何影响。 Raphael 关于 OnPush 策略的建议不是解决方案,而是建议您解决问题的罪魁祸首。这不是什么神奇的修复,而是一种优化,只有在您不订阅 Observables 时才有效。实际上,您不应该订阅它们,而是将它们与管道或更高阶的管道结合起来。然后在模板中对它们使用异步管道。这样你甚至可以使用 OnPush ChangeDetectionStrategy。如果您努力创建Stackblitz,我将很乐意提供帮助。
  • 正如@H3AR7B3A7 解释的那样,这不是一个解决方案,但如果您确实回答“是”,那么我会建议您将其删除。你应该明确地做一个stackblitz,肯定会帮助一个用户找到问题和解决方案;)。 changeDetection: ChangeDetectionStrategy.OnPush 将使您的组件 无法再改变自己 Here 原因 但基本上,如果这个组件,或者他的任何一个父组件(声明他的那个)有OnPush那么你不应该改变组件的html。
  • @RaphaëlBalet 对不起我的误解!但无论如何,谢谢,我确实在测试后已经删除了它......关于stackblitz,我会尝试这样做,以便我们可以解决问题,然后我会告诉你!再次感谢!

标签: angular mean-stack angular-ngmodel angular12


【解决方案1】:

好吧,我在创建 @H3AR7B3A7 和 @Raphaël Balet 建议的 stackblitz 时发现了这一点。发生的事情是我有一个额外的 HTML 代码,使用 [formGroup]:

<form novalidate #form="ngForm" [formGroup]="formGroup" (ngSubmit)="onSubmit(form)">

这意味着,我试图将双向数据绑定与 ngModel 和角度反应形式一起使用,但不知何故,角度在它上面迷失了,我的模型无法正常工作。我需要做的就是删除[formGroup]="formGroup",它运行良好。

另外,对于未来的观众来说,stackblitz 帮助我提供了比浏览器更精确的错误消息,因此它帮助我解决了我的应用程序中的其他错误,例如空注入。

【讨论】:

    猜你喜欢
    • 2017-03-14
    • 2017-10-26
    • 2021-09-15
    • 1970-01-01
    • 2017-07-25
    • 2015-10-21
    • 1970-01-01
    • 1970-01-01
    • 2018-11-25
    相关资源
    最近更新 更多