Я новичок в Angular, JS и наблюдаемых. У меня есть класс машинописи под названием DataService. Я хочу, чтобы он загружал список URL-адресов из локального файла в формате JSON, а затем каким-то образом вызывал эти URL-адреса (для нескольких API REST) и возвращал наблюдаемые. Проблема в том, что мой код не ждет загрузки файла конфигурации, прежде чем будут вызваны функции REST API.
Я подумал, что конструктор DataService мог бы загрузить файл конфигурации, а затем иметь уникальные функции для каждого вызова API REST, но это не работает
мой код:
export class DataService {
configFile
constructor(private http: HttpClient) {
this.http.get('/assets/restApiUrlListConfig.json').subscribe(config => {
this.configFile = config;
});
}
getUrlFromConfigFile(name: string): string {
...
this returns the URL from the config file
...
}
getUrlAData(): Observable {
return this.http.get( getUrlFromConfigFile('A') )
}
}
Мои другие компоненты имеют такой код:
export class SomeComponent implements OnInit {
someComponentAData
constructor(private data: DataService) { }
ngOnInit() {
this.data.getUrlAData().subscribe(
data => {
this.someComponentAData = data
}
)
}
Я получаю сообщение об ошибке, что наблюдаемое, возвращаемое из службы данных, не определено. Я верю в то, что конструктор еще не завершил загрузку файла конфигурации, и я думаю, что функция getUrlAData ничего не возвращает.
Мне кажется, что я не правильно обрабатываю эти асинхронные вызовы, но я не знаю, как сообщить свой код:
- создать объект службы данных
- загрузить файл данных, прежде чем что-либо еще можно сделать
- позволяет асинхронно вызывать другие функции ПОСЛЕ загрузки файла конфигурации
Угловой CLI: 6.2.3
Узел: 8.12.0
ОС: win32 x64
Угловой: 6.1.8
Редактировать 1: попытка реализовать предложенное решение
My DataService
configFile
configObservable: Observable<any>;
someSubscribeObj
constructor(private http: HttpClient) {
this.someSubscribeObj = this.http.get('/assets/restApiUrlListConfig.json').subscribe(config => {
this.someSubscribeObj = undefined;
this.configFile = config;
});
}
getObsFromConfigFile(name: string): Observable<any> {
//...
if (this.configFile != undefined) {
console.log('this.restApiUrlListConfig[name]',this.configFile[name])
return of(this.configFile[name])
}
else
return of(this.someSubscribeObj.pipe(map(c => c[name])))
//this.configObservable
//...
}
getUrlAData(): Observable<any> {
return this.getObsFromConfigFile('A').pipe(mergeMap(url => this.http.get(url)))
}
Мой другой компонент:
constructor( private data: DataService ) { }
ngOnInit() {
//this.data.loggedIn.pipe((p) => p);
this.data.getUrlAData().subscribe(
data => {
this.urlAData = data
}
)
}
Мне не удалось сохранить «подписку» в наблюдаемой, поэтому я создал универсальный тип varable любого типа, но во время выполнения у меня возникает проблема с командой pipe:
TypeError: this.someSubscribeObj.pipe не является функцией
в DataService.push ../ src / app / services / data.service.ts.DataService.getObsFromConfigFile
(data.service.ts: 67)
в DataService.push ../ src / app / services / data.service.ts.DataService.getUrlAData
(data.service.ts: 74)
Редактировать 2: неудачный обходной путь
В настоящее время я использую две вложенные подписки, чтобы выполнить работу в основном
http.get(config_file_url).subscribe(
config => {
http.get( config['A'] ).subscribe( adata => { do things };
http.get config['B'].subscribe( bdata => {do things };
}
)
Я чувствую, что должен иметь возможность использовать какую-то MergeMap, но я не мог заставить их работать так, как я думал.