[英]Chaining recursive RxJS observables while operating on object
我的后端有兩個 graphql 查詢: familiyTreeQuery
返回一個家譜作為帶有孩子的節點,它也可以有孩子等等,以及personPicturesQuery($name: string)
返回給定人的照片。
我的目標是調用familyTreeQuery
,迭代樹,如果這個人叫做 Alice,那么我想為這個人調用personPicturesQuery
並將信息添加到樹中的節點。 應該對樹中的所有 Alice 執行此操作。
我的問題是,獲取圖片的調用是異步發生的,因此在將信息添加到節點之前返回數據。 我沒有按照這個問題中的建議使用flatMap
,因為在迭代樹時正在調用獲取圖片,而我無法在familyTreeQuery
的管道方法中調用它。
public getContext(): Observable<TreeNode> {
return this.familyTreeQuery.watch().valueChanges.pipe(
map(result => {
const familyTree = result.data.familyTree;;
this.addPicturesToAlice(familyTree);
return familyTree;
})
)
}
private addPicturesToAlice(node: TreeNode) {
if (node.name === 'Alice') {
this.fetchPictures(node.id).subscribe(pictures => {
node.pictures = pictures;
})
}
if (node.children && node.children.length > 0) {
for (const childNode of node.children) {
this.addPicturesToAlice(childNode);
}
}
}
private this.fetchPictures(personId): Observable<Picture[]> {
return this.personPicturesQuery.fetch({id: personId}).pipe(
map(result => {
return result.data.personPictures;
})
)
}
據我所知,我不應該在addPicturesToAlice
方法中調用 subscribe ,但我是 Angular 和 RxJS 的新手,並沒有找到使這項工作的方法。
您可以通過創建一組 observable 並遞歸傳遞它來實現這一點,然后使用forkJoin
在getContext
訂閱它,如下所示:
public getContext(): Observable<TreeNode> {
return this.familyTreeQuery.watch().valueChanges.pipe(
switchMap(({ data: { familyTree } }) => forkJoin(this.addPicturesToAlice(familyTree)))
)
}
private addPicturesToAlice(node: TreeNode, observables: Observable<Picture[]>[] = []): Observable<Picture[]>[] {
if (node.name === 'Alice') observables.push(
this.fetchPictures(node.id).pipe(tap(pictures => node.pictures = pictures))
)
if (node.children?.length) {
for (const childNode of node.children) {
this.addPicturesToAlice(childNode, observables);
}
}
return observables;
}
private fetchPictures(personId: number): Observable<Picture[]> {
return this.personPicturesQuery
.fetch({ id: personId })
.pipe(map(result => result.data.personPictures))
}
希望它足夠清楚。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.