Reputation: 261
I'm creating a to-do in react to practice certain concepts, and I'm currently trying to have my list items as a separate component to help make the state iteration cleaner with having check boxes and add/remove buttons for each item on the list.
When iterating over the state to create each list item, I am trying to pass the id of each item to the list in order to have a unique id for each li element as requested by react. My code is currently as follows:
App.js
function App() {
const [items, setItems] = useState([
])
const addItem = (item) => {
if(item === '') {return}
setItems([...items, { item, id: uuid() }])
}
return (
<Layout>
<div>
<h1>To-Do</h1>
<Input addItem={addItem}/>
<ul>
{items.map(i => (
<ListItem
id={i.id}>
{i.item}
</ListItem>
))}
</ul>
</div>
</Layout>
);
}
ListItem.js
const ListItem = (props) => {
return (
<li key={props.id}>{props.children}</li>
)
}
I am using react-uuid to create the unique id's. The id's are showing properly when listed out from the state, so they are there. But they aren't passing correctly as a prop from App.js to ListItem.js for some reason. When I add new items to the list, I receive the "Warning: Each child in a list should have a unique "key" prop."
Any ideas why this error is happening?
Upvotes: 2
Views: 1471
Reputation: 1317
React uses keys in order to uniquely identify siblings in a list. Why you might ask? Because React will try to update the DOM as little as possible with only the elements that have been changed / added / removed. See more details in the React documentation.
So whenever you use map, make sure to add keys:
items.map(i => <ListItem key={i.id} />);
No need to add a key when implementing ListItem.
Upvotes: 2