0

Lets say I want to make 2 http calls which returns data and I want to call a function only after both the http calls have returned data so I can merge both the data.

 ngOnInit(): void {
    this.getData();
  }



getData() {

this.func1();
this.func2();
this.func3();

}

async func1() {
 this.service.call1().subscribe((data) => {
    this.data1 = data;
  });

}

async func2() {
  this.service.call2().subscribe((data) => {
    this.data2 = data;
  });
}

func3() {
//this should only get called when func1 and func2 have finished their http calls.
}
Jay
  • 2,485
  • 6
  • 28
  • 34
  • Please [edit] your question title to something that isn't just a repetition of information available from the tags. Your title should describe the problem you're having or question you're asking in a way that will have meaning to a future user of this site who is scanning a list of search results trying to find a solution to their problem. Your current title does nothing in that regard - it's just a regurgitation of the tags. – Ken White Aug 27 '21 at 02:21
  • @Jay Not sure why you changed the accepted answer. Was there anything missing in my answer? – Alvin Saldanha Sep 01 '21 at 00:21

3 Answers3

4

You should be using RxJS forkJoin to achive what you are trying to do.

forkJoin will wait for all passed observables to emit and complete and then it will emit an array or an object with last values from corresponding observables.

In angular you subscribe (await) to the values of an observable to receive data. In your example, anything in the subscribe would be executed once the response has been received from the server.


If `func3` is not an Observable

forkJoin([this.func1(),this.func2()]).subscribe(results => {
    let data1 = results[0];
    let data 2 = results[1];
    this.func3();
});

If `func3` is an Observable you have to pipe your calls

this.subscription.add(
        forkJoin([this.func1(),this.func2()])
            .pipe(
                switchMap(results => {
                    let data1 = results[0];
                    let data2 = results[1];
                    return func3();  
                 }
            ))
            .subscribe((value3) => {
                // value returned from the func3() observable
            })
    );

Note: Don't forget to unsubscribe all your subscriptions onDestroy.

Alvin Saldanha
  • 886
  • 9
  • 20
2

here is the latest syntax in angular

    forkJoin([httpcall1,httpcall2... httpcalln])
          .subscribe((resultArray) => {

            //once the data are recived they will be in the result array in order of the call
            console.log(resultArray[0]);
            console.log(resultArray[1]);
            
});
thanzeel
  • 431
  • 4
  • 12
-1

You can call func2 inside func1 after getting the data, and func3 inside func2 so it will work one by one

getData() {
this.func1();
}

func1() {
this.service.call1().subscribe((data) => {
   this.data1 = data;
this.func2();
});

func2() {
this.service.call2().subscribe((data) => {
   this.data2 = data;
this.func3();
});

func3() {
// Your code here
}
Williamz007
  • 31
  • 1
  • 5