reduxForm decorator should have access to props passed to it's wrapped component same as react-redux connect decorator has access to ownProps
See original GitHub issueIn my opinion this module still hasn’t solved a problem with multiple forms on a same page where those forms need to be initialized at render time. Usually, if you have a page with multiple forms you don’t want to connect each and every component with connect, what you want to do is to connect parent component to store and pass values to all forms inside. But the problem is, there is no way to set initialState in that case to all your child forms. Example how I have to do it now:
Profile.js
import React, { Component, PropTypes } from 'react';
import { connect } from 'react-redux';
import { changeEmailFetch, profileUpdateFetch } from '../actions/profile';
import ProfileForm from '../components/ProfileForm';
import ChangeEmailForm from '../components/ChangeEmailForm';
@connect(state => ({
user: state.get('user'),
}))
export default class Profile extends Component {
static propTypes = {
dispatch: PropTypes.func.isRequired,
user: PropTypes.object.isRequired,
};
constructor() {
super();
this.handleChangeEmail = this.handleChangeEmail.bind(this);
this.handleProfileUpdate = this.handleProfileUpdate.bind(this);
}
handleChangeEmail(values) {
const { dispatch } = this.props;
return dispatch(changeEmailFetch(values));
}
handleProfileUpdate(values) {
const { dispatch, user } = this.props;
return dispatch(profileUpdateFetch(values, user.get('id')));
}
render() {
return (
<section>
<ProfileForm onProfileUpdate={this.handleProfileUpdate} />
<ChangeEmailForm onChangeEmail={this.handleChangeEmail} />
</section>
);
}
}
ProfileForm.js
import React, { Component, PropTypes } from 'react';
import { connect } from 'react-redux';
import { Field, reduxForm, propTypes } from 'redux-form/immutable';
import Input from './Input';
import Textarea from './Textarea';
@connect(state => ({
initialValues: {
bio: state.getIn(['user', 'bio']),
firstname: state.getIn(['user', 'firstname']),
lastname: state.getIn(['user', 'lastname']),
},
}))
@reduxForm({
form: 'ProfileForm',
})
export default class ProfileForm extends Component {
static propTypes = {
...propTypes,
onProfileUpdate: PropTypes.func.isRequired,
};
render() {
const { error, handleSubmit, onProfileUpdate, submitSucceeded,
submitting } = this.props;
return (
<form onSubmit={handleSubmit(onProfileUpdate)} noValidate>
<Field
name="firstname"
component={Input}
label="First Name"
type="text"
placeholder="First Name"
maxLength="30"
/>
<Field
name="lastname"
component={Input}
label="Last Name"
type="text"
placeholder="Last Name"
maxLength="30"
/>
<Field
name="bio"
component={Textarea}
label="Bio"
placeholder="Bio"
maxLength="1000"
/>
{submitSucceeded && !submitting && <p>Profile Updated</p>}
{error && <p>{error}</p>}
<button type="submit" disabled={submitting}>Update</button>
</form>
);
}
}
As you can see, I have to connect both files instead of just having to connect Profile.js and pass data as props. For instance, connect function has 4 parameters:
connect([mapStateToProps], [mapDispatchToProps], [mergeProps], [options])
And first 3 parameters are also functions that can access ownProps as one of it’s parameters which gives an option to do something like this:
@connect((state, ownProps) => {
console.log(ownProps);
return {
user: state.get('user'),
};
})
In this case we can access all the props that have been passed down to connect-ed component from it’s parent. Can’t we have same thing with reduxForm decorator, why can’t it be a function that returns config object instead of immediatelly passing config object which doesn’t have access to it’s props? Something in these lines:
@reduxForm(props => ({
form: 'MyForm',
initialState: {
firstname: props.user.getIn('user', 'firstname'),
lastname: props.user.getIn('user', 'lastname'),
},
}))
Problem with connecting each form is that it can never be reused. In this example I really don’t need to reuse ProfileForm with another connect-ed data, but there are examples of it like reusing same form in lists where each list item form has to be initialized to different data from different part of state from store.
Issue Analytics
- State:
- Created 7 years ago
- Reactions:2
- Comments:5 (2 by maintainers)
As I see you only need to map
initialState
from parent props, look at withProps.AFAIK Form configuration already takes values from parent props, so you can pass or map everything you need in form parent.
This thread has been automatically locked since there has not been any recent activity after it was closed. Please open a new issue for related bugs.