Background
On page load I am making a http get call to obtain some data.
There is a form on the page which submits new data to the APi. The response does not hold the new updated data but the data exist in the database after the form is submitted.
I need to access the data by making a second api call after the form is submitted.
Question
After the form is submitted, how do I make the initial API call again to retrieve current data and then update my view component with it?
Code
On page load I call this function inside
Initial call to retrieve data
ngOnInit() { this.getPaymentMethods() }
Function definition
private getPaymentMethods() {
let params: URLSearchParams = new URLSearchParams();
params.set('api_key', this.apiKeyData);
params.set('email', this.auth.user.email);
return this.http.get(STATICS.API_BASE + STATICS.API_ALL_PAYMENT_METHODS,
{ search: params })
.map((res: Response) => res.json()).subscribe((res) => {
localStorage.setItem('payment_profiles', JSON.stringify(res.payment_profiles));
});
}
Handling Response From Initial Call
Parsing the data object response
this.PaymentMethodKeys = Object.keys(this.pMethodsData);
Inside the view I display the data like this
<div *ngFor="let key of PaymentMethodKeys">
{{pMethodsData[key].card_no}}
{{pMethodsData[key].payment_profile_id}}
</div>
This is the form that is submitted to add new data to database
saveCreditCard(model: Payment, isValid: boolean) {
let params: URLSearchParams = new URLSearchParams();
params.set('api_key', this.apiKeyData);
params.set('email', model.email);
params.set('u_address', model.street_address);
params.set('u_city', model.city_address);
return this.http.get(STATICS.API_BASE + STATICS.API_PAY_METHOD,
{ search: params })
.map((res: Response) => res.json())
.subscribe((res) => {
console.log(res);
});
}
}
I think part of my problem is that I am getting the keys from the object inside the constructor. So I think I keep trying to make this work but the only way it will update the keys is when the component refreshes so the constructor will run again.
Any help would be appreciated.
We discussed Subjects, but that's not necessary. It's sufficient to render the observable in the view and simply pass it new data each time you update your database.
import { Observable } from 'rxjs/Observable';
import 'rxjs/add/operator/take';
private paymentMethods: Observable<any>;
private getPaymentMethods() {
let params: URLSearchParams = new URLSearchParams();
params.set('api_key', this.apiKeyData);
params.set('email', this.auth.user.email);
this.http.get(STATICS.API_BASE + STATICS.API_ALL_PAYMENT_METHODS,
{ search: params })
.map((res: Response) => res.json())
.take(1) //Takes the first observable and unsubscribes
.subscribe(res => this.paymentMethods = res.payment_profiles)
}
saveCreditCard(model: Payment, isValid: boolean) {
let params: URLSearchParams = new URLSearchParams();
params.set('api_key', this.apiKeyData);
params.set('email', model.email);
return this.http.get(STATICS.API_BASE + STATICS.API_PAY_METHOD,{ search: params })
.map((res: Response) => res.json())
.take(1)
.subscribe((res) => {
//Maybe make sure status is 200.
console.log(res);
this.getPaymentMethods();
});
}
ngOnInit() {
this.getPaymentMethods()
}
Note that since we are subscribing to the results of getPaymentMethods()
within the function, it's not necessary for it to return anything and, hence, not necessary for us to assign the returned Observable to paymentMethods
within ngOnInit()
. Whenever getPaymentMethods()
is called (e.g., on the initial load and when saveCreditCard()
is called) paymentMethods
subscribes to the first response emitted and then unsubscribes with the take
operator.
And in your view you'll notice we aren't using the async pipe anymore. Remember that the async pipe subscribes and unsubscribes. We are doing that manually, so there's no need for that.
<div *ngFor="let item of paymentMethods">
{{item.card_no}}
</div>
Let me know how this works out.
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