为Observable <sourceitem []>中的每个项目调用api,然后将其“合并”回到Observable <targetitem []>

时间:2018-09-07 16:09:39

标签: rxjs rxjs6

我有一个Observable,其中包含用户选择的项目。每个选定的项目均用作api调用的源。并且api调用的结果应“合并”到Observable。

我似乎没有得到的是如何合并结果。我尝试使用扫描运算符,但“累加器”仅“增长”。

我有这个:

import {
  Observable,
  Subject,
  of ,
  from
} from 'rxjs';
import {
  map,
  merge,
  flatMap
} from 'rxjs/operators';

function apiUri(albumId: String) {
  return `https://jsonplaceholder.typicode.com/albums/${albumId}`
}


const albums$ = new Subject < String[] > ();

const responseStream = albums$.pipe(
  flatMap(albumIds => albumIds),
  flatMap(id => from(fetch(apiUri(id)))),
  flatMap(resp => resp.json()),
  /* I'm in the dark on how to "merge" it back into an Observable<String[]> */
);

responseStream.subscribe(resp => console.log(resp))
const randomCodes1 = ['5', '1', '3'];
albums$.next(randomCodes1);

运行示例为https://stackblitz.com/edit/rxjs-flatmap-galore?&file=index.ts

的Stackblitz链接

1 个答案:

答案 0 :(得分:1)

这是应该允许您创建正在寻找的responseStream的代码。

const responseStream = albums$.pipe(
  map(albumIds => albumIds.map(id => from(fetch(apiUrl(id))).pipe(mergeMap(resp => resp.json())))),
  mergeMap(obsOfIds => forkJoin(obsOfIds)),
);

首先,让我们关注forkJoin。您可以将一个Observable数组传递给此运算符,该运算符将返回一个Observable,当输入数组中的所有Observable均已发出时,该Observable就会发出,并且它将发出一个数组,其中包含输入数组中每个Observable所发出的值。

这可能是您要照顾的。如何创建所需的Observable数组?这是第一个map运算符执行的操作。

考虑该操作员时,请考虑一件事。

map(albumIds => albumIds.map(id => from(fetch(apiUrl(id))).pipe(mergeMap(resp => resp.json()))))

您正在使用2次map,但它们不是相同的map。第一map(即最外部的)是Observable的map运算符。第二个map,即最内部的一个,是Array的map方法。

我已经更新了您的堆叠闪电,它似乎工作正常。