Компонент React не получает обновленное состояние из редуктора

#javascript #reactjs #redux #react-hooks #react-component

#javascript #reactjs #redux #реагирующие крючки #реагирующий компонент

Вопрос:

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

Когда я отправляю форму, сценарий успеха работает довольно хорошо. Он отправляет запрос на серверную часть, где пользователь правильно сохраняется в БД! Проблема связана со случаем ошибки, когда пользователь отправляет форму с уже принятым электронным письмом. В этом случае блок if (auth.error) не вызывается, поскольку состояние не получает объект ошибки из редуктора.

 const Signup = () => {
  debug('In the Render shit!');
  const auth = useSelector((state) => state, shallowEqual);
  const dispatch = useDispatch();
  const [values, setValues] = useState({
    name: 'Rahul',
    lastname: 'Kodu',
    email: 'rahul.kodu@entr.co',
    password: '12345',
    success: false,
  });

  const { name, email, password, success, lastname } = values;

  const handleChange = (event) => {
    setValues({
      ...values,
      [event.target.name]: event.target.value,
    });
  };

  const handleSubmit = (e) => {
    e.preventDefault();
    //make thunk call here
    debug('Submit Button Clicked');
    const user = { name, email, password, lastname };
    dispatch(signUpUser(user))
      .then(() => {
        debug('In then of thunk!');
        //Finale
        debug(auth);
        if (auth.error) {
          setValues({ ...values, success: false });
          toast.error('Email Already Taken');
        } else {
          toast.info('🏃 Signed Up! Now Sign in!');
          setValues({
            email: '',
            password: '',
            name: '',
            lastname: '',
            success: true,
          });
        }
        //finale
      })
      .catch((err) => {
        debug('In err of thunk'   err);
      });
  };
  const successMessage = () => {
    if (success) {
      return <Redirect to="/signin"></Redirect>;
    }
  };

  const signUpForm = () => {
    return (
      <div className="row">
        <div className="col-md-6 offset-sm-3 text-left">
          <form onSubmit={handleSubmit}>
            <div className="form-group">
              <label htmlFor="name-field">Name</label>
              <input
                className="form-control"
                type="text"
                id="name-field"
                name="name"
                value={name}
                onChange={handleChange}
                required
              />
            </div>
            <div className="form-group">
              <label htmlFor="name-field">Last name</label>
              <input
                className="form-control"
                type="text"
                id="lastname-field"
                name="lastname"
                value={lastname}
                onChange={handleChange}
                required
              />
            </div>
            <div className="form-group">
              <label htmlFor="email-field">Email</label>
              <input
                className="form-control"
                type="email"
                id="email-field"
                name="email"
                value={email}
                onChange={handleChange}
                required
              />
            </div>
            <div className="form-group">
              <label htmlFor="password-field">Password</label>
              <input
                className="form-control"
                type="password"
                id="password-field"
                name="password"
                value={password}
                onChange={handleChange}
                required
              />
            </div>
            <div className="form-group">
              <button
                type="submit"
                className="btn btn-sm btn-custom btn-block mt-5"
              >
                Sign-up!
              </button>
            </div>
          </form>
        </div>
      </div>
    );
  };

  return (
    <Base title="Signup Page" description="Exisitng user? Goto Signin">
      {JSON.stringify(auth)}
      {signUpForm()}
      {successMessage()}
    </Base>
  );
};
  

Асинхронная часть действия. Часть thunk, как показано ниже. Ошибка в части promise вызывает проблему.

 //thunk
export const signUpUser = (user) => {
  return function (dispatch) {
    dispatch(beginApiCall());

    const options = {
      headers: {
        Accept: 'application/json',
        'Content-Type': 'application/json',
      },
    };

    return axios
      .post(config.API   'signup', user, options)
      .then((response) => {
        debug('In success of axios');
        dispatch(signUpUserSuccess(response.data));
      })
      .catch((err) => {
        debug('In err of axios');
        dispatch(signUpUserFailure(err.response.data));
        dispatch(apiCallError());
      });
  };
};
  

В редукторе я возвращаю новый объект для случаев сбоя (SIGNUP_USER_FAILURE), используя синтаксис spread для воспроизведения по правилам неизменности.

 const authReducer = (state = initialState.auth, action) => {
  switch (action.type) {
    case types.LOAD_PROFILE:
      if (!action.newAuth) {
        action.newAuth = state;
      }
      return action.newAuth;

    case types.SIGNUP_USER_SUCCESS:
      if (!action.user) {
        action.user = state;
      }
      debug(action.user);
      return { ...action.user };
    case types.SIGNUP_USER_FAILURE:
      return { ...state, ...action.error };
    default:
      return state;
  }
};
  

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

Комментарии:

1. Обратный вызов dispatch(signUpUser(user)).then имеет устаревшее закрытие auth , вы можете использовать useEffect перехват для просмотра auth , чтобы вызвать setValues и toast . Или вы можете вернуть auth объект из signUpUser

2. Привет @HMR, спасибо, я попробую это.

3. Привет, ссылка ниже, я нашел ее очень находчивой. css-tricks.com /…