I am programming an Angular application, which talks to a REST-like backend.
The UI consists of a master/detail page, where an element is selectable on the left side and the details are shown to the right. Using angular router, router outlet etc.
The selectable items show a summary of the details. When the detailed item is edited, I want to update the selectable item with the updated information.
I have an api service which uses HttpClient to fetch the values from the backend.
api.service.ts
public getAllItems(): Observable<Item[]> {
return this.http.get<Item[]>(this.apiUrl + '/items')
.map(response => {
return response.map((item) => new Item(item));
});
}
I also have a data service which currently just returns the observable from the api service.
items-data.service.ts
get items$(): Observable<Item[]> {
return this.api.getAllItems();
}
The master (left-side) component just registers the data service observable.
item-master.component.ts
data$: Observable<Item[]>;
constructor(private itemsDataService: ItemsDataService) { }
ngOnInit() {
this.data$ = this.itemsDataService.items$;
}
The template uses async pipe and iterates the array to show the summary.
item-master.component.html
<div *ngIf="(data$ | async) as data">
Using this method, the selectable item is not updated automatically when an item is updated in the application.
Now, I am considering changing the data service such that I have an internal Subject which can be observed. When an update is performed through a method in the data service, I can call subject.next() to inform about a change. BUT this application is also used concurrently by other people on other machines/browsers.
Ideally I would like to refetch the data from the backend, but a Subject will effectively act as a "cache" only triggering the first call to the api. How do I most effectively make sure that I fetch the most recent data from the backend and also get updates from changes made locally?
Assuming I got your question right, I will change the service to something like this (this is a very schematic description):
Whenever you click on an item in the master view, it will call the
loadItem()method which will fetch the specific value and pipe it to thecurrentItem$.This gives you a more service oriented (with store) approach, meaning, you tell it to load an item and consume the item at the exposed observable