我正在寻找每个城市的文件。
我有第一个通过解析页面来获取城市的http GET,然后我需要对每个城市提出另一个请求以检索关联的文档。
我做了什么
this.httpService.callUrl(ifrUrl).subscribe((html: string) => {
const root = parse(html);
const nodes = root.querySelectorAll(IFR_AIRPORTS_SELECTOR);
const airports = [];
for (const node of nodes) { // Loop for each city
if (node.childNodes.length === 2) {
const linkElement = node.childNodes[1];
// @ts-ignore
const link = linkElement.attributes.href;
const airportUrl = this.urlService.getIfrUrlWithEnd(link);
const airportName = linkElement.innerText.trim().replace('\n', ' ');
// @ts-ignore
const icaoSplit = linkElement.attributes.id.toString().split('.');
const icao = icaoSplit[icaoSplit.length - 1];
// Retrieve documents associated to the actual airport
// with an other http request
this.getIfrChartsForUrl(airportUrl).subscribe((charts) => {
const airport = new IfrAirport();
airport.icao = icao;
airport.name = airportName;
airport.url = airportUrl;
airport.charts = charts;
});
}
}
console.log('Airports');
console.log(airports);
我对异步功能不是很熟悉。在此之后,我尝试显示机场,但是运行带有空机场数组的脚本后,会直接显示日志...
应返回数组构建airports
。
我想念什么?
T H A N K S
答案 0 :(得分:2)
您可以使用RxJS高阶映射运算符(例如switchMap
来映射可观察的对象,而forkJoin
函数来组合多个可观察的对象,而不是嵌套的订阅和循环中的订阅。
尝试以下
this.httpService.callUrl(ifrUrl).pipe(
switchMap((html: string) => {
const root = parse(html);
const nodes = root.querySelectorAll(IFR_AIRPORTS_SELECTOR);
const requests = [];
for (const node of nodes) { // Loop for each city
if (node.childNodes.length === 2) {
const linkElement = node.childNodes[1];
// @ts-ignore
const link = linkElement.attributes.href;
const airportUrl = this.urlService.getIfrUrlWithEnd(link);
const airportName = linkElement.innerText.trim().replace('\n', ' ');
// @ts-ignore
const icaoSplit = linkElement.attributes.id.toString().split('.');
const icao = icaoSplit[icaoSplit.length - 1];
requests.push(
this.getIfrChartsForUrl(airportUrl).pipe(
map(charts => {
const airport = new IfrAirport();
airport.icao = icao;
airport.name = airportName;
airport.url = airportUrl;
airport.charts = charts;
return airport;
})
)
);
}
}
return forkJoin(requests);
})
).subscribe(
airports => console.log(airports),
err => console.log(err)
);