递归遍历Promises [英] Iterating over Promises recursively
问题描述
我有一个REST API接口,该接口仅使我获得一些信息的第一层.
I have an REST API interface which only gets me the first level of some information.
例如,我想收集组.每个组都可以有子组.因此,例如组1"具有子组组A"和组B".组A"具有子组"GroupX".依此类推.
So for example I want to collect groups. Every Group can have subgroups. So for example "Group 1" has the Subgroups "Group A" and "Group B". "Group A" has the Subgroup "GroupX". And so on.
但是API仅为我提供了组名称的第一级组.因此,我将"Group 1"传递给API,并返回"Group A"和"Group B".要获得组A的子组,我需要再次调用API.但是我不知道它将有多少次迭代.
But the API only gives me the first level of Groups for a group name. So I pass "Group 1" to the API and it returns "Group A" and "Group B". To get the supgroups of Group A, I need to call the API again. But i don't know how many iterations of this it will have.
所以我考虑过使用递归,但距离还很远.
So I thought about using recursion but I haven't come far.
到目前为止,我的代码:
So far my Code:
getGroupChildren(group:string){ return this restService.getGroupChildren(group)}
getGroups():Promise<any>{
let collection:string[] = [];
return this.getGroupChildren("Group A").then((result)=> {
if(result.data.length !==0){
return this.getGroupChildren(data[0].groupName);
}
});
}
现在,这只会返回我第一个元素的第一个Supgroups.
Now this will only return me the first Supgroups of the first element.
我怎么才能做到,无论有多少个Supgroup,总能找到它?也许使用Observables很好吗?
How can I accomplish it will always find every Supgroup no matter how many? Maybe is it good to use Observables?
这里是一个API调用的示例结构:
Here an example structure of one API call:
{ "groupName" : "Group_1", "children" : ["Group_A", "Group_B"]}
推荐答案
您可以使用 Observable
getGroups(group: string) {
return this.http.get(`/group/{group}`).flatMap(response => {
if (response.children.length === 0) { // you hit a leaf, stop recursion here
return Observable.of(response);
} else { // there are more levels to go deeper
return this.getGroups(response.children[0].groupName);
}
});
}
编辑使用Promise
Edit Using Promise
假设您使用 GroupService
返回数据而不是 HttpClient
.您可以使用 fromPromise
运算符将 Promise
转换为 Observable
.
Let's say you use a GroupService
which returns the data instead of HttpClient
. You can convert a Promise
to an Observable
with fromPromise
operator.
getGroups(group: string) {
return Observable.fromPromise(this.groupService.get(group)).flatMap(response => {
if (response.children.length === 0) { // you hit a leaf, stop recursion here
return Observable.of(response);
} else { // there are more levels to go deeper
return this.getGroups(response.children[0].groupName);
}
});
}
编辑2 使用此服务
让我们看一下您的示例.您有以下json
Let's take a look at your example. You have following json
{
"groupName": "Group_1",
"children" : ["Group_A", "Group_B"]
}
在组件文件中,您按以下方式调用服务
In your component file, you call the service as follows
...
this.recursiveGroupService.getGroups("Group_1")
.subscribe(response => {
// at this point response will be `Group_A`
})
编辑3 获取整个对象
这次,我们将使用 forkJoin
并为所有子代调用 getGroups
并将结果收集在 children
数组中.
This time we'll use forkJoin
and call getGroups
for all of the children and collect the results in a children
array.
注意:我尚未亲自测试此代码.它可能包含一些错误.如果有的话,让我知道.
Note: I haven't tested this code myself. It may contains some error. If it has, let me know.
import { forkJoin, of } from 'rxjs';
import { map } from 'rxjs/operators';
getGroups(group: string) {
let retVal;
return Observable.fromPromise(this.groupService.get(group)).flatMap(response => {
retVal = {
groupName: response.groupName
};
if (response.children.length === 0) { // you hit a leaf, stop recursion here
return of(retVal);
} else { // there are more levels to go deeper
// this will create list of observable for each child
const children$ = response.children.map(
child => this.getGroups(child));
// forkJoin will execute these observables in parallel
return forkJoin(children$).pipe(
map(results => {
// results is an array containing children data
retVal.children = results;
return retVal;
})
);
}
});
}
这篇关于递归遍历Promises的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!