-
-
Notifications
You must be signed in to change notification settings - Fork 1.6k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Dynamic form name #603
Comments
Oooh, subtle nuance here! When it says "or passed in as props to your component at runtime", it means "passed in as props to your decorated component", where "your decorated component" is the result of the Did that make any sense? |
It's not just I understand that I don't reference state, but since it's just high-order component, I don't see any problem with it. Anyway, you're right, I can pass |
Damn, you got me there. Well played. 😄 The difference is that |
Ah, right! So we have three places: Component props, config and |
Sure, if you can figure out a cogent way to state it. 😄 If you prefer to forego GH contributor cred for ease, you're welcome to write a paragraph here and I'll put it in the docs. Up to you. Gonna close this, as I think we're on the same wavelength now. |
@tricoder42 Apart from the obvious Hitchhiker's reference, is your username also a reference to the tricorder? That's some serious geek points. 👍 |
@erikras It is! Tricoder42 == Triathlon + Programmer + StarTrek reference + Tricoder at GitHub is already taken |
For anyone else who finds this issue and wants a solution, here's what I'm doing:
This is sorta pseudocode, but the gist here is that you wrap your redux form wrapped component in yet another redux-connected component that just maps passed props (or state) to the props passed into the form component. This way you can have component-local logic for determining a dynamic form. |
I'm writing a basic CRUD and I need my form to adopt the entity's ID, here's what I'm doing (same idea as @staab) const Entity = connect(
(state, { routeParams }) => ({
form: routeParams.entityId || 'new-entity',
})
)(
reduxForm()(() =>
<form>
<Field name="hello" type="text" component="input" />
{' '}
<Link to="/entities/a">a</Link>
{' '}
<Link to="/entities/b">b</Link>
</form>
));
const Routes = (
<Route component={Layout}>
<Route path="/entities/:entityId" component={Entity} />
</Route>
); I can type in the form for "a": But if I navigate to "b" I cannot write anything and the actions are sent to the wrong form: Any idea? |
+1 |
I think the bottom line is that React is right when they say that https://facebook.github.io/react/docs/context.html Because I had so much weird issues with redux-form I ended up writing my own project-specific form library (not that costly by the way), and realized everything becomes very weird once you start messing with the context (which is the thing that is used to propagate form name to form form fields). |
I was looking for a way to pass just the form name and wanted to share how I used @staab solution. I am using same component for filling in optionally address in few forms, that is why passing name of the form in props made a lot of sense:
|
The form name can be a prop to the decorated component. |
- Using reduxForm() within render() causes DOM to get thrown away, and has weird side effects like redux-form/redux-form#1944. See redux-form/redux-form#603 (comment) - Refactored <FormBuilderLoader> as a separate container component which connects to redux and redux-form. This keeps the <FormBuilder> component dependency free and easy to test. It'll also be an advantage if we switch to a GraphQL backed component, in which case the async loading routines will look very different from the current <FormBuilderLoader> implementation - Refactoring out the redux-form dependency from FormBuilder to make it more testable (through baseFormComponent and baseFieldComponent) - Passing through 'form' to allow custom identifiers (which is important because currently the schema "id" contains the record identifier, making the form identifier non-deterministic - which means you can't use it with the redux-form selector API)
- Using reduxForm() within render() causes DOM to get thrown away, and has weird side effects like redux-form/redux-form#1944. See redux-form/redux-form#603 (comment) - Refactored <FormBuilderLoader> as a separate container component which connects to redux and redux-form. This keeps the <FormBuilder> component dependency free and easy to test. It'll also be an advantage if we switch to a GraphQL backed component, in which case the async loading routines will look very different from the current <FormBuilderLoader> implementation - Refactoring out the redux-form dependency from FormBuilder to make it more testable (through baseFormComponent and baseFieldComponent) - Passing through 'form' to allow custom identifiers (which is important because currently the schema "id" contains the record identifier, making the form identifier non-deterministic - which means you can't use it with the redux-form selector API)
- Using reduxForm() within render() causes DOM to get thrown away, and has weird side effects like redux-form/redux-form#1944. See redux-form/redux-form#603 (comment) - Refactored <FormBuilderLoader> as a separate container component which connects to redux and redux-form. This keeps the <FormBuilder> component dependency free and easy to test. It'll also be an advantage if we switch to a GraphQL backed component, in which case the async loading routines will look very different from the current <FormBuilderLoader> implementation - Refactoring out the redux-form dependency from FormBuilder to make it more testable (through baseFormComponent and baseFieldComponent) - Passing through 'form' to allow custom identifiers (which is important because currently the schema "id" contains the record identifier, making the form identifier non-deterministic - which means you can't use it with the redux-form selector API)
…#5524) - Removed custom form reducers in favour of redux-form (updateField(), addForm(), etc) - Storing 'state' in schema reducer to avoid a separate forms reducer tree (no longer needed for other use cases). This means 'state' is only the "initial state", any form edits will be handled by redux-form internally in the 'reduxForm' reducer namespace - Removed componentWillUnmount() from <Form> since there's no more reducer state to clean up (removed formReducer.js), and redux-form handles that internally - Removed isFetching state from <FormBuilder> since there's now a props.submitting coming from redux-form - Improved passing of "clicked button" (submittingAction), using component state rather than reducer and passing it into action handlers (no need for components to inspect it any other way) - Hacky duplication of this.submittingAction and this.state.submittingAction to avoid re-render of <FormBuilder> *during* a submission (see redux-form/redux-form#1944) - Inlined handleSubmit() XHR (rather than using a redux action). There's other ways for form consumers to listen to form evens (e.g. onSubmitSuccess passed through <FormBuilder> into reduxForm()). - Adapting checkbox/radio fields to redux-forms Need to send onChange event with values rather than the original event, see http://redux-form.com/6.1.1/docs/api/Field.md/#-input-onchange-eventorvalue-function- - Using reduxForm() within render() causes DOM to get thrown away, and has weird side effects like redux-form/redux-form#1944. See redux-form/redux-form#603 (comment) - Refactored <FormBuilderLoader> as a separate container component which connects to redux and redux-form. This keeps the <FormBuilder> component dependency free and easy to test. It'll also be an advantage if we switch to a GraphQL backed component, in which case the async loading routines will look very different from the current <FormBuilderLoader> implementation - Refactoring out the redux-form dependency from FormBuilder to make it more testable (through baseFormComponent and baseFieldComponent) - Passing through 'form' to allow custom identifiers (which is important because currently the schema "id" contains the record identifier, making the form identifier non-deterministic - which means you can't use it with the redux-form selector API)
@TheFullResolution solution is very nice - I wish this was documented somewhere, I'm sure it's a fairly common question Thanks for posting that help |
I'm having a real problem trying to implement the dynamic form names. I'm passing the formName down through the props, but reduxForm doesnt seem to know anything about the state or props values. How do I get around this? |
Got this problem with the latest release See the example: http://www.webpackbin.com/Vkwc8SZzM |
- Removed custom form reducers in favour of redux-form (updateField(), addForm(), etc) - Storing 'state' in schema reducer to avoid a separate forms reducer tree (no longer needed for other use cases). This means 'state' is only the "initial state", any form edits will be handled by redux-form internally in the 'reduxForm' reducer namespace - Removed componentWillUnmount() from <Form> since there's no more reducer state to clean up (removed formReducer.js), and redux-form handles that internally - Removed isFetching state from <FormBuilder> since there's now a props.submitting coming from redux-form - Improved passing of "clicked button" (submittingAction), using component state rather than reducer and passing it into action handlers (no need for components to inspect it any other way) - Hacky duplication of this.submittingAction and this.state.submittingAction to avoid re-render of <FormBuilder> *during* a submission (see redux-form/redux-form#1944) - Inlined handleSubmit() XHR (rather than using a redux action). There's other ways for form consumers to listen to form evens (e.g. onSubmitSuccess passed through <FormBuilder> into reduxForm()). - Adapting checkbox/radio fields to redux-forms Need to send onChange event with values rather than the original event, see http://redux-form.com/6.1.1/docs/api/Field.md/#-input-onchange-eventorvalue-function- - Using reduxForm() within render() causes DOM to get thrown away, and has weird side effects like redux-form/redux-form#1944. See redux-form/redux-form#603 (comment) - Refactored <FormBuilderLoader> as a separate container component which connects to redux and redux-form. This keeps the <FormBuilder> component dependency free and easy to test. It'll also be an advantage if we switch to a GraphQL backed component, in which case the async loading routines will look very different from the current <FormBuilderLoader> implementation - Refactoring out the redux-form dependency from FormBuilder to make it more testable (through baseFormComponent and baseFieldComponent) - Passing through 'form' to allow custom identifiers (which is important because currently the schema "id" contains the record identifier, making the form identifier non-deterministic - which means you can't use it with the redux-form selector API)
Just to detail @TheFullResolution 's solution, this is what I did and it's been working fine. I have a Form which is a Presentational component. And wrap it with reduxForm
And then I have a FormContainer which contains all the logic, like fetching data, handle onSubmit and such, and it will have a formId, passed down as a prop from the parent, which is used as the name of the form in redux-form.
And then use FormContainer like this
then the redux form state will reside in state.form.my_form |
@clu3 👍 I have same solution with you, it's been working fine with me too! |
@clu3 You've made my day. Thank you! |
In order to use Redux's
|
Or with ES6 decorators:
|
I know it has been a while since the last response on the thread, but I'm using import React from 'react'
import { connect } from 'react-redux'
import { reduxForm } from 'redux-form'
const PageOneComponent = () => {}
const PageOneForm = reduxForm({
destroyOnUnmount: false,
forceUnregisterOnUnmount: true,
})(PageOneComponent)
const mapStateToProps = (_, { form }) => ({
form: form || 'leetName',
})
const PageOneFormContainer = connect(mapStateToProps)(PageOneForm)
export default PageOneFormContainer And then, when I render the <PageOneFormContainer form="wizardForTheWin" /> This is the pretty much what you will need. Hope it helps somebody just as it helped me. |
I found this answer useful: https://stackoverflow.com/questions/40509754/how-do-you-pass-in-a-dynamic-form-name-in-redux-form#40688745
|
I think you can directly pass a prop named <PageOneForm form="custom-name" /> |
According to docs:
However, when I try to use dynamic form name based on ID (which doesn't change), I see
form: undefined
in redux-logger for all form related actions.Something like:
When I pass
form
parameter in props (<DynamicForm form={id} />
, everything works.What do I miss?
The text was updated successfully, but these errors were encountered: