【问题标题】:Angular http: prevent calling multiple requests by chaining themAngular http:通过链接它们来防止调用多个请求
【发布时间】:2020-08-31 00:10:32
【问题描述】:

我有一个 API PUT 到 /api,我想通过链接它们来防止同时发送多个请求:第二个调用应该等待第一个调用完成,依此类推。不应忽略任何呼叫(我不谈论油门/去抖动/速率限制)。

目前,我想出的唯一解决方案是Promise


@Injectable({providedIn: 'root'})
export class ApiService {
  private lastCall: Promise<null> = Promise.resolve(null);
  constructor(private readonly httpClient: HttpClient}

  async update(data: Data): Promise<null> {
    this.lastCall = this.lastCall.finally(() =>
      this.httpClient.put<null>('/api', data).toPromise(),
    );
  }
}

不知道有没有更好的rxjs解决方案比如concatMap运算符在ngrx效果中使用,但我想在服务层面实现:

  update$ = createEffect(() => this.actions$.pipe(
    ofType(updateAction),
    concatMap(action => this.api.update(...)),
  ));

【问题讨论】:

  • 你已经有了答案
  • 我只对 Observable 的解决方案感兴趣,而无需转换为/返回 Promise,因为经过 1 小时的反思后我找不到任何东西。
  • 你为什么不在update(...)里面返回this.httpClient.put&lt;null&gt;('/api', data)
  • 因为我想要 ApiService 级别的行为,而不是效果级别的行为,因为 API 在多个位置使用。

标签: angular typescript rxjs angular-httpclient


【解决方案1】:

使用Subject 发出您的http 请求。创建一个 Observable,用concatAll 展平这个主题。在您的服务中订阅它。

您可以使用 tap 将 Observer 附加到您的 http 请求。

import { Subject, Observable, PartialObserver } from "rxjs";
import { concatAll, tap } from "rxjs/operators";

@Injectable({providedIn: 'root'})
export class ApiService {
  private requests = new Subject<Observable<any>>();
  private update$ = this.requests.pipe(concatAll());

  constructor(private readonly httpClient: HttpClient) {
    this.update$.subscribe()
  }

  update(data: Data, observer: PartialObserver<any> = { complete: () => null }) {
    this.requests.next(
      this.httpClient.put<any>('/api', data).pipe(tap(observer))
    )
  }
}

【讨论】:

  • update 方法的调用者应该能够在请求结束时添加回调
  • @htn 我更新了我的答案,所以你可以通过Observer
  • 我没有尝试过,但我认为它有效。但是,它比我的 Promise 解决方案更复杂,没有任何好处。通过使用Promise 而不是Observable,我们失去了调用者的能力:1. 决定何时订阅,2. 在订阅之前为Observable 应用运算符。我们无法使用您的解决方案来执行任何这些操作。
猜你喜欢
  • 1970-01-01
  • 2014-04-24
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-12-31
  • 2021-03-22
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多