Reputation: 3144
I have a component that receives some props. In the same file, I have some helper functions that also use one of the props. I'd like to save the prop value inside a variable in the file.
Is there any reason in terms of functionality or style that I should not do this?
Here's some pseudo code to show what I'm talking about, representing the whole file:
// imports go here
let unscopedVar = null
const myOnBlur = (ev) => {
console.log(unscopedVar)
console.log(ev)
}
const MyComponent = (props) => {
unscopedVar = props.someVar
return <input onBlur={myOnBlur} />
}
export default MyComponent
The alternative would be to pass more variables to the functions, but I'd like to avoid that. In my real code, more than one function needs the variable, and they each take more than one other parameter:
// imports...
const myOnBlur = (ev, unscopedVar) => {
console.log(unscopedVar)
console.log(ev)
}
const MyComponent = (props) => {
return <input onBlur = {(ev) => myOnBlur(ev, props.someVar)}
}
Upvotes: 0
Views: 221
Reputation: 101662
Probably the biggest problem with that approach is that there will only ever be one instance of that variable. If there are multiple instances of your component, then they will all be fighting over the value of that variable and messing up each others' data.
So generally you shouldn't try to store values outside of your components.
In terms of alternatives, there are several ways you could go about it:
const MyComponent = (props) => {
return <input onBlur = {(ev) => myOnBlur(ev, props.someVar)}
}
this.props
:class MyComponent extends React.Component {
myOnBlur(ev) {
console.log(this.props.someVar)
console.log(ev)
}
render() {
return <input onBlur={this.myOnBlur} />
}
}
MyComponent
function, so that it has access to the same scope:const MyComponent = (props) => {
const myOnBlur = (ev) => {
console.log(props.someVar)
console.log(ev)
}
return <input onBlur={myOnBlur} />
};
If your handler is fairly large and complex, the last option is probably the least ideal because it means a separate copy of the whole handler would be created every time the component is rendered.
Upvotes: 1
Reputation: 15106
This is not a good idea. Your unscopedVar
may be equal to props.someVar
but this is not clear when looking at it's declaration or use. For a toy example it seems harmless, but as your component grows (as they usually do,) it will be harder to keep track of these relations between props and variables.
Another problem arises if you convert your functional component to a class component, after which you'll need to use lifecycle methods to keep the variable in sync with the prop.
If a lot of helper functions use props, you can just use a class component, and access this.props
in the helper functions:
class MyComponent extends React.Component {
myOnBlur = (ev) => {
console.log(this.props.someVar)
console.log(ev)
}
render() {
return <input onBlur={this.myOnBlur} />
}
}
Upvotes: 1