繁体   English   中英

如何通过异步操作维护订户顺序

How to maintain order of subscribers with async operations

提示:本站收集StackOverFlow近2千万问答,支持中英文搜索,鼠标放在语句上弹窗显示对应的参考中文或英文, 本站还提供   中文繁体   英文版本   中英对照 版本,有任何建议请联系yoyou2525@163.com。

我有一个角度组件,可以订阅其路线参数。 每当路由参数更改时,它都会从参数中读取id并调用函数以查找该ID的记录。 该函数返回一个promise。 解决后,该组件将自己设置一个属性以用于数据绑定。

在某些情况下,响应似乎混乱了,设置了错误的值。 看起来是这样的:

ngOnInit() {
  this.route.params.subscribe((params) => {
    const id = params['id'];
    console.log('processing', id);
    this.service.getPerson(id).then((person) => {
      console.log('processed id', id);
      this.person = person; // sometimes this happens out of order
    }
  }
}

因此,假设我有一个按名称过滤的文本框,当我键入内容时,导航事件发生,其中id获取该名称的第一个结果。 有时我看到以下内容:

处理1

处理2

已处理2

已处理1 <----问题

解决这个问题的最优雅的方法是什么? 我曾考虑过将诺言转换为可观察的并试图取消它,但这似乎是举手之劳。 我试图找出是否有一种序列化订阅的方法,以使第二个“处理”直到第一个完成时才开始。

2 个回复

您将要使用concatMapswitchMap concatMap将确保上一个请求在完成下一个请求之前已完成处理。 switchMap也将确保顺序,除了如果下一个请求到来时仍在处理前一个请求,它将中断处理先前的请求。

ngOnInit() {
  this.route.params.pipe(
      map(params => params['id']),
      tap(id => console.log('processing', id)),
      concatMap(id => fromPromise(this.service.getPerson(id)).pipe(
        tap(person => console.log('processed id', id))
      )), 
      tap(person => this.person = person)
  )
  .subscribe();
}

您可以在每个呼叫中​​添加一个“请求ID”,然后将其返回给您。 然后在回调中,您可以检查请求ID是否高于您处理的最后一个ID。

对于带有单整数响应的小调用来说,这不是理想的选择,但是我将我的头隐藏在了头文件中,并使用拦截器/过滤器在每次请求时将该头文件回显给客户端。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题
 
粤ICP备18138465号  © 2020-2022 STACKOOM.COM