CPCODELAB
React

useContext — Avoiding Prop Drilling

11 min read

Global-ish State Without Prop Chains

Prop drilling happens when you pass data through many intermediate components just to reach a deeply nested child. useContext lets you broadcast a value to an entire subtree without threading it through every level.

jsx
import { createContext, useContext, useState } from 'react';

const ThemeContext = createContext('light');

function ThemeProvider({ children }) {
  const [theme, setTheme] = useState('light');
  return (
    <ThemeContext.Provider value={{ theme, setTheme }}>
      {children}
    </ThemeContext.Provider>
  );
}

function ThemeToggle() {
  const { theme, setTheme } = useContext(ThemeContext);
  return (
    <button onClick={() => setTheme(t => t === 'light' ? 'dark' : 'light')}>
      Current: {theme}
    </button>
  );
}

export default function App() {
  return (
    <ThemeProvider>
      <ThemeToggle />
    </ThemeProvider>
  );
}

Context is not a replacement for state management. When a context value changes, every consumer re-renders. Split large contexts into smaller ones, or memoize the value object to prevent unnecessary re-renders.

Ready to test yourself?
Practice React— quiz & coding exercises