React: первые компоненты и состояние с нуля
Пошаговый гайд для тех, кто впервые открыл React: как собрать проект на Vite, написать первый компонент, передать данные через пропсы и завести состояние через useState. Итог — рабочий счётчик за 20 минут.

За 20 минут вы получите работающее приложение на React: страницу с кнопкой, которая считает клики и показывает число на экране. По пути напишете два компонента, передадите данные из одного в другой и заведёте первое состояние. Всё делается на актуальной сборке — React 18/19 и Vite 5.x, без устаревшего create-react-app, который команда React больше не рекомендует для новых проектов.
Что нужно иметь до начала
Проверьте это заранее, чтобы не застрять на середине:
- Node.js версии 18 или выше. Проверьте командой
node -vв терминале. Если версия ниже или Node не установлен — скачайте LTS-сборку с nodejs.org. - Любой редактор кода. Подойдёт VS Code, но не обязателен.
- Терминал. На macOS и Linux встроенный, на Windows — PowerShell или встроенный терминал VS Code.
Знать JavaScript на уровне функций, массивов и стрелочных функций желательно — React это не отдельный язык, а библиотека поверх обычного JS.
Шаг 1. Создаём проект на Vite
В терминале перейдите в папку, где хотите создать проект, и выполните:
npm create vite@latest my-app -- --template react
Vite задаст пару вопросов, если запускать без флагов, но с --template react он сразу возьмёт нужный шаблон. Затем установите зависимости и запустите:
cd my-app
npm install
npm run dev
Проверка: в терминале появится строка вида Local: http://localhost:5173/. Откройте этот адрес в браузере — увидите стартовую страницу Vite с логотипами React и счётчиком. Значит, всё запустилось.
Что здесь произошло
Vite — это инструмент сборки и dev-сервер. Он отдаёт браузеру код и мгновенно обновляет страницу при изменении файлов. Точка входа — файл src/main.jsx, а сам интерфейс живёт в src/App.jsx. С ним и будем работать.
Шаг 2. Пишем первый компонент
Компонент в React — это функция, которая возвращает разметку. Откройте src/App.jsx, удалите всё содержимое и вставьте:
function App() {
return (
<div>
<h1>Моё первое приложение</h1>
<p>Оно работает.</p>
</div>
);
}
export default App;
Проверка: сохраните файл. Браузер сам обновится и покажет заголовок «Моё первое приложение» и строку под ним. Перезагружать вручную не нужно — Vite делает это за вас.
То, что похоже на HTML внутри функции, называется JSX*. Это не строка и не HTML в чистом виде, а синтаксис, который сборщик превращает в вызовы React. Важное отличие от HTML: атрибут class пишется как className, потому что class — зарезервированное слово в JavaScript.
* JSX (JavaScript XML) — расширение синтаксиса JavaScript, позволяющее писать разметку прямо в коде. Браузер его не понимает напрямую, поэтому сборщик компилирует JSX в обычный JavaScript.
Шаг 3. Передаём данные через пропсы
Компоненты хочется переиспользовать с разными данными. Для этого в них передают пропсы — как аргументы функции. Создайте новый файл src/Greeting.jsx:
function Greeting({ name }) {
return <p>Привет, {name}!</p>;
}
export default Greeting;
Фигурные скобки {name} внутри JSX означают «вставь сюда значение переменной». Теперь подключите этот компонент в App.jsx:
import Greeting from './Greeting';
function App() {
return (
<div>
<h1>Моё первое приложение</h1>
<Greeting name="Анна" />
<Greeting name="Борис" />
</div>
);
}
export default App;
Проверка: на странице появятся две строки — «Привет, Анна!» и «Привет, Борис!». Один компонент, разные данные.
Пропсы передаются только сверху вниз: родитель отдаёт данные ребёнку, но ребёнок не может изменить пропс. Если нужно, чтобы что-то менялось внутри самого компонента, — это уже состояние, а не пропс.
Шаг 4. Заводим состояние через useState
Состояние — это данные, которые компонент помнит между перерисовками и при изменении которых React перерисовывает интерфейс. Классический пример — счётчик кликов. Замените содержимое App.jsx:
import { useState } from 'react';
function App() {
// count — текущее значение, setCount — функция для его изменения
const [count, setCount] = useState(0);
return (
<div>
<h1>Счётчик</h1>
<p>Кликов: {count}</p>
<button onClick={() => setCount(count + 1)}>
Нажми меня
</button>
</div>
);
}
export default App;
Проверка: на странице появится кнопка. Каждый клик увеличивает число рядом со словом «Кликов». Если число растёт — состояние работает.
Что важно понять про useState
useState(0) возвращает массив из двух элементов: текущее значение и функцию для его изменения. Начальное значение здесь — ноль.
- Меняйте состояние только через функцию-сеттер (
setCount). Прямое присваиваниеcount = 5React не заметит, и перерисовки не будет. - Вызов
setCountне меняет переменную мгновенно в текущей функции — React запланирует перерисовку, и в следующий раз компонент выполнится уже с новым значением. - Если новое значение зависит от старого, безопаснее передавать функцию:
setCount(prev => prev + 1). Это спасает от ошибок при нескольких обновлениях подряд.
Если не получилось
Самые частые ошибки на старте и что они значат:
- «Adjacent JSX elements must be wrapped in an enclosing tag». Вы вернули из компонента два элемента рядом без обёртки. Оберните их в
<div>или в пустой фрагмент<>...</>. - «useState is not defined». Забыли импорт. В начале файла должна быть строка
import { useState } from 'react';. - Кнопка вызывает функцию сразу при загрузке, а не по клику. Скорее всего написали
onClick={setCount(count + 1)}вместоonClick={() => setCount(count + 1)}. Без стрелочной обёртки функция вызывается при отрисовке, а не при клике. - Белый экран и ошибка в консоли браузера. Откройте консоль (F12 → Console), React обычно пишет понятное сообщение с именем файла и строкой. Чаще всего — незакрытый тег или опечатка в имени компонента.
- Компонент не отображается. Имя компонента должно начинаться с заглавной буквы:
Greeting, а неgreeting. С маленькой буквы React считает тег обычным HTML-элементом.
Что делать дальше
Работающий счётчик — это уже полный цикл React: компонент, пропсы, состояние, событие. Дальше двигайтесь по порядку:
- Соберите список: попробуйте отрендерить массив данных через
.map()— это самый частый паттерн в реальных проектах. - Разберитесь с формами: как хранить введённый текст в состоянии и читать его при отправке.
- Познакомьтесь с
useEffect— хук для действий при загрузке компонента, например запроса данных с сервера. - Прочитайте раздел «Thinking in React» в официальной документации: он объясняет, как разбивать интерфейс на компоненты.
Не спешите тянуть роутеры и библиотеки состояния вроде Redux — на первых проектах их не нужно, а useState закрывает большинство задач.
Инфобез и 152-ФЗ: Аудит политик конфиденциальности, правила сбора cookie.
Спросить за 20 ₽Источники: React — официальная документация (Quick Start), Vite — Getting Started
Частые вопросы
Почему Vite, а не create-react-app?
У меня другая версия Node, всё сломается?
В чём разница между пропсами и состоянием?
Можно ли использовать хуки в любом месте компонента?
Расширение файлов должно быть .jsx или .js?
Кнопка ничего не делает при клике, что проверить?
Материал носит информационный характер и подготовлен редакцией «Агентуры». Он не является офертой, рекламой или индивидуальной консультацией. Упомянутые продукты, компании и торговые знаки принадлежат их правообладателям. Перед принятием решений, влекущих юридические или финансовые последствия, обратитесь к профильному специалисту.