Хобрук: Ваш путь к мастерству в программировании

Как отправить несколько действий в ngrx / effect (redux-observable)?

Я использую Angular 6, ngrx / store. У меня такой эффект, что отвечает за обновление вещей. В зависимости от какой-то логики я хочу отправлять разные действия. В чем разница, если я использую switchMap вместо map?

Это то, что я пробовал, но не работает:

 @Effect()
  dispathMultipleActions$ = this.actions$.pipe(
    ofType(ActionTypes.UpdateSomething),
    map(() => {
      const actions: Action[] = [];
      const array = [1, 2, 3, 4, 5];
      array.forEach(item => {
        if (item > 3) {
          actions.push(new DeleteAction(item));
        } else {
          actions.push(new ChangeAction(item));
        }
      });
      return actions;
    })
  );

  • Я думаю, вы хотите попробовать switchMap с функцией, которая возвращает Observable.concat внутренних действий. Это сгладит список действий и учтет порядок. 31.05.2018

Ответы:


1

Эффект преобразует поток действий, поэтому у вас есть поток действий в качестве ввода и вывода. В вашем примере вы сопоставляете действие с массивом действий. Поток массивов действий не является допустимым типом вывода. Вам нужно сгладить этот массив, что означает, что вы не испускаете сам массив в выходной поток, а вместо этого отправляете каждый из его элементов.

Вместо того:

input:  --a-------a------>
output: --[b,c]---[b,c]-->

Ты должен сделать:

input:  --a-------a------>
output: --b-c-----b-c-->

Для сглаживания наблюдаемого массива в Observable каждого элемента вы можете использовать один из операторов mergeMap, switchMap, exhaustMap. В большинстве случаев mergeMap будет правильным выбором. Если вы хотите узнать больше об этих операторах, прочтите этот ответ.

@Effect()
register$: Observable<Action> = this.actions$.pipe(
  ofType(AuthActionTypes.REGISTER_REQUEST),
  mergeMap((action: RegisterRequest) => {
    // check for register request success
    return [
      new RegisterSuccess(),
      new LoginRequest(action.payload)
    ]
  })
);
31.05.2018
  • Здравствуйте, похоже, он больше не работает с NGRX 10: как только я помещаю массив для возврата 2 действий (которые работают отдельно), у меня появляется ошибка TS, в которой говорится, что type [] несовместим с 'Action' ... 08.10.2020
  • В завершение своего комментария: решение выглядит так: `this.store $ .dispatch (RegisterSuccess ()); return LoginRequest (action.payload); 08.10.2020
  • Не могли бы вы уточнить - почему в данном случае массив действий считается массивом наблюдаемых? Действие! = Наблюдаемое. Хотя я тоже использую этот шаблон, и он работает так, как ожидалось 26.01.2021

  • 2

    У меня была такая же ситуация (и предполагая, что NgRx 10 или выше), у меня другая точка зрения, более фундаментальный способ использования эффектов. Последовательный запуск нескольких действий в одном месте, особенно в рамках одного эффекта, является анти-паттерном. По сути, важно поддерживать согласованный общий поток состояний приложения в NgRx действий и потенциалов. сокращения. Так же, как это предусмотрено архитектурой NgRx.

    После 3 правила эффекта уже помогут избежать сложных ситуаций:

    1. Назовите эффекты как название эффекта
    2. Сделайте так, чтобы ваш эффект делал только одно
    3. Выпустить только одно действие

    Таким образом, это поможет вам следовать шаблону проектирования разделения проблем, который, конечно, также поможет вам эффекты NgRx, чтобы сделать их более пригодными для модульного тестирования.

    Вернемся к вашему примеру, вы можете просто отделить то, что вы хотите сделать (2 дополнительных действия), с помощью промежуточного действия.

    В вашем случае кажется, что вам может не понадобиться даже ваш исходный эффект dispathMultipleActions $, если внутри не появится особая логика. (который, возможно, может принадлежать редуктору состояния, который еще более поддается модульному тестированию).

    Предполагая, что ActionTypes.UpdateSomething уже имеет объект полезной нагрузки массива, вы можете разделить свои dispathMultipleActions $ на отдельные, чтобы сделать что-то вроде этого:

    @Effect()
    deleteAction$ = this.actions$.pipe(
        ofType(ActionTypes.UpdateSomething),
        concatMap(from(new Promise((array) => {
            array.forEach(item => {
                if (item > 3) {
                    //do something
                }
            });
        }))),
        {dispatch: false}
    );
    
    @Effect()
    changeAction$ = this.actions$.pipe(
        ofType(ActionTypes.UpdateSomething),
        concatMap(from(new Promise((array) => {
            array.forEach(item => {
                if (item <= 3) {
                    //do something
                }
            });
        }))),
        {dispatch: false}
    );
    
    24.02.2021

    3

    У меня была такая же проблема с Ngrx 10, и решение с возвратом массива, похоже, больше не работает ...

    Мое решение - использовать this.store$.dispatch( myAction(...) )

    `

    mergeMap((action: RegisterRequest) => {
      // check for register request success
    
      // for all actions from 0 to (last -1), use a dispatch() :
      this.store$.dispatch( RegisterSuccess() );
    
      // and the last action is returned:
      return LoginRequest(action.payload);
    

    })

    08.10.2020
  • Хотя возможно, я думаю, что это антипаттерн, см. Мой ответ ниже. 24.02.2021
  • Пожалуйста, объедините документацию, операции должны быть без гражданства и чистыми. Вы нарушаете архитектуру, создавая побочный эффект! 16.07.2021
  • Новые материалы

    Что нужно знать перед тем, как начать свой первый язык программирования
    Что такое язык программирования и зачем он нам? Языки программирования - это то, что мы используем, чтобы указывать компьютерам, что им делать. Языки программирования - это средство, с..

    Нормализация Юникода
    Нормализация Юникода Когда мы разрабатываем код для очистки тегов HTML, мы можем столкнуться с символами Unicode, такими как символы, эмодзи и другие графические символы. Для анализа таких..

    Лучшее машинное обучение как сервисная компания и лучшие варианты использования
    Оригинальная статья была опубликована в блоге CHI Software . Как мы видим, машинное обучение (ML) быстро произвело революцию в том, как сегодня работает бизнес. В связи с растущим спросом..

    Обнаружение и отслеживание транспортных средств
    Путем проб и ошибок я нашел набор параметров HOG . Извлечение признаков и параметры HOG Была создана функция extract_hog_features , которая берет массив изображений размером 64x64x3 и..

    Начало работы с OpenStack
    Начало участия в OpenStack не для слабонервных. Чтобы начать работу, нужно много времени — настройка учетных записей, linux vm, devstack, Gerrit, панель запуска и IRC. Чрезвычайно сложно понять,..

    «Шаг» в вашу особенность огурца
    Этот пост посвящен тому, как уменьшить ваши неудобства при написании определений шагов в огурце с помощью Vim. Когда я пишу свои огуречные истории, я обычно пытаюсь набросать описание шага в..

    Торговая стратегия «Золотой крест».
    Сможете ли вы превзойти рынок, торгуя пересечением скользящих средних 50 и 200? Отказ от ответственности: материал в этой статье предназначен исключительно для образовательных целей и не должен..