#angular #asynchronous #subscribe #fork-join
Вопрос:
Я пытаюсь понять, как лучше всего дождаться нескольких запросов и что-то сделать, когда они будут выполнены, имейте в виду, что оба запрашивают обед одновременно, и они не должны ждать друг друга.
// table filling public SUB_getActSearch: Subscription; // table filling 2 public SUB_getDeclarationSearch: Subscription; public fillTable(): void { const searchOBJ = { CreateDateFrom: this.currentDate, CreateDateTo: this.currentDate, ActNumber: this.ActNumber == undefined ? '' : this.ActNumber, vinCode: this.vinCode == undefined ? '' : this.vinCode, GovNumber: this.GovNumber == undefined ? '' : this.GovNumber, IsFromDashboard: true }; const searchOBJ2 = { ActNumber: this.ActNumber == undefined ? '' : this.ActNumber, vinCode: this.vinCode == undefined ? '' : this.vinCode, GovNumber: this.GovNumber == undefined ? '' : this.GovNumber, }; if ((this.ActNumber amp;amp; this.ActNumber != undefined amp;amp; this.ActNumber != null) || (this.vinCode amp;amp; this.vinCode != undefined amp;amp; this.vinCode != null) || (this.GovNumber amp;amp; this.GovNumber != undefined amp;amp; this.GovNumber != null)) { this.SUB_getActSearch = this.searchService.getActSearch({ ...searchOBJ2, PageSize: this.pageSize, PageNumber: this.currentPage }).subscribe((res) =gt; { this.Act_Data = []; let headerPagin = JSON.parse(res.headers.get('X-Pagination')); this.elementsLength = headerPagin.totalCount; this.currentPage = headerPagin.currentPage; this.pageSize = headerPagin.pageSize; res.body.map((param) =gt; { this.Act_Data.push(param); }); this.ActDataSource = new MatTableDataSourcelt;Elementgt;(this.Act_Data); // console.log('Your form data : ', this.ActDataSource); }); } else { this.SUB_getActSearch = this.searchService.getActSearch({ ...searchOBJ, PageSize: this.pageSize, PageNumber: this.currentPage }).subscribe((res) =gt; { this.Act_Data = []; let headerPagin = JSON.parse(res.headers.get('X-Pagination')); this.elementsLength = headerPagin.totalCount; this.currentPage = headerPagin.currentPage; this.pageSize = headerPagin.pageSize; res.body.map((param) =gt; { this.Act_Data.push(param); }); this.ActDataSource = new MatTableDataSourcelt;Elementgt;(this.Act_Data); // console.log('Your form data : ', this.ActDataSource); }); } } public fillTable2(): void { const searchOBJ = { DeclarationCreateDateFrom: this.currentDate.substring(0, 10), DeclarationCreateDateTo: this.currentDate, DeclarationNumber: this.ActNumber == undefined ? '' : this.ActNumber, VinCode: this.vinCode == undefined ? '' : this.vinCode, TransitNumber: this.GovNumber == undefined ? '' : this.GovNumber, }; const searchOBJ2 = { DeclarationNumber: this.ActNumber == undefined ? '' : this.ActNumber, VinCode: this.vinCode == undefined ? '' : this.vinCode, TransitNumber: this.GovNumber == undefined ? '' : this.GovNumber, }; if ((this.ActNumber amp;amp; this.ActNumber != undefined amp;amp; this.ActNumber != null) || (this.vinCode amp;amp; this.vinCode != undefined amp;amp; this.vinCode != null) || (this.GovNumber amp;amp; this.GovNumber != undefined amp;amp; this.GovNumber != null)) { this.SUB_getDeclarationSearch = this.declarationsService.getDeclarations({ ...searchOBJ, IsFromDashboard: true, PageSize: this.pageSizeDecl, PageNumber: this.currentPageDecl }).subscribe((res) =gt; { this.Declaration_Data = []; let headerPaginDecl = JSON.parse(res.headers.get('X-Pagination')); this.elementsLengthDecl = headerPaginDecl.totalCount; this.currentPageDecl = headerPaginDecl.currentPage; this.pageSizeDecl = headerPaginDecl.pageSize; res.body.map((param) =gt; { this.Declaration_Data.push(param); }); this.DeclarationDataSource = new MatTableDataSourcelt;Elementgt;(this.Declaration_Data); // console.log('Your form data : ', this.DeclarationDataSource); }); } else { this.SUB_getDeclarationSearch = this.declarationsService.getDeclarations({ ...searchOBJ, IsFromDashboard: true, PageSize: this.pageSizeDecl, PageNumber: this.currentPageDecl }).subscribe((res) =gt; { this.Declaration_Data = []; let headerPaginDecl = JSON.parse(res.headers.get('X-Pagination')); this.elementsLengthDecl = headerPaginDecl.totalCount; this.currentPageDecl = headerPaginDecl.currentPage; this.pageSizeDecl = headerPaginDecl.pageSize; res.body.map((param) =gt; { this.Declaration_Data.push(param); }); this.DeclarationDataSource = new MatTableDataSourcelt;Elementgt;(this.Declaration_Data); // console.log('Your form data : ', this.DeclarationDataSource); }); } }
Внутри ngoninit вызываются два метода: fillTable() и fillTable2().
Я попытался использовать следующий метод, чтобы прослушивать подписки и ждать их
public testingforkJoin(): void { forkJoin([this.SUB_getActSearch, this.SUB_getDeclarationSearch] ).subscribe(val =gt; console.log("xxxxx", val)); // call some method here as soon as both are done }
Но, как оказалось, forkJoin не может прослушивать подписки, есть ли какой-либо другой способ, аналогичный forkjoin для подписок?
Существуют методы буксировки, которые включают HTTP-запросы, и я хочу дождаться завершения обоих сетевых запросов и что-то сделать, как только они будут завершены.
Ответ №1:
Я обычно объявляю некоторые логические переменные для решения этого типа асинхронной проблемы. В вашем случае это выглядело так:
isSearch: boolean; isDeclarationSearch: boolean;
А затем я инициализировал каждую переменную как false, и в конце каждой переменной я изменяю значение как true, а затем я создаю новую функцию, которая работает, когда оба значения истинны.
Комментарии:
1. Я думаю, что в моем случае это единственный способ сделать это
Ответ №2:
Смысл forkJoin в том, что вы будете подписываться на него, а не отдельно, он вернет весь результат за один раз в подписке
let call: [] = []; call.push(this.declarationsService.getDeclarations1()); call.push(this.declarationsService.getDeclarations2()); call.push(this.declarationsService.getDeclarations3()); forkJoin(call).subscribe((res) =gt; { });
или
forkJoin({ 'prop1' :this.declarationsService.getDeclarations1() 'prop2' : this.declarationsService.getDeclarations2() }).subscribe((result) =gt; { result.prop1; result.prop2 });