Проблема с действиями React Redux Thunk Chaining

Я делаю приложение для реагирования и с некоторым успехом использую redux с thunk, однако недавно у меня возникла необходимость связать некоторые действия. Проблема, с которой я столкнулся, заключается в том, что даже первый вызов api действия возвращает 422, поэтому я ожидал, что возврат Promise.reject(error); остановит продолжение стека, но он все равно продолжает двигаться вниз по цепочке.

Вот код:

actions.js

вот связанное действие, которое я пытаюсь использовать:

export const resetPasswordAndRefreshUser = (password, password_confirmation) => {
  return (dispatch, getState) => {
    return dispatch(resetPassword(password, password_confirmation))
      .then((result) => {

        //// This shouldn't get executed in resetPassword rejects /////
        //// console.info(result) is undefined ////

        return dispatch(getAuthedUser());

      }, (error) =>{
        // Do Nothing
      }).catch((error) => {
        return Promise.reject(error);
      });
  }
};

И сами определения действий:

export const resetPassword = (password, password_confirmation) => {
  return dispatch => {
    dispatch({
      type: authConstants.LOGIN_RESET_REQUEST
    });

    return AuthService.resetPassword(password, password_confirmation)
      .then((result) => {
        dispatch({
          type: authConstants.LOGIN_RESET_SUCCESS
        });
        dispatch({
          type: alertConstants.SUCCESS,
          message: 'Your new password was set successfully.'
        });
        history.push('/');
      }, error => {
        dispatch({
          type: authConstants.LOGIN_RESET_ERROR
        });
        dispatch({
          type: alertConstants.ERROR,
          message: 'Error: ' + error
        });
      });
  }
};


export const getAuthedUser = () => {
  return dispatch => {
    dispatch({
      type: authConstants.LOGIN_AUTHED_USER_REQUEST
    });

    return AuthService.getAuthedUser()
      .then((result) => {
        dispatch({
          type: authConstants.LOGIN_AUTHED_USER_SUCCESS,
          user: result
        });
      }, error => {
        dispatch({
          type: authConstants.LOGIN_AUTHED_USER_ERROR
        });
        dispatch({
          type: alertConstants.ERROR,
          message: 'Error: ' + error
        });
      });
  };
};

service.js

static getAuthedUser = () => {
    return API.get(config.api.url + '/me')
      .then((response) => {
        // Get Current User From LocalStorage
        const vmuser = JSON.parse(localStorage.getItem('vmuser'));
        if (vmuser) {
          // Update User & Set Back In LocalStorage
          vmuser.user = response.data;
          localStorage.setItem('vmuser', JSON.stringify(vmuser));
        }
        return response.data;
      }).catch(error => {
        return Promise.reject(error);
      }).finally(() => {})
  };

  static resetPassword = (password, password_confirmation) => {
    return API.post(config.api.url + '/reset', { password, password_confirmation })
      .then((response) => {
        return response.data;
      }).catch(error => {
        console.info('reset error');
        return Promise.reject(error);
      }).finally(() => {})
  };

Теперь вызов api Сброс пароля возвращает 422 (как я хочу, для тестирования). Но когда я смотрю на вкладку сетевых запросов, я все еще вижу, что выполняется вызов getAuthedUser, хотя обещание должно быть отклонено в authservice.

Я просто неправильно понимаю обещания и когда должен выполняться .then()?

Похоже, вы сами решили свою проблему, но небольшой совет: не смешивайте promise.then(..., onRejected) и promise.catch(). Под капотом они делают то же самое, и, комбинируя их, вы получите результаты, не соответствующие вашим ожиданиям.

Christopher Moore 04.11.2018 21:54

@ChristopherMoore спасибо за совет, я обязательно удалю один из них. Что предпочтительнее? Думаю, я предполагал, что .catch() перехватит исключения, а (error) => {} отловит отклонения обещаний.

Matthew Brown 06.11.2018 16:49

Они делают то же самое. developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/… - я обычно предпочитаю использовать catch, поскольку это явно указано в его определении.

Christopher Moore 06.11.2018 20:39
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
В настоящее время производительность загрузки веб-сайта имеет решающее значение не только для удобства пользователей, но и для ранжирования в...
Безумие обратных вызовов в javascript [JS]
Безумие обратных вызовов в javascript [JS]
Здравствуйте! Юный падаван 🚀. Присоединяйся ко мне, чтобы разобраться в одной из самых запутанных концепций, когда вы начинаете изучать мир...
Система управления парковками с использованием HTML, CSS и JavaScript
Система управления парковками с использованием HTML, CSS и JavaScript
Веб-сайт по управлению парковками был создан с использованием HTML, CSS и JavaScript. Это простой сайт, ничего вычурного. Основная цель -...
JavaScript Вопросы с множественным выбором и ответы
JavaScript Вопросы с множественным выбором и ответы
Если вы ищете платформу, которая предоставляет вам бесплатный тест JavaScript MCQ (Multiple Choice Questions With Answers) для оценки ваших знаний,...
1
3
61
1

Ответы 1

Ах, я думаю, что нашел правильный способ сделать это благодаря дальнейшему поиску в Google:

в моем комбинированном действии я добавил проверку текущего состояния:

// State Updated, Check If Successful
if (true === getState().auth.resetPassword) {
  return dispatch(getAuthedUser());
}

Итак, полный код комбинированного действия выглядит так:

export const resetPasswordAndRefreshUser = (password, password_confirmation) => {
  return (dispatch, getState) => {
    return dispatch(resetPassword(password, password_confirmation))
      .then((result) => {
        // State Updated, Check If Successful
        if (true === getState().auth.resetPassword) {
          return dispatch(getAuthedUser());
        }
      }, (error) => {
        // Do Nothing
      }).catch((error) => {
        return Promise.reject(error);
      });
  }
};

Другие вопросы по теме