bhylu.com

Advertisements

React Lists and Keys

Use stable domain IDs as keys so state stays attached to the record rather than its current row number.

How it works

A key tells React which sibling corresponds to which earlier sibling. It matters when rows are inserted, removed or reordered. An array index describes a position, not a record. The example lets each item row retain an uncontrolled note while the order reverses. Stable item IDs keep the typed note with the same item. The key is used by React and is not passed to the component as an ordinary prop.

Run the code

Use a separate empty lab folder with Node 22.12+ in the 22 series. Save the files below using their displayed paths; browsers may download only the basename, so create src, public or tests folders as listed. The pinned project uses React and React DOM 19.3.1 with Vite 7.3.1. Run npm install, then npm run dev and open the local address Vite prints. React examples do not run in Bhylu’s current playground.

No Apache, MySQL or change to Bhylu’s server configuration is needed. These are local teaching projects, not a publishing package. Keep generated dependencies and lockfiles in your own lab. Review the project setup.

Example

src/main.jsx

import React, { StrictMode, useState } from 'react';
import { createRoot } from 'react-dom/client';
import './style.css';

const stock = [
  { id: 'basket', name: 'Market basket' },
  { id: 'stool', name: 'Folding stool' },
];
function Row({ item }) {
  return (
    <li>
      <label>
        {item.name} note
        <input aria-label={item.name + ' note'} defaultValue="" />
      </label>
    </li>
  );
}
function App() {
  const [reversed, setReversed] = useState(false);
  const rows = reversed ? [...stock].reverse() : stock;
  return (
    <main>
      <h1>Neighbourhood lending desk</h1>
      <button onClick={() => setReversed((value) => !value)}>Reverse order</button>
      <ul>
        {rows.map((item) => (
          <Row key={item.id} item={item} />
        ))}
      </ul>
    </main>
  );
}

createRoot(document.getElementById('root')).render(
  <StrictMode>
    <App />
  </StrictMode>,
);

Expected result

After a note is typed for the basket and the list reverses, the note remains with the basket.

The order changes through a copied array, so the original stock stays unchanged. Each Row has a stable key chosen from the data. IDs must be unique among these siblings, not globally across the entire app. If records come from a server, use its persistent ID. A freshly generated random key on every render discards identity instead of preserving it.

For API contracts and version differences, use React’s official documentation.

Advertisements