Мы не строим SPA. Вот почему.
Time to first content
дностраничное приложение — SPA — работает так: браузер скачивает JavaScript-файл, запускает его, и только потом отрисовывает страницу. Пока скрипт не выполнится, пользователь видит пустой экран или спиннер. На быстром ноутбуке с хорошим интернетом это занимает доли секунды. На среднем телефоне с мобильным интернетом — может растянуться на 3–5 секунд. А эти три секунды — момент, когда большинство людей уходит.
Мы строим server-first. С Next.js App Router и React Server Components сервер собирает HTML и отправляет его в браузер уже готовым. Пользователь видит реальный контент с самого первого ответа — не состояние загрузки, не пустой блок. Это разница между First Contentful Paint в 0.4 секунды и 3 секундами. Интерактивность страницы тоже улучшается: в бандл попадает меньше JavaScript, потому что серверные компоненты просто не отправляют код на клиент.
Есть ещё один плюс, про который часто забывают: безопасность. В классическом SPA вся логика выполняется в браузере — значит, она доступна любому, кто откроет DevTools. В server-first архитектуре API-ключи, запросы к базе данных и чувствительная бизнес-логика остаются на сервере. Клиент получает только готовый результат. Это убирает целый класс уязвимостей.
Клиентские компоненты мы всё равно используем — там, где опыт этого действительно требует: сложные анимации, обновления в реальном времени, формы с моментальной валидацией. Но это осознанный выбор, а не значение по умолчанию. Мы спрашиваем себя: а этой функции реально нужно работать в браузере? Если да — она становится клиентским компонентом. Если нет — остаётся на сервере, где быстрее, безопаснее и проще.