React Hook Form — формы в React без лишнего кода

React Hook Form — библиотека для форм, которая уменьшает количество state и обработчиков. Она особенно удобна для форм с валидацией, ошибками и отправкой данных.

Базовая форма на React Hook Form

Начинать лучше с простой формы: регистрация полей, валидация и значения по умолчанию. Когда этот слой понятен, Controller, схемы валидации и отправка на backend воспринимаются как развитие идеи, а не как отдельная магия.

Важная мысль: библиотека не отменяет понимание формы, а забирает на себя рутинную регистрацию полей и ошибки. Пользовательский сценарий всё равно нужно проектировать вручную.

Установка

npm install react-hook-form

Минимальная форма

import { useForm } from 'react-hook-form';

function ContactForm() {
  const { register, handleSubmit } = useForm();

  function onSubmit(data) {
    console.log(data);
  }

  return (
    <form onSubmit={handleSubmit(onSubmit)}>
      <input {...register('name')} placeholder="Имя" />
      <input {...register('email')} placeholder="Email" />
      <button>Отправить</button>
    </form>
  );
}

register связывает input с формой. handleSubmit отменяет стандартную отправку, собирает данные и вызывает вашу функцию.

Валидация

function ContactForm() {
  const {
    register,
    handleSubmit,
    formState: { errors },
  } = useForm();

  return (
    <form onSubmit={handleSubmit(console.log)}>
      <input
        {...register('email', {
          required: 'Email обязателен',
          pattern: {
            value: /^[^\s@]+@[^\s@]+\.[^\s@]+$/,
            message: 'Введите корректный email',
          },
        })}
        placeholder="Email"
      />
      {errors.email && <p>{errors.email.message}</p>}
      <button>Отправить</button>
    </form>
  );
}

Значения по умолчанию

const { register, handleSubmit } = useForm({
  defaultValues: {
    name: 'Алиса',
    email: 'alice@example.com',
  },
});

Когда React Hook Form особенно полезен

  • Много полей.
  • Нужна валидация.
  • Есть повторяющиеся формы в проекте.
  • Нужно меньше перерендеров при вводе.
  • Форма работает с UI-библиотекой через Controller.

Controller для UI-компонентов

import { Controller, useForm } from 'react-hook-form';

function FormWithSelect() {
  const { control, handleSubmit } = useForm();

  return (
    <form onSubmit={handleSubmit(console.log)}>
      <Controller
        name="city"
        control={control}
        defaultValue=""
        render={({ field }) => (
          <select {...field}>
            <option value="">Выберите город</option>
            <option value="moscow">Москва</option>
          </select>
        )}
      />
      <button>Сохранить</button>
    </form>
  );
}

Практический пример: регистрация

В форме регистрации обычно нужны обязательные поля, проверка длины пароля и повтор пароля. Даже без внешних схем валидации React Hook Form закрывает базовую задачу.

function RegisterForm() {
  const {
    register,
    handleSubmit,
    watch,
    formState: { errors, isSubmitting },
  } = useForm();

  const password = watch('password');

  return (
    <form onSubmit={handleSubmit(console.log)}>
      <input {...register('email', { required: 'Email обязателен' })} />
      {errors.email && <p>{errors.email.message}</p>}

      <input
        type="password"
        {...register('password', {
          required: 'Пароль обязателен',
          minLength: { value: 6, message: 'Минимум 6 символов' },
        })}
      />

      <input
        type="password"
        {...register('repeatPassword', {
          validate: value => value === password || 'Пароли не совпадают',
        })}
      />

      <button disabled={isSubmitting}>Создать аккаунт</button>
    </form>
  );
}

Что не стоит делать

  • Не смешивайте ручной useState для каждого поля и register без необходимости.
  • Не прячьте ошибки: пользователь должен понять, что исправить.
  • Не отправляйте форму, если handleSubmit уже даёт валидные данные.
  • Не забывайте defaultValues при редактировании существующей записи.

Следующий уровень

Когда базовая валидация станет тесной, подключите Zod или Yup через resolvers. Тогда правила формы будут жить в отдельной схеме и их проще переиспользовать на frontend и backend.

Как понять, что форма написана нормально

Форма считается хорошей не тогда, когда она просто отправляет данные, а когда пользователь понимает, что заполнить, где ошибка и что происходит после отправки.

Проверьте форму глазами пользователя: ошибка появляется рядом с полем, кнопка не отправляет пустые данные, после успешной отправки понятно, что произошло. Если эти базовые вещи работают, форма уже лучше большинства учебных примеров.

Проверочный список

  • у обязательных полей есть понятные сообщения об ошибке;
  • кнопка отправки блокируется во время запроса;
  • ошибки показываются рядом с полями, а не где-то внизу страницы;
  • значения по умолчанию работают при редактировании записи;
  • после успешной отправки понятно, что произошло.

Когда подключать схемы валидации

Если правил мало, хватит встроенной валидации register. Если форма растёт, появляются вложенные объекты, повторяющиеся правила и backend с похожими проверками, лучше подключить Zod или Yup через resolver.

Что улучшить после первого варианта

Добавьте состояние загрузки, обработку ошибки API и reset формы после успешной отправки. Эти три вещи сильнее влияют на качество формы, чем ещё один красивый input.

Оцените статью
0 0 голоса
Рейтинг статьи
Подписаться
Уведомить о
guest

0 комментариев
Старые
Новые Популярные
Межтекстовые Отзывы
Посмотреть все комментарии
0
Оставьте комментарий! Напишите, что думаете по поводу статьи.x