0

我正在使用 RxJS。我有两个 Observables(API 调用),它们为同一个数组返回不同数量的信息。我想在 Observables 之间切换并让订阅识别这两个结果,即每次返回值时触发。

这是一个使用 Typescript 的示例(这不起作用

let foo = [];
const callOne$ = this.service.getSomeData$; // this should take 0.5 seconds
const callTwo$ = this.service.getAllTheData$; // this should take 6 seconds

callOne$.pipe(
    switchMap(data => data.length > 0 ? callTwo$ : of(data)
).subscribe(data => {
    console.log(data); // this fires once but I want it to fire twice
    foo = data;
});

上面的例子先检索callOne$,然后检索callTwo$,然后给我结果。相反,我希望两者的结果都按顺序排列。我将如何订阅 Observables 以便接收第一个结果,然后通过第二个调用进行更新?

4

2 回答 2

1

最简单的方法可能是

merge(callOne$, callTwo$)
.subscribe(data => { 
    console.log(data); // this fires twice but results are not guaranteed to be ordered
    foo = data;
});

您可以保留订单,但会发出一个类似这样的事件

forkJoin(callOne$, callTwo$)
.subscribe(([data1, data2]) => { // this fires once with both results ordered
     console.log(data1); 
     console.log(data2);
     foo = data;
 });

如果您希望有 2 个单独的通知来维护订单,即首先是 callOne$ 的结果,然后是 callTwo$ 的结果,您可以尝试使用这样的expand运算符

callOne$.pipe(
  expand(val => callTwo$),
  take(2)  // to make sure you do not call callTwo$ infinitely
)
.subscribe(data => { 
  console.log(data); // this fires twice and the results are guaranteed to be ordered
  foo = data;
});

看它foo是一个数组的事实,你可能会倾向于使用forkJoin,即第二个选项。

您可以在本文中找到更详细的解释。

于 2020-03-22T22:04:09.407 回答
0

我发现最好的结果是使用concat(),它按顺序响应 Observable 结果。

换句话说:

concat(callOne$, callTwo$)
.subscribe(data => {
    console.log(data); // this will fire twice
    foo = data;
});

此代码将返回两个结果,按列表data顺序更新变量。concat()

于 2020-03-26T16:17:14.127 回答