Как мне превратить наблюдаемый набор из двух разных типов в другой третий тип, наблюдаемый в Typescript с помощью rx js? - PullRequest
0 голосов
/ 30 мая 2020

Итак, у меня проблема в том, что я получаю две разные службы, скажем, типа Observable и Observable. Они возвращаются службами и отлично работают при начальной загрузке, делая что-то вроде этого (в конструкторе компонента в Angular)

combineLatest([this.service.A(), this.service.B()])
  ).subscribe(([A, B]) => {
    this.C = A.map(x => {
        return { 
           id: x.id,
           name: x.specificA
        };  //Different type of C 
    }).concat(B.map(x => {
         return {
            id: x.id,
            name: x.specificB
       };
   });

Итак, это работает, когда это делается в конструкторе, а представление загружается с моим «C» в этом примере, и мир прав. Однако я хотел бы время от времени вызывать обновление строк и go полный круг обратно в мою коллекцию, а затем обновлять. Я думал о выполнении combLatest, но без подписки, чтобы получить наблюдаемый компонент чего-то вроде C $: Observable. Затем заставьте этот объект выполнять всю работу по подпискам и дальнейшим обновлениям. Затем выполняю

  this.C$ = ([this.service.A(), this.service.B()]).pipe(map( //this is wrong))

В основном я не хочу подписываться на наблюдаемое, но настраиваю его из других наблюдаемых, ТОГДА подписываюсь на это. Потенциально выполните комбо с rx js, чтобы взять два наблюдаемых типа и создать третий тип. Затем, когда происходит событие обновления, начните подписку на наблюдаемую 'C $'. Я знаю, что это, вероятно, простая операция, я просто не понимаю, что кто-то, кто хорош в rx js, мог бы сказать мне, как комбинировать.

1 Ответ

0 голосов
/ 30 мая 2020

Ваш первый combineLatest кажется почти решением.

Поскольку операция сопоставления для обоих типов различается, сначала я бы создал наблюдаемое для каждого типа, которое сопоставляет их с третьим типом, а затем объединю их с одним наблюдаемым третьего типа.

Давайте go, предположим, что у меня есть эти 3 типа:

interface ModelA { aSpecific: string; }
interface ModelB { bSpecific: string; }
interface ModelC { id: string; }

с этими двумя Observable s из них:

const a$: Observable<ModelA[]> = of([{ aSpecific: "a-1" }, { aSpecific: "a-2" }]);
const b$: Observable<ModelB[]> = of([{ bSpecific: "b-1" }, { bSpecific: "b-2" }]);

Теперь, создайте 2 Observables, которые соответствуют ModelC:

const mappedA$: Observable<ModelC[]> = a$.pipe(map(a => a.map(({ aSpecific: id }) => ({ id }))));

const mappedB$: Observable<ModelC[]> = b$.pipe(map(b => b.map(({ bSpecific: id }) => ({ id }))));

Наконец, объедините их с combineLAtest и mergeAll, чтобы развернуть первый «массив массивов»

const c$: Observable<ModelC[]> = combineLatest(mappedA$, mappedB$).pipe(
  mergeAll()
);

Вы можете найти полный исходный код в this stackblitz

...