Props vs State in React
By Flavio
Tagged: React
Understand props vs state in React: props come from the parent and stay read-only, while state is owned by the component with useState.
In a React component, props are values passed to it by its parent. State is data the component owns and can change.
Props come from the outside. State lives inside.
Class components still work, but React lists them under legacy APIs. New code uses function components. You read props from the function argument, not this.props.
Props come from the parent
A parent includes a child and passes values the same way you pass HTML attributes:
function ColorSwatch({ color }) {
return <p>Selected color: {color}</p>
}
function App() {
return <ColorSwatch color="green" />
}
color is a prop. ColorSwatch reads it. It does not change it.
You can pass any JavaScript value: a string, a number, an object, an array, a function.
Most of your components will just display information based on the props they received, and stay stateless.
State belongs to the component
When the component needs to remember something after a click or a keystroke, that value is state. You add it with useState:
import { useState } from 'react'
function Counter() {
const [count, setCount] = useState(0)
return (
<button onClick={() => setCount(value => value + 1)}>
Clicked {count} times
</button>
)
}
count starts at 0. Each click asks React to render again with the new number. That memory is local to this Counter. Two counters on the page keep two separate counts.
State can start from a prop:
function ColorSwatch({ color }) {
const [label, setLabel] = useState(color)
return (
<button onClick={() => setLabel('blue')}>
{label}
</button>
)
}
useState(color) reads color only for the first render. If the parent later passes color="red", label stays 'green' until setLabel runs. Do not copy a prop into state unless you really want a one-time initial value.
If the UI should follow the prop, use the prop. Do not store it.
Props never change in the child
A child that needs to change a value should not write to the prop. Either the value is its own state, or the parent owns it and passes a function down:
function ColorSwatch({ color, onPick }) {
return (
<button onClick={() => onPick('blue')}>
{color}
</button>
)
}
function App() {
const [color, setColor] = useState('green')
return <ColorSwatch color={color} onPick={setColor} />
}
The parent holds the state. The child asks for a change through onPick.
When to use which
Use props when the parent already has the value, or when the child is only displaying data.
Use state when this component is the one that changes the value: a typed input, an open/closed menu, a selected tab.
If two siblings need the same changing value, lift the state to their parent and pass it down as props. Do not duplicate it.
I wrote more on each side in React Props and The React State.
Want me to talk about your product? You can sponsor this site.