UPDATE How I managed to do it is below (scroll to my answer or here's the link): https://stackoverflow.com/a/55013081/1729405
I'm trying to build a APIService in Angular 7. I'm using subscribe to push to an array which I can't access through another service.
Here's the api service method:
getResponse(url):Observable<any> {
return this.http.post(url, '', {responseType: 'text'});
}
getAll() {
this.getResponse(this.todayApiUrl).subscribe(
(response) => {
this.data.push(response);
});
return this.data;
}
Here's how I'm trying to call it in the secondary service:
export class AdsHealthService {
today = this.callResponseApiService.getAll();
constructor(private callResponseApiService: CallResponseApiService) { }
getHealthValue(interval, type) {
let obj = this.today;
console.log(obj);
}
}
In the attached image is what I get when I console.log() the response. It looks like an array but when I try to access the first element, I get an undefined message. What am I doing wrong??

This happens because the http.post is asynchronous, you can make it synchronous by making the getResponse() async, transforming the Observable to Promise by .toPromise() and adding await before the http.post since that the getResponse() will not return Observable but raw data so the .subscribe() is no more necessary.
async getResponse(url) {
return await this.http.post(url, '', {responseType: 'text'}).toPromise();
}
async getAll() {
this.data = await this.getResponse('some url');
return this.data
}
async some() {
const data = await this.getAll();
console.log(data);
console.log(this.data);
}
In your service you would need the following:
async getResponse(url) {
return await this.http.post(url, '', {responseType: 'text'}).toPromise();
}
async getAll(url) {
return await this.getResponse(url);
}
In another service/component, you can retrieve the promise like below. To ensure that you're getting a promise back, you'd need to use a try catch block.
async getToday() {
try {
let today = await this.yourServiceName.getAll(this.todayApiUrl);
return today;
} catch(e) {
console.log(e);
}
}
then call:
let data = this.yourServiceName.getToday();
this.data.then((res) => {
// do stuff with 'res' here.
}
There isn't a way to save the value outside a then scope. To avoid hitting the API multiple times, I set up a cache service so that you can store/retrieve from cache when necessary. Here's the link to the article that I referenced for caching: https://hackernoon.com/angular-simple-in-memory-cache-service-on-the-ui-with-rxjs-77f167387e39
Here's what you can do:
if (!this.cacheService.has('some key')) {
let data = this.yourServiceName.init();
this.cacheService.set('some key', data)
} else {
let cache = this.cacheService.get('data');
// do stuff here.
}
Hope that helps!
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With