Estoy conectando un observable, que transmite una variedad de, digamos, comida. Necesito conseguir el último cocinero, la última cocina y el último cuchillo para preparar cada uno de estos alimentos. Estos tres valores son valores obtenidos por un observable como getCookById(food.cook.id). ¿Cómo podría mapearlo así:
{ foodItem, cook, kitchen, knife }Actualmente, obtengo una serie de elementos vacíos haciéndolo así:
const foodObservable = new Subject(); foodObservable.pipe( map(foodItems => { return foodItems.map((foodItem: any)=>{ const cookObservable = new Subject(); const kitchenObservable = new Subject(); const knifeObservable = new Subject(); combineLatest(cookObservable, kitchenObservable, knifeObservable).subscribe(([cook, kitchen, knife]) => { return { foodItem, cook, kitchen, knife }; }); }) }) ).subscribe(foodPreparationArray=>{ console.log(foodPreparationArray) // array of empty values :( })Según su condición y su comentario, sugeriría los siguientes cambios
Necesitaría usar un operador de mapeo de orden superior como switchMap para mapear de un observable a otro. El operador de map se utiliza para transformar los datos emitidos.
Usar Firebase get() en lugar de valueChanges() sería una mejor opción. Supongo que necesita el valor en este momento y no necesita observar ningún cambio en la propiedad. Vea aquí para más información.
El uso de get() en lugar de valueChanges() nos proporciona observables que se completan en lugar de transmitir. Entonces podría reemplazar combineLatest con forkJoin .
Necesitarías dos forkJoin s. El primer forkJoin es para activar solicitudes para cada elemento de la matriz foodItems y el segundo forkJoin es para activar solicitudes para cook , knife y kitchen simultáneamente.
Finalmente, podría usar el operador de map para combinar todo.
Prueba lo siguiente
foodObservable.pipe( switchMap((foodItems: any) => // <-- RxJS `switchMap` operator forkJoin( foodItems.map((foodItem: any) => // <-- JS `Array#map` function forkJoin({ cook: db.collection('cook').doc(foodItem.cookId).get(), kitchen: db.collection('kitchen').doc(foodItem.kitchenId).get(), knife: db.collection('knife').doc(foodItem.knifeId).get() }).pipe( map(({cook, kitchen, knife}) => ({ // <-- RxJS `map` operator ...foodItem, // <-- spread operator cook: cook, kitchen: kitchen, knife: knife )}) ) ) ) ) ).subscribe({ next: (foodPreparationArray: any) => { console.log(foodPreparationArray); }, error: (error: any) => { // handle error } });