Дизайн-опрос о правильном использовании понятия побочного эффекта ngrx / effects

Я пишу это, чтобы знать, правильно я понял или нет.

В примерах, найденных в Интернете, шаблон обычно выглядит следующим образом (здесь пример действий по добавлению / удалению в состоянии и в удаленной базе данных):

эффекты.ts:

@Effect()
add$ = this.action$
  .ofType(ADD)
  .switchMap((action: Action) => {
     return this.http.put(...)
       .map( response => response.json() )
       .map( response => Observable.of({ type: ADD_SUCCESS, payload: action.payload }))
       .catch( response => Observable.of({ type: ADD_FAIL, payload: response.status }))

reducer.ts

...
switch (action.type){
  case 'ADD_SUCCESS':
     ...
     return new_state;
  case 'ADD_FAIL':
     return state;
}

Это работает, но скорость выполнения, которую ощущает пользователь, зависит от скорости сети. Поэтому я придумал шаблон, который делает ставку на высокую вероятность того, что API не вернет ошибку:

reducer.ts

...
switch (action.type){
  case 'ADD':
     ... // make the adequate addition
     return new_state;
  case 'ADD_FAIL':
     ... // delete the addition previously made
     return new_state;
}

эффекты.ts:

@Effect()
add$ = this.action$
  .ofType(ADD)
  .switchMap((action: Action) => {
     return this.http.put(...)
       .map( response => response.json() )
       .catch( response => Observable.of({ type: ADD_FAIL, payload: action.payload }))

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

Но я еще не нашел этот дизайн в примерах, приведенных в Интернете: поскольку я начинающий разработчик, мне интересно, не пропустил ли я что-то, что в конечном итоге делает его неправильным / опасным / неэффективным.


person Gwendo    schedule 31.03.2017    source источник


Ответы (1)


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

Но в этой ситуации, если проблема пойдет не так, пользователь все равно не узнает об этом, пока действие не завершится. В сценарии действительно медленной сети и наличия как SUCCESS, так и FAIL действий, пользователь более уверен в имеющихся данных, потому что действие SUCCESS должно было сработать. Если вы пропустите действие SUCCESS, тогда пользователь может работать вдали и не знать, что его данные неверны, пока не произойдет действие FAIL. Результат может быть незначительным или может прервать рабочий процесс пользователя.

В общем, время, необходимое для отправки запроса put или post и получения ответа, должно быть довольно коротким. И ваши SUCCESS или FAIL действия не должны быть настолько большими, чтобы их вычисление занимало много времени.

Возьмем, к примеру, кассовую систему. Пользователь переходит на кассу и posts на сервер. Вы не хотите переходить на страницу подтверждения, пока не узнаете, было ли сообщение успешным или нет. Поэтому в этой ситуации необходимы отдельные действия SUCCESS и FAIL.

Я думаю, что это обеспечивает лучший пользовательский опыт, чтобы убедиться, что данные, которые они видят, точны и не откатываются изменения после сбоя. Если пользователь posts или puts что-то на сервере, действие SUCCESS должно добавить это в состояние приложения, а не раньше, а также возможное уведомление пользователя. Действие FAIL будет обрабатывать уведомление пользователя, потенциальную регистрацию и т. Д. В зависимости от приложения.

Другой пример: предположим, что пользователь редактирует онлайн-профиль. Если они нажмут «Сохранить», вы хотите, чтобы пользователь был уведомлен об успешном сохранении на сервере. Таким образом, они не уходят со страницы, думая: «Надеюсь, она сохранена, я не получил ответа».

Я бы сказал, что в большинстве сценариев уместно иметь как действия SUCCESS, так и FAIL. Но, как я уже сказал, все зависит от вашего приложения и того, что приемлемо для ваших пользователей в вашей среде.

Надеюсь, это поможет.

person Tyler Jennings    schedule 31.03.2017
comment
Спасибо Тайлеру за быстрый и точный ответ. Я согласен с приведенными вами примерами, что классический дизайн лучше. В предлагаемом дизайне и для некритичных данных, поставленных на карту (например, в моем проекте), я буду работать над тем, чтобы предоставить пользователю правильный пользовательский интерфейс, чтобы он / она понимал, что его / ее действие не было выполнено. - person Gwendo; 31.03.2017