I have the following situation using Observables in my Angular4 app that I just can't get to work: I want to gather summary data of all my booking days for a overview page. Getting all the days is an Observable, and each day has a list of bookings of that day that I have to retrieve - again an observable source. From this list I calculate a summary of the day. All these summaries I want to emit in a resulting observable.
I have tried lot's of more complicated things, but always the inner observables where not waited on to complete and I got empty summaries. I have gotten back to the basics, and something along these lines should work:
getSummaries(): Observable<BookingDaySummary[]> {
return this.bookingService.getBookingDays().take(1).mergeMap(
days => this.calculateSummaryOfDays(days)
)
};
private calculateSummaryOfDays(days: BookingDay[]): Observable<BookingDaySummary[]> {
const summaries$ = days.map(day => this.calculateSummary(day));
// I'm aware that the next line is not correct.
// Essentially I want the array of observables to complete
// and have an array of the resulting values.
return Observable.merge(summaries$);
}
private calculateSummary(day: BookingDay): Observable<BookingDaySummary> {
// ... logic to get summary from one day
}
However, the type of summaries$
is Observable<Observable<BookingDaySummary>
and not Observable. So it all boils down to: How do I make an Observable<T[]>
from [Observable<T>]
?
Also: Should the most inner method I use in .map
return an Observable or just be a map on the incoming type to T when intending to produce an Observable<T>
?
Alternate of forkJoin means you need to subscribe to the array of observables sequencially. merge and concat are the ways to go in this case. In your case, modify your code and use a spread operator at the very beginning of your array of observables when using merge and concat .
ObservableArray is an array that allows listeners to track changes when they occur.
An Observable is basically a function that can return a stream of values to an observer over time, this can either be synchronously or asynchronously. The data values returned can go from zero to an infinite range of values.
How do I make an Observable< T[] > from Observable< T >[] ?
forkJoin does this. Using String for your T:
import { of, forkJoin} from 'rxjs';
import { Observable } from 'rxjs'
const source:Array<Observable<String>> = [of('A'), of('B'), of('C') ];
const source2:Observable<String[]> = forkJoin(source);
source2.subscribe((res=>console.log(res)));
https://stackblitz.com/edit/arrayofobs2obsofarray?file=index.ts
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