Back
LearnReact — Build Modern Web AppsCustom hooks — reusing logic

Custom hooks — reusing logic

2 min read

Reusing logic, not just UI

Components let you reuse UI. But what about reusing logic — like the same data-fetching steps, or the same form handling, across many components? For that, React lets you write your own hook: a custom hook.

A custom hook is just a function whose name starts with use and that uses other hooks inside it.

Example: a useFetch hook

Remember our data-fetching pattern? Let us extract it once and reuse it everywhere:

import { useState, useEffect } from "react";

function useFetch(url) {
  const [data, setData] = useState(null);
  const [loading, setLoading] = useState(true);

  useEffect(() => {
    fetch(url)
      .then((res) => res.json())
      .then((d) => {
        setData(d);
        setLoading(false);
      });
  }, [url]);

  return { data, loading };
}

Now any component can fetch in one line:

function Users() {
  const { data, loading } = useFetch("https://.../users");

  if (loading) return <p>Loading...</p>;
  return <ul>{data.map((u) => <li key={u.id}>{u.name}</li>)}</ul>;
}

The messy fetch logic is written once, used everywhere. Clean.

The rules of hooks (important)

Two simple rules keep hooks working correctly:

  1. Only call hooks at the top level of a component or custom hook — never inside if, loops, or nested functions.
  2. Only call hooks from React functions — components or other custom hooks, not plain functions.

Why custom hooks matter

They are how React apps stay DRY (Don't Repeat Yourself). Form handling, fetching, timers, localStorage — wrap any repeated logic in a use... hook, and your components become short and readable.

A custom hook is a use... function that bundles reusable logic (built from other hooks). Write the logic once, share it across components. Follow the rules: hooks only at the top level, only in React functions.

Tip