Why Does My React List Need Keys?

Jeremy Wood
5 min readNov 6, 2021

--

Three keys. Each key is a different color: gold, blue, and purple.
Photo by Florian Berger on Unsplash

So you’re building an app with React. It can easily become apparent how useful it is to break your app up into components. The ability to reuse components, and make them abstract and dynamic, is one of the biggest benefit of a framework like React. But if you’ve ever used a loop to build a collection of one specific React component, you’ve likely been scolded in the console for not adding keys to your components.

Let’s say for instance, you have a list of books, and you want to display each book as a separate component. That might look something like this:

Our BookContainer is returning a BookExample component for every book name in our bookList. But if we add this to our React app and open the console, we’ll see this error:

Warning: Each child in a list should have a unique “key” prop.

Check the render method of `BookContainer`.

Our components all rendered fine on the page, why are we getting an error about keys?

This has to do with the way React updates the Dom. One huge benefit of React is that you don’t have to re-render an entire page when you make changes to that page. React is smart enough to find only the elements that have changed, and update only those elements and their children. But it also tries to make that change in the most performant way possible.

React docs assert you can visualize each render method like a tree. When you update a component in React, the previously returned tree is compared to the newly returned tree. The first thing React does is compare the root element. If they are different element types, React knows it can just wipe the whole “tree”, (destroying the old tree any associated state), and display just the new information. But if it finds the same element type, it will only change the properties on the element itself. This is the important first step of rebuilding. Since React components have to return a single element, this check will always run first.

Now that the root node is out of the way, assuming we are truly updating the component and haven’t built a whole new one, React moves on to the children of that node. If those children are non repeating elements, then React will handle them the same way it did the root element. It will recursively move down the children as necessary until all possibly changed nodes have been inspected.

This can become an issue if you get to a list of items. If you were to add something to the beginning of a list, you’ve just created a lot of work for React. It checks the first element of the previous list, compares it to your new item, and has to make that change. Then it gets to the second item on the old list, but the second item on the new list used to be the first item. This means every item in the list is going to be rewritten all the way down. Much like when you unshift() an item onto the beginning of an Array, and every item’s index has to be changed to account for the new placement. This is very inefficient, especially as your list gets longer. This is where the key property finally comes into play.

When you assign a key= property to your component, React uses it as a smart way to compare items. It matches up elements with the same key before determining what changes need to be made. This keeps elements that haven’t changed, but are just out of order, from being needlessly updated. When adding to the beginning of a list, the unchanged items are all matched up first, and spared from any rewriting. This allows you to just append your element to the DOM just before the unchanged elements.

This comparing and changing is why these keys have to be unique. If you end up with elements that have the same key property, you’ll make the console angry again, and get this error:

Warning: Encountered two children with the same key

Since keys are React’s preferred method for updating, if you have more than one component with the same key it would be pretty easy to accidentally update or change the wrong elements. Luckily unique keys are not usually that hard to establish for components. When looping and instantiating React components, there is typically some sort of data you are passing to that component that can be used as a unique identifier. This could be a unique ID already attached to the data, some part of the data, abstractly hashed for each component, or even some sort of unique key generator.

While you could use an item’s index as the key, that’s typically not good practice. Say you use indices as keys for a component. If the array those components are based on is mutated, that array’s indices will change. This will create a mismatch between the data each index points to in the array holding your data, and the component your key index is pointing to. This can cause buggy and confusing updates to components.

Here is the code with the key property added to the BookExample components:

Since this is just for an example, and there’s no chance of duplicate names, I’ve just named the key after each book. But if dealing with larger or unpredictable sets of data, you may have to set up unique identifiers accordingly. Luckily for us, keys only have to be unique between their siblings though, and not globally.

Lastly it’s important to remember, keys need to be set inside the loop where you are creating the list, as in the example. If you were to add the key inside the BookExample component, you would still receive an error for not having key properties.

Hopefully this has helped you get a basic understanding of what the key property is actually for, and why it’s beneficial. You can find the official documentation here:

Lists and Keys

Reconciliation

Sign up to discover human stories that deepen your understanding of the world.

Free

Distraction-free reading. No ads.

Organize your knowledge with lists and highlights.

Tell your story. Find your audience.

Membership

Read member-only stories

Support writers you read most

Earn money for your writing

Listen to audio narrations

Read offline with the Medium app

--

--

Jeremy Wood
Jeremy Wood

Written by Jeremy Wood

I’m a full stack engineer who loves to learn, solve problems, and fix things! When I’m not working on my code, you’ll usually find me working on my motorcycles.

No responses yet

Write a response