Співбесіда з React: тренуйся з ШІ голосом
Сторінка для фронтенд-розробників, які готуються до співбесіди з React на junior, middle чи senior і хочуть навчитися пояснювати React уголос, а не лише читати про нього. ШІ-інтерв'юер питає про рендеринг, hooks, стан, продуктивність і нове в React 19, слухає ваші відповіді та дає звіт з оцінками за технічну точність, повноту і ясність.
Про що питає ШІ на співбесіді з React
Рендеринг і reconciliation
Що викликає ре-рендер, як React порівнює дерево елементів, навіщо потрібні key і чим фаза render відрізняється від commit.
Hooks і ефекти
Правила hooks, залежності та cleanup у useEffect, stale closures, useRef проти state і чому ефект часто взагалі не потрібен.
Керування станом
Підняття стану, Context і ціна його ре-рендерів, useReducer, коли варто брати TanStack Query для серверних даних чи Zustand або Redux Toolkit.
Продуктивність і мемоізація
React.memo, useMemo і useCallback, React Compiler, віртуалізація списків, code splitting через lazy і Suspense, профілювання в React DevTools.
React 19 і Server Components
Actions, useActionState, useOptimistic, API use, ref як звичайний prop і як Server Components та Server Functions ділять роботу між сервером і клієнтом.
Concurrent rendering і Suspense
useTransition і useDeferredValue, межі Suspense для даних і коду, streaming SSR і помилки гідрації.
Форми
Controlled і uncontrolled інпути, form actions у React 19, валідація і коли виправдана бібліотека на кшталт React Hook Form.
Тестування і доступність
Тести поведінки через React Testing Library замість деталей реалізації, семантичний HTML, керування фокусом і ARIA в компонентах.
Питання на співбесіді з React: junior, middle, senior
Junior
Чим props відрізняються від state?
Що має бути в сильній відповіді:Props передає батьківський компонент, і всередині вони тільки для читання; state належить самому компоненту й змінюється через setter. Зміна і того, і іншого спричиняє ре-рендер, але змінювати state може лише його власник. Добре додати, що дані йдуть униз через props, а зміни піднімаються вгору через колбеки.
Навіщо React потрібен key в елементах списку і чому індекс масиву часто поганий key?
Що має бути в сильній відповіді:Key дозволяє React зіставити елементи між рендерами й зберегти, перемістити чи видалити правильні екземпляри компонентів разом з їхнім станом. Індекс ламається при вставці, видаленні чи сортуванні: стан і DOM, наприклад значення інпутів, чіпляються не до того елемента. Потрібен стабільний унікальний ID з даних; індекс ок лише для статичного списку, що не змінює порядок.
Як працює масив залежностей useEffect і навіщо функція cleanup?
Що має бути в сильній відповіді:Без масиву ефект виконується після кожного рендеру, з порожнім масивом — один раз після монтування, зі значеннями — коли будь-яке з них змінилось за Object.is. Cleanup викликається перед наступним запуском ефекту та при розмонтуванні: там знімають слухачі, чистять таймери, скасовують запити. Варто згадати, що StrictMode у dev монтує, розмонтовує і знову монтує компонент, щоб виявити відсутній cleanup.
Чим controlled інпут відрізняється від uncontrolled?
Що має бути в сильній відповіді:Controlled інпут бере value зі state й оновлює його через onChange, тож єдине джерело правди — React. Uncontrolled тримає значення в DOM, а прочитати його можна через ref або FormData при сабміті. Controlled зручний для миттєвої валідації й залежних полів, uncontrolled простіший і добре поєднується з form actions у React 19.
Чому hooks не можна викликати в умовах чи циклах?
Що має бути в сильній відповіді:React розпізнає кожен hook за порядком виклику в компоненті, а не за назвою. Якщо умова пропустить hook в одному рендері, всі наступні hooks прочитають чужий збережений стан. Hooks викликають лише на верхньому рівні компонента чи кастомного hook, це перевіряє eslint-plugin-react-hooks; виняток — новий API use, його можна викликати умовно.
Middle
Коли компонент ре-рендериться і як reconciliation вирішує, що оновити в DOM?
Що має бути в сильній відповіді:Компонент ре-рендериться, коли змінюється його state, ре-рендериться батько або змінюється context, який він читає; самі по собі нові props не тригер — тригер це рендер батька. Далі React порівнює нове дерево з попереднім: інший тип елемента на тому ж місці — піддерево монтується заново, той самий тип — оновлюються props, а дітей у списках зіставляють за key. У фазі commit у DOM потрапляє лише різниця.
Коли useMemo, useCallback і React.memo реально допомагають, а коли марні?
Що має бути в сильній відповіді:Допомагають, коли обчислення справді дороге або коли стабільне посилання рятує мемоізованого нащадка від ре-рендеру чи ефект від зайвого запуску. Марні, якщо нащадок не обгорнутий у memo, залежності змінюються щорендеру або робота дешева — мемоізація теж коштує. Сильна відповідь згадує React Compiler, який додає мемоізацію автоматично, тож вручну її тепер ставлять точково, за даними Profiler.
Що таке stale closure в React-компоненті і як її виправити?
Що має бути в сильній відповіді:Функція, створена під час рендеру, захоплює props і state саме цього рендеру; якщо інтервал чи слухач продовжує її використовувати, він бачить старі значення. Варіанти: додати значення в залежності ефекту, використати updater-форму setCount(c => c + 1), тримати актуальне значення в ref або винести логіку в useEffectEvent, щоб читати свіжі дані без перезапуску ефекту.
Які проблеми з продуктивністю має Context і як ти організуєш глобальний стан?
Що має бути в сильній відповіді:Кожен споживач ре-рендериться при зміні value, а новий об'єкт-літерал у кожному рендері змінює його щоразу. Рішення: мемоізувати value, розділити контексти за частотою оновлень або взяти стор із селекторами, як Zustand чи Redux Toolkit. Також варто відокремити серверний стан (TanStack Query чи завантаження даних фреймворку) від UI-стану, який часто лишається локальним.
Яку проблему розв'язують useTransition і useDeferredValue?
Що має бути в сильній відповіді:Вони позначають частину оновлень як нетермінові, щоб термінові, як-от введення тексту, лишались чуйними, а повільний рендер можна було перервати. useTransition обгортає оновлення стану, яке ти контролюєш, і дає isPending; useDeferredValue повертає «відстаючу» копію значення, яке ти отримуєш, наприклад для фільтрації великого списку. Рендер вони не пришвидшують, лише змінюють його пріоритет.
Senior
Чим Server Components відрізняються від Client Components і де ти ставиш межу "use client"?
Що має бути в сильній відповіді:Server Components виконуються тільки на сервері, можуть напряму читати дані й не відправляють свій JavaScript у браузер, але не мають state, ефектів і браузерних API. "use client" позначає вхід у клієнтський бандл, і все, що звідти імпортується, стає клієнтським кодом, тому межу опускають до дрібних інтерактивних листків. Props через межу мають бути серіалізовними, а Server Components можна передати в Client Component як children.
Сторінка в React-застосунку гальмує. Як знайдеш і виправиш причину?
Що має бути в сильній відповіді:Спершу вимірювання: React DevTools Profiler покаже, які компоненти рендеряться, як часто й чому, а вкладка Performance та INP — вартість взаємодій. Типові причини: широкі оновлення context чи стору, нестабільні props, що ламають memo, величезні списки, важка робота під час рендеру. Виправлення залежить від причини: опустити стан нижче, розділити context або взяти селектори, віртуалізувати списки, мемоізувати чи покластися на React Compiler, code splitting, transitions для нетермінових оновлень.
Що спричиняє hydration mismatch і як streaming SSR із Suspense змінює гідрацію?
Що має бути в сильній відповіді:Mismatch виникає, коли серверний HTML відрізняється від першого клієнтського рендеру: Date.now, Math.random, форматування за локаллю, читання window чи localStorage під час рендеру, невалідна вкладеність HTML. Лікується детермінованим першим рендером і перенесенням браузерних значень в ефект. При streaming межі Suspense віддають HTML частинами й гідруються незалежно, а React першою гідрує ту частину, з якою взаємодіє користувач.
Як працюють Actions у React 19 і що дають useActionState та useOptimistic?
Що має бути в сильній відповіді:Action — це async-функція, запущена в transition, наприклад передана в prop action форми; React відстежує pending, скидає uncontrolled форму після успіху і передає кинуті помилки в error boundary. useActionState обгортає action і повертає останній результат, функцію dispatch та isPending. useOptimistic показує тимчасове значення, поки action виконується, і сам повертається до реального стану після завершення.
Як би ти побудував стратегію тестування для великого React-проєкту?
Що має бути в сильній відповіді:Тестувати поведінку, яку бачить користувач: React Testing Library з запитами за role і label, user-event для взаємодій, мережу мокати через MSW, а не мокати hooks. Основна маса — компонентні та інтеграційні тести, невеликий набір e2e на Playwright для критичних сценаріїв, чиста логіка — в unit-тестах. Варто окремо сказати, що запити за role заодно ловлять регресії доступності.
Як проходить мок-співбесіда з React
- Оберіть React (та інші технології зі свого стеку), свій рівень і мову співбесіди: українську, англійську або російську. Або завантажте резюме й опис вакансії.
- Відповідайте на кожне запитання голосом, як на справжній співбесіді.
- Отримайте оцінку кожної відповіді за точністю, повнотою та зрозумілістю і звіт зі слабкими місцями.
Як відповідати на питання з React уголос
- →Почни з відповіді в одне речення, далі — чому так, потім короткий приклад з реального проєкту: «таке було в дашборді, де кожне натискання клавіші ре-рендерило всю таблицю».
- →Описуй код словами точно: назви hook, залежність і тригер, наприклад «setCount з updater-функцією, тому count не потрібен у залежностях ефекту».
- →Завжди додавай trade-off. Сказати, коли НЕ варто брати useMemo, Context чи глобальний стор, звучить значно сильніше, ніж перелічити, що вони роблять.
- →Прив'язуй відповіді до версій: «з React 18 оновлення батчаться автоматично», «у React 19 ref — звичайний prop». Це показує, що ти в темі.
- →Якщо не певен у деталях API, міркуй уголос від моделі рендеру — що рендериться, коли і з якими значеннями — замість вгадувати назви. Правильне міркування теж зараховується.
Часті запитання
Співбесіда базується на React 19?
Так, питання відповідають актуальному React: hooks, concurrent-фічі та API React 19 — Actions, use, Server Components — плюс основи, які не змінились. Якщо ваш проєкт на старішій версії, завантажте вакансію чи резюме, і питання підлаштуються під ваш реальний стек.
Можна тренуватись на питаннях з моєї вакансії?
Так. Замість вибору React можна завантажити опис вакансії або резюме, і ШІ збудує співбесіду під стек і рівень, які там вказані, наприклад React з Next.js і TypeScript.
Чи є live coding?
Ні. Питання усні й концептуальні, відповідаєш голосом, редактора коду немає. Частина питань просить пояснити, як ти написав би чи дебажив би щось, тож варто потренуватись описувати код словами.
Скільки це коштує?
Перша співбесіда до 5 питань безкоштовна. Далі оплата за кожну співбесіду, від $1.75, до 50 питань. Підписки немає.