Combinar múltiples Observables condicionales para preparar los datos
Tengo dos storesque necesito para preparar los datos combinados.
- Para obtener todos los departamentos (para ex 50 departamentos)
- Para obtener todos los usuarios (ex:
1000usuarios)
Quiero fusionar los datos y preparar los datos finales. Nota: el departamento requeriría que se carguen todos los usuarios (lo que puede llevar algún tiempo) y, userssin darse cuenta, no pueden hacer nada por sí mismos, ya que necesitan departmentdatos para preparar el resultado final.
Aquí es para department:
this.store.select(getUserInfo).subscribe((info) => {
this.store.select(getAllDepts).subscribe((depts) => {
if (depts.length < 1) {
this.store.dispatch(loadDeptStore({ accountId: info.acntId}));
} else {
console.log(depts); // get Dept data
}
});
})
para los Usersdatos que tengo:
this.store
.select(getUserInfo)
.pipe(
flatMap((info) => {
this.acntName = info.acntId;
return this.store.select(getAllUsers, { accountId: info.acntId });
})
)
.subscribe((res) => {
if (res.length < 1 ) {
this.store.dispatch(loadUsersInAccountStore({ billingCrmAccountId: this.acntName }));
} else {
console.log(res); // get users data
}
})
¿Debo usar combineLateso algo más, si es así, cómo debo hacerlo de manera reactiva usando las funciones de RxJS?
Respuestas
Primero, no realice una suscripción en una suscripción, es un anti-patrón. Utilice siempre observables más altos. No sé exactamente cómo funciona el código ya que no uso ngrx pero podrías construir tus observables así:
const userInfo$ = this.store.select(getUserInfo); userInfo$.pipe(
mergeMap(info => {
this.acntName = info.acntId;
const departments$ = this.store.select(getAllDepts) .pipe( map(depts => { if (depts.length < 1) { return this.store.dispatch(loadDeptStore({ accountId: info.acntId})); } else { return depts; // get Dept data } }) ); const users$ = this.store.select(getAllUsers, { accountId: info.acntId })
.pipe(
map(res => {
if (res.length < 1 ) {
return this.store.dispatch(loadUsersInAccountStore({billingCrmAccountId: this.acntName }));
} else {
return res; // get users data
}
})
);
return combineLatest([departments$, users$]);
}),
map(([depts, users]) => {
// do stuffs and return something
})
).subscribe(res => console.log('results: ', res));
CombineLatest emitirá cuando ambos observables hayan emitido una vez. Emitirá de nuevo cada vez que uno de los observables emita.
Puede que no funcione con su implementación actual, pero tiene la idea de cómo combinar dos observables de una fuente.