redux-form: [v8.1.0] initialValues are undefined at first render
Are you submitting a bug report or a feature request?
Bug Report
What is the current behavior?
When providing inivialValues
, on first render the value specified in initialValues
is undefined
What is the expected behavior?
In v7.4.2 the value passed as initialValue
was available at first render. I couldn’t find any information about it in changelog
so i assume this should work as in v7.4.2.
Sandbox Link
i’ve created a simple component - reduxForm()
is created using an initialValue, then it is passed to the component using connect()
and formValueSelector
. Observe the console.logs:
redux-form@8.1.0 https://codesandbox.io/s/54pn3nvv8n
firstname undefined
firstname john
redux-form@7.4.2 https://codesandbox.io/s/lrk4y97qw9
firstname john
firstname john
Is it a bug or is it now an expected behaviour?
Other information
here’s the code (same as in codesandbox):
const valueSelector = formValueSelector("myform");
const enhance = compose(
reduxForm({
form: "myform",
initialValues: { firstname: "john" }
}),
connect(state => ({
firstname: valueSelector(state, "firstname")
}))
);
class Page extends PureComponent {
render() {
console.log("firstname", this.props.firstname);
return (
<div>
<Field name="firstname" placeholder="firstname" component="input" />
</div>
);
}
}
export default enhance(Page);
About this issue
- Original URL
- State: open
- Created 5 years ago
- Reactions: 35
- Comments: 22
Commits related to this issue
- workaround for https://github.com/erikras/redux-form/issues/4344 — committed to onionful/admin by hsz 5 years ago
Is this being worked on? I think it is a big fat bug, right?
A quick update for those who don’t follow ecosystem updates closely: A few weeks ago
react-redux
publishedv7.0.0-beta.0
which is a massive reworking ofv6
; mostly fixing performance issues but also reverting how child components see state changes made by mounting parent components back to thev5
behaviour:A few people have already tried the new
react-redux
beta release withredux-form
v8 and it fixes this issue. Once it goes gold, should just be a case of updating the dependency for this project and lots of the issues we’re seeing with v8 will be fixed. As a heads up,react-redux
v7 now uses hooks internally so requires React16.8.4
or higherAnother symptom of this problem is now initial call of validate() receives empty object, despite initialValues being passed to the form. So it breaks validations on FieldArrays which previously worked
I would suggest to everyone not to migrate to v8 version. With the new context API lots of things got broken. Let them sort things out first.
We had to roll back to v7 in the end, v8 is a hot mess right now - I’d recommend people don’t use it.
@Olliebaba thx, i also think it’s related, but in #4304 there are also lifecycle methods being mentioned, which adds more complexity into this issue. I think it can be related to “Behavior Changes” (second one) mentioned here: https://github.com/reduxjs/react-redux/releases/tag/v6.0.0 and i’m not sure if this can be so easily fixed in redux-form, but maybe a note should be added into
Breaking Changes
list?However when validating datas, you still have the validate method called twice with empty data => https://codesandbox.io/s/v6xpm1222y
As @jacekkolasa mentioned this is indeed due to changes in react-redux 6. When the parent form component mounts it dispatches an action to set the
initialValues
, however the child components (including theField
s) use the state before the dispatch occured, meaning that they don’t see theinitialValues
. This is intentional in react-redux 6 to prevent what is known as “tearing” where child components get a different version of state than their parents. Most of the time this is great and prevents a whole class of bugs but not in our use case.There is a great detailed discussion of the problem here https://github.com/reduxjs/react-redux/issues/1126
Interestingly there is a workaround provided in this comment https://github.com/reduxjs/react-redux/issues/1126#issuecomment-447341725 - wrapping the
Field
component in a new<ReactReduxContext.Provider>
should give it access to the most current version of the state.I don’t have time to work on a fix right now but hopefully this points somebody in the right direction.
I think I may have the same problem, but with different function in FieldArray component
this.props.fields.getAll() // return null at first as well
Hope you can take a look at this as well
Wrote a simple hoc as a workaround for this issue
Just wrap your field’s component to fix for specific cases, or similar logic can be used to override default
Field
’s behavior. *mb not be suitable for some edge cases, ex. programmatically remove the value at some point.I think this is definatly should be hadnled as a bug at least because
Field
’smeta.dirty
equalstrue
on initial render.Would love to see this one get some attention. This is definitely the biggest issue affecting V8 adoption for us. @erikras , any ideas?
A lot of code is broken at new version and lot of code depends on it right now, and cannot switch to previous
redux-form
version duewithRef
react changes. Need time to move old code tofinal form