如何加载多个休息请求 [英] How to load multiple rest requests
问题描述
我必须执行多个GET请求才能从外部页面加载数据.
I have to do multiple GET Requests to load data from an external page.
a请求的响应可能返回一个标志,指示有更多数据要加载: "nextPage":"/v1/catalog/products?page = 2& pageSize = 10",
The response of the a request might return a flag that indicates that there is more data to load: "nextPage" : "/v1/catalog/products?page=2&pageSize=10",
下面是我的函数代码.
我试图实现一个do while循环,但无法使其正常工作.我想还有一种更聪明的方式可以做到这一点-也许是Switchmap?
I tried to implement a do while loop but I couldn't make it work. I guess there is also a smarter way to do this - maybe Switchmap?
旧版本
loadCatalog() {
return new Promise((resolve, reject) => {
this.http.get<Catalog[]>(ZUORA_URL + '/v1/catalog/products?page=1&pageSize=10', { headers })
.pipe(map(data => data))
.subscribe(data => {
this.catalog = data;
resolve(true);
});
});
}
我想加载完整的数据并将其存储在一个地方.如何循环播放,直到没有其他下一页? -现在可以一页一页地加载,但是我仍在努力存储响应...
I want to load the complete data and store it in one place. How can I loop until there is no additional nextpage? - loading one page after another is now working but I'm still struggeling to store the responses...
更新版本
getProducts(url, dataSoFar = []): Observable<any[]> {
if (!url) {
return of (dataSoFar);
} else {
url = ZUORA_URL + url;
}
return this.http.get<any>(url, { headers }).pipe(
switchMap(p => this.getProducts( p.nextPage, [...dataSoFar, ...p.data]))
);
}
getData() {
return this.getProducts('/v1/catalog/products');
}
推荐答案
您可以使用 expand
递归调用您的api,然后 reduce
减少对单个数组的所有响应.
You can use expand
to call your api recursively and reduce
to reduce all the responses to a single array.
在您的Service
(MyService)中:
In your Service
(MyService):
import { EMPTY } from 'rxjs';
import { expand, reduce, map } from 'rxjs/operators';
baseUrl = ZUORA_URL;
// Let's say you get an object like this from your API
interface ApiResponse {
nextPage: string,
data: any[]
}
public fetchData(apiEndpoint: string): Observable<any[]> {
return this.http.get<ApiResponse>(baseUrl + apiEndpoint, { headers })
.pipe(
// recursively call the GET requests until there is no further 'nextPage' url
expand(apiResponse => {
if (!apiResponse.nextPage) {
return EMPTY;
}
return this.http.get<ApiResponse>(apiResponse.nextPage, { headers });
}),
// map the api response to the data we actually want to return
map(apiResponse => apiResponse.data),
// reduce the data of all GET requests to a single array
reduce((accData, data) => accData.concat(data))
)
}
在您的组件中:
private products: Product[];
loadProducts() {
this.myService.fetchData('/v1/catalog/products').subscribe(products =>
this.products = products as Product[]
)
}
这篇关于如何加载多个休息请求的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!