redux-formalize
v0.1.3
Published
Seamless management of stateless forms in your React/Redux app
Downloads
6
Maintainers
Readme
Redux Formalize
Seamless management of stateless forms in your React/Redux app.
Install
yarn add redux-formalize
Setup
:one: Add a form reducer to your root reducer
import {formsReducerCreator} from 'redux-formalize';
const rootReducer = combineReducers({
[...],
forms: formsReducerCreator()
}
:two: Add form meta to your actions
Ensure your asynchronous action triad for submitting the form (pending, success, and failure actions) have the same formName
as given to connectForm
below.
const actionCreators = {
saveFormValues(payload) {
const formName = 'myFormName';
return dispatch => {
dispatch({type: 'SAVE_FORM', payload, formName});
return post('/api/save', payload).then(
response => dispatch({type: 'SAVE_FORM_SUCCESS', payload, response, formName}),
error => dispatch({type: 'SAVE_FORM_FAIL', payload, error, formName})
);
};
}
};
:three: Connect and configure your stateless form:
import {connectForm} from 'redux-formalize';
// your stateless form enhanced with handlers and form state provided by redux-formalize
function Form({fields, updateField, submitForm, state: {isSubmitting, errors}}) {
return (
<form onSubmit={submitForm} onChange={updateField}>
<p>
<label>
A Field:
<input type="text" name="text" value={fields.field}/>
</label>
</p>
<p>
<label>
Another Field:
<input type="radio" name="anotherField" value="foo" checked={fields.anotherField === 'foo'}/>
<input type="radio" name="anotherField" value="bar" checked={fields.anotherField === 'bar'}/>
</label>
</p>
<p>
<label>
Last Field:
<input type="checkbox" name="lastField" value="baz" checked={fields.lastField}/>
</label>
</p>
<p>
<button type="submit" disabled={isSubmitting}>{isSubmitting ? 'Submitting' : 'Submit'}</button>
</p>
</form>
);
}
const fieldNames = ['field', 'anotherField', 'lastField'];
// props are passed to your submit handler including any dispatched wrapped action creators
function onSubmit({saveFormValues, fields}) {
saveFormValues(fields.field, fields.anotherField, fields.lastField);
}
// connect the form
export default connectForm('myFormName', fieldNames, onSubmit, {actionCreators})(Form);
That's it! :tada:
Redux Formalize will wrap your stateless form in a higher-order component that passes field values and form management functions as props to your form. Furthermore, actions dispatched with a connected form's name will have it's state automatically reduced and passed to your form as a state prop.
API
formsReducerCreator([config])
config
- an optional object to configure the action type pattern matching of the reducer. Valid settings aresuccessMatch
- a regex to match a successful form action type. Defaults to/_SUCCESS$/
failMatch
- a regex to match a failed form action type. Defaults to/_FAIL$/
Returns a reducer that will reduce new form state when an action is encountered containing the formName
property. If the action type does not match the success or fail regex's defined above, it's assumed to be an action describing a form's "pending" state. Form state is reduced as follows for a given action type:
- Pending:
{isSubmitting: true, errors: undefined}
- Success:
{isSubmitting: false, errors: undefined}
- Fail:
{isSubmitting: false, errors}
whereerrors
is taken from the failed action
The form state is reduced to a property keyed by the formName
provided in the action.
connectForm(formName, fieldNames, onSubmit, [config])
formName
- the name of the form. Any action associated with the form's submission must provide the same name as a property on the action for automatic form state reductionfieldNames
- an array containing all field names of controlled elements within the formonSubmit
- a callback function to be called when the form is submitted. The callback will be passed props containing field values and any action creators or handlers passed in the config defined below along with any custom props passed in on creation of the formconfig
- an optional object to further configure the form. Valid settings areactionCreators
- any action creators required to submit the form. This can be in any format accepted by themapDispatchToProps
argument of react-redux'sconnect
functioninitialState
- an object or function used to override the initial state of the fields in the form. If a function is given, it will be passed the current props and is expected to return an object containing the initial stateshouldResetFormOnProps
- a function that is called with the current props and is expected to return a boolean designating whether or not the form should be reset based on the new props. By default, a function will be provided that simply returnsfalse
if the form is submitting or contains errorshandlers
- a convenience setting to allow for further handlers required to manage the state of the form to be passed in. For example, some custom form element components don't bubble anonChange
event that the parentform
can handle so instead a handler can be provided that usesupdateForm
to manually save the new field to state. The format of the handlers must conform to thehandlerCreators
defined in recomposeswithHandlers
function
Returns a higher-order component that will supply the wrapped stateless form with the following props:
fields
- an object containing the values of all controlled form fields with the field names as the keysstate
- an object containing the state of the form. It will be comprised of anisSubmitting
boolean indicating whether the form is submitting or not and, on failed form submissions, anerrors
object taken from the failed form actionsubmitForm
- a function to be used to handle the form'ssubmit
event. The function will simply prevent the event's default behaviour from executing before calling the suppliedonSubmit
function passed toconnectForm
updateField
- a function to be used to handle the form elements'change
event. It can either be placed on each form element or on the parent form to handle anychange
events via bubblingupdateForm
- a convenience function which can be used to manually update form elements that either don't firechange
events or may require specific processing to extract the required value before saving to state. Use this in combination withhandlers
defined above for custom form element change handling
Example
yarn && yarn start
:thumbsup:
Use Redux DevTools to monitor the actions and state changes on form submission.