Reputation: 488
I created a Service in Angular2 which is responsible for making REST call to java services and get Array of products using HTTP Observable.
getAll(): Observable<Product[]>{
let data$ = this.http
.get(`${this.baseUrl}/productdata`, {headers: this.getHeaders()})
.map(mapData)
.catch(handleError);
console.log(' object array:' , data$)
return data$;
}
I have then written a subscriber for this Observable in my component and placed inside the ngOnInit() method and wanted to just extract the first product so placed inside ngOnInit().
this.product = this.products[0];
ngOnInit() {
this.productService
.getAll()
.subscribe(
/* happy path */ p => this.products = p,
/* error path */ e => this.errorMessage = e,
/* onComplete */ () => this.isLoading = false);
this.product = this.products[0];
}
But the last operation in OnInit method is causing product to be undefined because of the asynchronous behavior of Observable. Similarly, I am not able to use the property of product to interpolate in HTML component. I want the extraction to be automatic. So can you provide me a way to do that?
Upvotes: 1
Views: 1234
Reputation: 1
Since you are using observables, you can take advantage from all the methods of an observable such as the .map() function which you're already using.
this.productService
.getAll()
.map(products => products[0])
.subscribe(
/* happy path */ product => this.product = product,
/* error path */ e => this.errorMessage = e,
/* onComplete */ () => this.isLoading = false
);
Upvotes: 0
Reputation: 116
You actually answered your own question - since it's asynchronous, your call to this.product = ...
is called immediately, while the observable takes some time to return. Solution is simple:
ngOnInit() {
this.productService
.getAll()
.subscribe(
/* happy path */ p => {
this.products = p;
this.product = this.products[0];
},
/* error path */ e => this.errorMessage = e,
/* onComplete */ () => this.isLoading = false);
}
Include the set inside of the observable callback.
Upvotes: 1
Reputation: 13416
your code:
this.product = this.products[0];
is being executed before it is defined. Move it into your on success function
this.productService
.getAll()
.subscribe(
/* happy path */ p => {
this.products = p;
this.product = this.products[0];
},
/* error path */ e => this.errorMessage = e,
/* onComplete */ () => this.isLoading = false
);
Upvotes: 0