Creatable.js mutates props.options, effectively changing it in parent Component as well
See original GitHub issueThe component Creatable.js
has the function createNewOption ()
which contains the following line
options.unshift(option);
When this executes, it will directly mutate the options
property, something that not only seems like an anti-pattern for React, but can result in a changed value in the Parent component as well.
Given the following example, when onChange is being called after a new option has been created, the options property of the Parent component has already been changed.
class CreatableWrapper extends React.Component {
static propTypes = {
options: React.PropTypes.array.isRequired
}
constructor(props){
this.onChange = this.onChange.bind(this);
}
onChange(newValue) {
const { options } = this.props;
// When a new option has been created in Creatable,
// the options property here has been changed.
console.log({ options });
}
render() {
const { options } = this.props;
return <Creatable {...{ options, onChange: this.onChange }} />
}
}
Is this something that is a temporary but known behaviour that will change in the future? Is it a behaviour that is here to stay, or is it simple a bug?
Issue Analytics
- State:
- Created 7 years ago
- Reactions:11
- Comments:9 (1 by maintainers)
Top Results From Across the Web
Changing a child components state changes the parent ...
When I modify state.object, the props from the parent component change as well. handleObjectChange = (event, key, subkey) => { ...
Read more >Communicating Between Components in React - Pluralsight
It receives a onTitleChange function in the props , sent from its parent. It binds this function to the onChange event on the...
Read more >React Props Cheatsheet: 10 Patterns You Should Know
Prop values must be pure values. In other words, they cannot be mutated or changed directly. We know that in React if we...
Read more >Docs • Svelte
A <script> block contains JavaScript that runs when a component instance is ... If you'd like to track changes to a prop, see...
Read more >Component interaction - Angular
Pass data from parent to child with input bindinglink ... Intercept input property changes with a setterlink. Use an input property setter to...
Read more >
Top Related Medium Post
No results found
Top Related StackOverflow Question
No results found
Troubleshoot Live Code
Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free
Top Related Reddit Thread
No results found
Top Related Hackernoon Post
No results found
Top Related Tweet
No results found
Top Related Dev.to Post
No results found
Top Related Hashnode Post
No results found
If we want the Creatable to “keep track of” the fact that things that were added are valid options, it should either:
Make the user/parent responsible for ensuring that
options
includes all things that have ever been passed toonChange
, if that is the desired behavior. Simply removing the offendingunshift
call and updatingexamples/Creatable.js
to append tothis.state.options
would do the trick.Or, own its own state, and pass down something to the underlying Select like
options: [...options, this.state.createdOptions]
rather than unshifting. However, this should be optional; for instance, if you’re reusing a form multiple times in a row without unmounting it, you may not want your custom value from last time to be autosuggested this time (i.e. if that data could be custom to each record).I’d highly recommend the first approach; the second seems too “magical” for such a reusable component.
The secret to happiness: never upgrade any software