Как обновить значение поля после действия, отправленного с помощью redux

Я хотел бы заполнить форму после вызова ajax с помощью redux.

Мой случай довольно прост:

  • У меня есть простая форма пользователя (пока только с одним текстовым полем), это представление реакции, привязанное к состоянию с помощью connect().
  • Я вызываю API отдыха, чтобы вызвать пользователя.
  • Когда вызов api выполнен, действие отправляется с пользователем.
  • Редуктор обновляет состояние хранилища вместе с пользователем.
  • Я хочу заполнить / обновить форму полученными значениями.

Решение 1.

Если я установлю значение из реквизита следующим образом:

const Field = ({ field, onFieldChange, value }) => (
  <input 
    value={value} 
    onChange={(event) => { onFieldChange(field, event.target.value) }} 
    type="text" 
  />
)

Это работает, но я получаю это предупреждение:

Field is changing an uncontrolled input of type text to be controlled. Input elements should not switch from uncontrolled to controlled (or vice versa).

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

Я также пытался использовать свойства defaultValue, но они используются только при создании компонента (а пользователя у нас еще нет). После возврата вызова ajax нельзя вызвать defaultValue.

Решение 2:

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

Я действительно считаю, что иду в неправильном направлении и что путь должен существовать лучше.

Кто-нибудь уже сталкивался с подобной проблемой?


person Julien Sanchez    schedule 20.09.2016    source источник


Ответы (2)


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

Чтобы исправить это, убедитесь, что вы передаете на вход хотя бы пустую строку, а не undefined

const Field = ({ field, onFieldChange, value }) => (
  <input 
    value={value || ''} // <- add fallback value here
    onChange={(event) => { onFieldChange(field, event.target.value) }} 
    type="text" 
  />
)
person just-boris    schedule 20.09.2016
comment
Отлично, исправил. Я был в таком отчаянии, спасибо большое! - person Julien Sanchez; 21.09.2016

  1. На самом деле вы можете попытаться сделать свой компонент с полным состоянием - хранить и управлять значением ввода внутри него (говорят нормально).
  2. Или, если вам действительно нужно это значение в магазине, используйте redux-form, у меня действительно хороший опыт его использования (вам придется писать меньше шаблонного кода). Кстати, вам не нужно будет использовать какие-либо настраиваемые плагины, вы можете использовать initialValues, см. Подробнее здесь

Приведенное выше решение наверняка сработает, но это не кажется приятным.

person kitos    schedule 20.09.2016
comment
initialValues ​​не работает с сокращенной формой, потому что, когда я инициализирую форму, пользователь еще не извлекается. Таким образом, форма инициализируется пустой, и я не могу ее обновить позже. - person Julien Sanchez; 21.09.2016
comment
@JulienSanchez, если вы посмотрите на пример, который я вам показал, вы увидите, что форма также инициализируется асинхронно (при нажатии кнопки). Более того, форма может быть инициализирована столько раз, сколько вы хотите, отправив действие INITIALIZE самостоятельно (с помощью создателя действия, предоставленного redux-form) - person kitos; 22.09.2016
comment
Ага, видел это, но по кнопке внутри формы. Так просто, что вы можете отправлять сообщения из формы. Кроме того, я считаю нецелесообразным отправлять внутреннее событие извне формы: / - person Julien Sanchez; 24.09.2016
comment
Вам не нужно ничего отправлять. Вы должны определить свои initialValues ​​только для того, что они будут загружены: - person kitos; 25.09.2016
comment
Вам не нужно ничего отправлять. Вы должны определять свои начальные значения только для того, что они будут загружены: github.com/kitos/web-purple/blob/master/src/containers/ - person kitos; 25.09.2016