1

I'm new to angular and I've been trying to use http.get to get data from an API and assign it to a value in a component

This is the method which is used to get data

  public getByUserName(username:String):User{

     let res:CommonResponse;

     this.http.get<CommonResponse>(BASE_URL+'/'+username)
    .subscribe(  (response) => { res = response },
      error => this.errorHandler.handleError(error)
    )
    console.log("Response "+ res)
    return res.responseObj;
  }

When I print the result inside the subscribe function I get the result

But when I've tried to assign it to a local variable and return responseObj from res.

but the res object is undefined. Is there any other way to archive this functionality

UserR
  • 391
  • 1
  • 6
  • 13
  • 1
    You can't reach data outside of subscribe .it is async – mr. pc_coder Sep 05 '20 at 11:48
  • Does this answer your question? [How do I return the response from an asynchronous call?](https://stackoverflow.com/questions/14220321/how-do-i-return-the-response-from-an-asynchronous-call) – jonrsharpe Sep 13 '20 at 11:26
  • I was looking for a way to do this with Observables without using promises – UserR Sep 14 '20 at 20:49

3 Answers3

2

The reason you dont get any response is that all the HTTP method is async

You have two options to handle the problem

Use the observable provided by angular on itself

let res:ReplaySubject<CommonResponse>=new ReplaySubject(); 

public getByUserName(username:String):User{    
    this.http.get<CommonResponse>(BASE_URL+'/'+username)
    .subscribe(  (response) => { this.res.next(response) },
      error => this.errorHandler.handleError(error)
    )
  }

and then you can use the res REplaySubject to subscribe in your component.

Or if you are not really familiar with RxJs and Observables/ReplaySubject a simpler method is to convert the request to a promise and use await

public async getByUserName(username:String):User{
     let res:CommonResponse;    
     res= await this.http.get<CommonResponse>(BASE_URL+'/'+username).toPromise()
          .catch((error)=>{
              this.errorHandler.handleError(error)
                 })
      console.log("Response "+ res)
      return res.responseObj;
}
Sándor Jankovics
  • 738
  • 1
  • 6
  • 19
0

You should move your console/return statement inside the subscribe like this:

public getByUserName(username:String):User{
this.http.get<CommonResponse>(BASE_URL+'/'+username).subscribe(  (response) => {
  console.log("Response "+ res);
  return res.responseObj;
},
error => this.errorHandler.handleError(error)

);

Your function won't wait for the subscribe to complete because it's asynchronous. That's why it's undefined when you try to access responseObj outside the subscribe.

munzld
  • 279
  • 4
  • 9
0

Ideally you should return res.responseObj within the subscribe method. Or you can try -

 public getByUserName(username:String):User{

 let res:CommonResponse;

 return this.http.get<CommonResponse>(BASE_URL+'/'+username)
.subscribe(  (response) => { res = response.responseObj },
  error => this.errorHandler.handleError(error)
)

}

Shivani
  • 64
  • 1
  • 5