Custom hook нужен не для красоты, а для переиспользования логики со state, эффектами и подписками. Если ты копируешь один и тот же useEffect, одну и ту же инициализацию состояния или одинаковую работу с API браузера в несколько компонентов, значит пора выносить это в отдельный хук.
- Что делает custom hook полезным
- Рабочий пример
useLocalStorage - Как использовать хук в компоненте
- Когда не нужно создавать custom hook
Что делает custom hook полезным
Custom hook не рендерит UI и не “магически ускоряет React”. Он просто выносит связанную логику в функцию, которая сама использует хуки.
Есть два практических правила:
- имя должно начинаться с
use; - внутри хука действуют те же правила хуков, что и в компоненте.
Рабочий пример useLocalStorage
Предположим, ты хочешь создать приложение, которое отслеживает значение даже после обновления страницы. Это легко сделать, воспользовавшись localStorage браузера. Custom Hook для этого может выглядеть следующим образом:
import { useEffect, useState } from "react";
function useLocalStorage(key, initialValue) {
const [value, setValue] = useState(() => {
const savedValue = window.localStorage.getItem(key);
if (savedValue !== null) {
return JSON.parse(savedValue);
}
return initialValue;
});
useEffect(() => {
window.localStorage.setItem(key, JSON.stringify(value));
}, [key, value]);
return [value, setValue];
}Здесь важны две вещи:
- начальное значение читается лениво, только на первом рендере;
localStorageхранит строки, поэтому для объектов и массивов нуженJSON.stringify/JSON.parse.
Как использовать хук в компоненте
После этого хук можно использовать как обычную пару state и setState:
function Counter() {
const [value, setValue] = useLocalStorage("day", 2);
return (
<button onClick={() => setValue((current) => current + 1)}>
Day: {value}
</button>
);
}После обновления страницы значение останется в localStorage, а компонент прочитает его при следующей инициализации.
Когда не нужно создавать custom hook
Не выноси код в hook слишком рано. Если логика живет в одном компоненте и не мешает чтению, отдельный хук только размажет контекст по файлам.
Custom hook оправдан, когда:
- логика реально повторяется;
- внутри есть состояние, подписка, эффект или работа с внешним API;
- отдельное имя делает намерение понятнее, чем длинный кусок кода в компоненте.