Загрузка данных


Ты работаешь как команда специалистов:

* Senior Full-Stack Developer;
* Software Architect;
* Database Engineer;
* UI/UX Designer;
* QA Automation Engineer;
* Application Security Engineer;
* DevOps Engineer.

Ты работаешь в Claude Code и имеешь возможность изучать проект, изменять файлы, запускать терминальные команды и использовать доступные MCP.

Твоя задача — разработать полноценный, поддерживаемый веб-продукт для быстрого создания персональных приложений для конкретных автосервисов, автомоек и детейлинг-студий.

Это не маркетплейс, где клиент выбирает одну из пятнадцати компаний. Каждый владелец получает отдельное брендированное приложение под названием своего бизнеса, с собственными услугами, ценами, фотографиями, расписанием и кабинетом управления.

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

Главная коммерческая задача — за сутки подготовить приложения для 10–15 реальных студий, предоставив каждому владельцу готовую ссылку без повторной ручной разработки сайта.

**Приоритеты в указанном порядке:**

1. Корректная запись и защита от двойного бронирования.
2. Изоляция студий и безопасность данных.
3. Работающая база данных и кабинет владельца.
4. Быстрое создание и персонализация новых приложений.
5. Качественный фирменный интерфейс.
6. Работающие ИИ-помощники с доступом только к разрешённым данным.
7. PWA, установка на телефон и корректная работа без сети там, где это возможно.
8. Автоматическое и нагрузочное тестирование.
9. Безопасный процесс развёртывания и дальнейшего обслуживания.

Не жертвуй корректностью серверной логики ради красивого интерфейса.

Не заявляй, что функциональность готова, протестирована, безопасна или выдерживает заданную нагрузку, если это фактически не подтверждено.

---

# ЧАСТЬ I. ПРЕДВАРИТЕЛЬНАЯ ПРОВЕРКА ИНСТРУМЕНТОВ

## 1. Сначала изучи существующий проект

До изменения файлов:

1. Определи текущую рабочую папку.
2. Изучи структуру проекта.
3. Проверь существующие файлы, зависимости, `package.json`, lock-файл, конфигурации и README.
4. Проверь состояние Git и незакоммиченные изменения.
5. Определи, есть ли уже код, который нужно сохранить.
6. Проверь версии Node.js, pnpm, Git, доступность Docker и инструменты Supabase CLI.
7. Определи, настроена ли локальная среда Supabase.
8. Проверь наличие необходимых переменных окружения без вывода их секретных значений.
9. Изучи доступные интеграции и реальные возможности MCP.

Не удаляй существующие файлы, не перезаписывай чужую работу и не сбрасывай базу данных без проверки последствий.

Если репозиторий уже содержит код, сначала пойми его устройство. Не переписывай весь проект заново только потому, что другая структура кажется удобнее.

Если папка пуста, создай проект с нуля.

## 2. Обязательно используй подключённые Skills

В Claude Code доступны следующие инструменты. Проверь их фактическую доступность и используй инструкции соответствующих skill-файлов.

### Skill `ui-ux-pro-max`

Примени до проектирования интерфейса.

Используй его для:

* выбора визуального направления;
* построения дизайн-системы;
* иерархии компонентов;
* типографики;
* цветовой палитры;
* адаптивного поведения;
* анализа пользовательских сценариев;
* доступности;
* проектирования форм и состояний;
* проверки визуальной согласованности.

Не игнорируй результаты skill и не возвращайся к стандартному шаблонному дизайну без причины.

### Skill `shadcn`

Примени для корректного использования shadcn/ui, интеграции компонентов и соблюдения соглашений проекта.

Не копируй огромный набор компонентов, если используются только несколько. Добавляй лишь те компоненты, которые необходимы текущему этапу.

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

### Важное правило

Skills — это инструкции и методики работы. Не утверждай, что применил skill, если фактически не изучил его инструкции или не использовал его возможности.

Если skill временно недоступен, продолжай работу по документированному плану и отметь ограничение.

## 3. Обязательно изучи оба MCP: shadcn и Astryx

Перед проектированием страниц проверь доступные инструменты, ресурсы и документацию подключённых MCP.

Не придумывай названия команд и не предполагай, что MCP поддерживает определённые операции без проверки.

### MCP shadcn

Используй для:

* изучения доступных компонентов и документации;
* поиска подходящих элементов интерфейса;
* проверки способов установки компонентов;
* получения примеров правильного использования;
* добавления необходимых компонентов в проект;
* проверки актуальных API и ограничений библиотек.

Перед добавлением компонента проверь его совместимость с установленным стеком, существующей системой стилей и версиями зависимостей.

### MCP Astryx

Перед созданием страниц обязательно изучи Astryx.

Проверь доступность и используй соответствующие команды или инструменты для:

* `build`;
* `template`;
* `component`;
* `docs layout`;
* `docs tokens`.

Это названия возможностей из исходного технического задания. Сначала установи, какие реальные инструменты предоставляет подключённый MCP, и только после этого вызывай их.

Изучи:

* дизайн-токены;
* типографику;
* компоненты;
* принципы layout;
* доступные варианты оформления;
* ограничения системы;
* примеры использования;
* доступные способы сборки и интеграции.

Если команда называется иначе, используй реальное название из MCP, а не выдумывай команду.

### Правила совместного использования Astryx и shadcn

Не смешивай две дизайн-системы бессистемно.

Сначала определи, какую роль каждая система выполняет в проекте. Зафиксируй единый слой токенов и согласованный набор компонентов.

Предпочтительный подход:

* Astryx — если его возможности доступны и совместимы, использовать для основного визуального языка, дизайн-токенов и необходимых компонентов;
* shadcn/ui — использовать для отсутствующих компонентов и надёжных интерфейсных примитивов;
* `ui-ux-pro-max` — использовать для принятия и проверки UX/UI-решений;
* Phosphor Icons — использовать для иконок.

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

Не выдумывай API Astryx и не пиши код на основе предположений о его документации.

## 4. Правила использования MCP и внешних сервисов

MCP нужны агенту разработки для изучения документации, работы с инструментами и разрешённых операций.

Они не должны попадать в клиентское приложение как привилегированные интеграции.

Если доступны MCP Supabase, Vercel или браузерный MCP, используй их для соответствующих задач в пределах реально предоставленных разрешений.

Если их нет:

* используй официальную документацию;
* используй официальные CLI;
* документируй, какие действия выполнить вручную;
* не заявляй о выполненной операции, если она не состоялась.

Не публикуй приложение в production, не создавай платные ресурсы и не изменяй реальные клиентские данные без соответствующего разрешения пользователя.

Не выполняй необратимые операции над существующей базой данных без предварительной проверки и подтверждения.

---

# ЧАСТЬ II. ТЕХНИЧЕСКАЯ АРХИТЕКТУРА

## 5. Технологический стек

Используй следующий стек:

* TypeScript;
* React;
* Vite;
* React Router;
* Astryx Design System;
* Phosphor Icons;
* TanStack Query;
* Zod;
* Supabase PostgreSQL;
* Supabase Auth;
* Supabase Storage;
* Supabase Edge Functions;
* date-fns;
* date-fns-tz;
* vite-plugin-pwa;
* Workbox;
* liquid-gl;
* Vitest;
* Playwright;
* Grafana k6;
* pnpm;
* Vercel.

Проверь доступность библиотек, их документацию и совместимость версий до установки.

Используй совместимую поддерживаемую LTS-версию Node.js.

Фиксируй зависимости lock-файлом pnpm. Не обновляй все пакеты одновременно только ради получения последних версий.

Не заменяй одну библиотеку другой без объяснения технической причины.

Если `liquid-gl` несовместим, недоступен или фактически не поддерживает нужный эффект, не изображай его использование. Объясни ограничение и создай полноценный CSS-fallback с `backdrop-filter`, градиентами и контролируемой прозрачностью.

## 6. Архитектурное решение

Базовая архитектура:

* React + Vite — клиентское приложение.
* React Router — маршрутизация.
* TanStack Query — загрузка, кеширование и обновление данных.
* Supabase PostgreSQL — постоянные данные.
* Supabase Auth — вход владельцев.
* Supabase Storage — загружаемые фотографии.
* Supabase Edge Functions — серверные операции, ИИ и интеграции.
* PostgreSQL-функции и транзакции — критические атомарные операции.
* Vercel — публикация frontend и необходимых маршрутов, если они потребуются.
* Vitest, Playwright и k6 — автоматические проверки.

Не создавай микросервисы, Kubernetes, Redis и другие лишние инфраструктурные компоненты без доказанной необходимости.

Не размещай бизнес-логику, секреты или критические проверки только во frontend.

Все операции с данными должны иметь документированные границы доверия между клиентом, Edge Functions и PostgreSQL.

### Один движок, отдельные брендированные приложения

С точки зрения клиента каждая студия должна выглядеть как самостоятельное приложение.

Не создавай общий публичный каталог всех студий.

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

У каждой студии — собственная ссылка и визуальный образ. Её клиенты не должны видеть другие студии.

Не создавай отдельную копию React-приложения вручную для каждого бизнеса.

Отдельные проекты, домены или базы создавай, только если это действительно требуется архитектурой, договорённостями с владельцем или подтверждёнными ограничениями.

---

# ЧАСТЬ III. БЫСТРОЕ СОЗДАНИЕ НОВЫХ СТУДИЙ

## 7. Структура проекта

Организуй конфигурации по структуре:

`tenants/<slug>/config.json`

`tenants/<slug>/assets/photos/`

`tenants/<slug>/assets/icons/`

Создай отдельный общий шаблон, используемый для всех новых студий.

Начальная конфигурация содержит:

* slug;
* название;
* описание;
* логотип;
* основную фотографию;
* цветовую тему;
* адрес;
* телефон;
* часовой пояс;
* валюту;
* график;
* услуги;
* стоимость;
* длительность услуг;
* боксы;
* время подготовки;
* правила отмены;
* три информационные карточки;
* фотографии работ;
* настройки иконок и PWA;
* начальные параметры помощника.

Проверяй конфигурацию через Zod.

Slug должен быть уникальным, валидным для URL и защищённым от path traversal и некорректных символов.

Некорректный файл конфигурации не должен приводить к частичному созданию студии.

### Источник истины

Файл конфигурации является исходным шаблоном, а не единственным постоянным хранилищем.

При создании новой студии настройки импортируются в Supabase PostgreSQL. Фотографии загружаются в Supabase Storage.

После этого изменяемые настройки в рабочем приложении хранятся в базе данных и изменяются через кабинет владельца.

Повторный запуск создания студии не должен сбрасывать уже существующие данные.

Изменение шаблона при обновлении версии приложения не должно неожиданно перезаписывать настройки работающих студий.

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

### Команды CLI

Реализуй рабочие команды:

* `pnpm tenant:create <slug>` — создание студии из шаблона;
* `pnpm tenant:validate <slug>` — проверка конфигурации;
* `pnpm tenant:preview <slug>` — локальный предварительный просмотр;
* `pnpm tenant:sync <slug>` — безопасная синхронизация разрешённых настроек;
* `pnpm tenant:publish <slug>` — публикация проверенной студии;
* `pnpm tenant:check-link <slug>` — проверка публичной ссылки и основных функций.

Не ограничивайся записью этих команд в README. Реально реализуй их в проекте.

Команды должны выдавать понятные ошибки, корректно завершаться при невалидных данных и не создавать повторно студию с существующим slug.

До проверки и публикации новый экземпляр остаётся в статусе `draft`.

Поддерживай статусы `draft`, `ready` и `published`.

Если для добавления нового бизнеса не требуется новый deploy, не запускай его без необходимости.

---

# ЧАСТЬ IV. ДИЗАЙН И ПОЛЬЗОВАТЕЛЬСКИЙ ОПЫТ

## 8. Визуальная концепция

Создай визуально качественное приложение для реального автосервиса.

Стиль:

* тёмный фон;
* белый основной текст;
* ярко-синий акцент `#4690FF`;
* премиальная автомобильная эстетика;
* точная типографика;
* выразительные фотографии;
* аккуратные скругления;
* понятная иерархия;
* адаптивность;
* минималистичная навигация;
* продуманные состояния интерфейса.

Не делай типовой шаблон SaaS с одинаковыми карточками и случайными градиентами.

Перед разработкой:

1. Изучи ui-ux-pro-max.
2. Изучи Astryx.
3. Изучи shadcn.
4. Определи единую дизайн-систему.
5. Выбери типографику, spacing, радиусы, цветовые токены и состояния.
6. Подготовь визуальный план основных страниц.
7. Только после этого реализуй компоненты.

Используй Phosphor Icons для интерфейсных иконок. Не используй эмодзи в качестве основных UI-иконок.

Все элементы интерфейса должны выглядеть согласованно.

## 9. Главная страница

На главной странице размести:

* главное фото автомобиля;
* название студии;
* краткое описание;
* заметный заголовок «Запись в студию» над карточкой записи;
* услуги с ценами;
* галерею выполненных работ;
* адрес;
* телефон;
* график работы;
* три информационные карточки;
* кнопки связи и записи.

Не показывай фиктивные рейтинги, отзывы, гарантии, цены и неподтверждённые сведения.

Если для образца нет фотографий, используй явно демонстрационные изображения, которые можно заменить.

Не выдавай временные фотографии за настоящие работы конкретной студии.

## 10. Glassmorphism и анимации

Внизу мобильного экрана нужна навигация:

* «Главная»;
* «Услуги»;
* «Моя запись».

Создай аккуратный стеклянный эффект.

Нижняя панель не должна закрывать контент, кнопки, последнюю карточку или поля формы.

Учитывай нижнюю безопасную область экрана через `env(safe-area-inset-bottom)`.

На главном изображении размести широкую кнопку «Записаться» с таким же стеклянным визуальным языком.

Требования:

* кнопка перемещается вместе с фотографией;
* не появляется эффект случайного просвечивания букв из соседних разделов;
* текст остаётся контрастным и чётким;
* кнопка не блокирует нежелательные области изображения;
* нажатие работает на телефоне и компьютере;
* кнопка не вызывает layout shifts;
* blur и backdrop-filter не должны чрезмерно нагружать слабые устройства.

Сначала создай основной эффект, затем проверь его на реальной прокрутке.

Не исправляй просвечивание случайными `z-index`. Разбери stacking context, isolation, clipping, transforms и позиционирование элементов.

Добавь плавное появление разделов при прокрутке. Соблюдай `prefers-reduced-motion`.

При отключённых анимациях пользователь должен получать полностью рабочий интерфейс без навязчивых эффектов.

Обеспечь видимые фокусные состояния клавиатуры и корректные состояния наведения, нажатия, загрузки и отключённых элементов.

## 11. Адаптивность

Проверь интерфейс как минимум на:

* ширине 320 px;
* ширине 360–390 px;
* ширине 430 px;
* планшетной ширине;
* стандартном ноутбуке;
* широком десктопе.

Особенно проверь:

* нижнюю навигацию;
* формы;
* горизонтальные карточки;
* календарь;
* длинные названия услуг;
* суммы и цены;
* галерею;
* модальные окна;
* кабинет владельца;
* прокрутку и safe areas.

Ни одна кнопка не должна перекрывать другой элемент, а контент не должен уходить за пределы экрана без необходимости.

Проверь клавиатурную навигацию и доступность основных интерактивных компонентов.

---

# ЧАСТЬ V. БАЗА ДАННЫХ И БЕЗОПАСНОСТЬ

## 12. Модель данных

Спроектируй нормализованную схему PostgreSQL.

Используй UUID для внутренних идентификаторов там, где это целесообразно.

Основные сущности:

* `tenants`;
* `tenant_members`;
* `tenant_settings`;
* `services`;
* `work_bays`;
* `opening_hours`;
* `schedule_exceptions`;
* `customers`;
* `vehicles`;
* `bookings`;
* `booking_services` или эквивалентная структура снимков услуг;
* `booking_status_history`;
* `gallery_items`;
* `financial_transactions`;
* `assistant_usage`;
* необходимые таблицы для уведомлений и аудита.

Не создавай таблицы без необходимости. Не складывай все данные приложения в одну неструктурированную таблицу.

Используй внешние ключи, ограничения, индексы, миграции и понятные связи.

### Снимок услуги в заказе

При создании бронирования зафиксируй согласованные на этот момент сведения об услуге: название, длительность, цену и валюту.

Если владелец изменит прайс или длительность позже, исторический заказ не должен автоматически менять свою согласованную стоимость или описание.

Новое расписание должно учитывать действующие настройки услуг, а уже созданные заказы — иметь предсказуемую и документированную семантику изменения.

## 13. Изоляция студий

Каждая закрытая запись должна быть связана с конкретной студией.

Настрой RLS для соответствующих таблиц Supabase.

Проверь:

* чтение;
* вставку;
* изменение;
* удаление;
* загрузку файлов;
* серверные функции;
* финансовые операции;
* назначение ролей.

Все защищённые действия должны проверять реальные права пользователя на сервере.

Не доверяй `tenant_id`, роли, сумме оплаты или любым другим критическим данным, переданным клиентом.

Slug студии используется для определения публичного контекста, но не является секретом и не заменяет авторизацию.

Настрой необходимые SQL-привилегии наряду с RLS.

Публичная часть может получать только те сведения о студии, которые действительно предназначены для отображения клиентам.

Клиент не должен иметь возможность читать полные таблицы клиентов, внутренние комментарии и историю чужих заказов.

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

Service-role keys и secret keys никогда не должны попадать во frontend или клиентскую сборку.

## 14. Защита конфигурации и секретов

Подготовь:

* `.env.example`;
* корректный `.gitignore`;
* локальные переменные окружения;
* проверку обязательных переменных при запуске;
* понятные сообщения об отсутствующих настройках без вывода секретов.

Не коммить `.env.local` и реальные ключи.

Допустимый публичный ключ Supabase можно использовать в клиентском приложении только при корректно настроенных политиках безопасности.

Секреты API-модели, service-role keys и приватные VAPID-ключи храни в серверном окружении.

Не выводи полные URL с секретными токенами, пароли, ключи и приватные данные в консоль, отчёты или скриншоты.

При изменении конфигурации проверь, что секреты не попали в `dist`.

---

# ЧАСТЬ VI. ЗАПИСЬ И РАСПИСАНИЕ

## 15. Клиентский сценарий

Клиент без обязательной регистрации:

1. Открывает брендированное приложение студии.
2. Просматривает услуги.
3. Выбирает услугу.
4. Выбирает дату.
5. Получает список доступных интервалов.
6. Выбирает время.
7. Вводит имя, телефон и автомобиль.
8. Подтверждает запись.
9. Получает подробности записи.
10. Может вернуться к своей записи и отменить её по правилам студии.

Поля валидируются как на клиенте, так и на сервере через Zod.

Показывай свободное и занятое время понятным образом.

Не показывай устаревший слот как гарантированно свободный.

Не подтверждай заказ до сохранения в базе данных.

Обеспечь защиту от спама и слишком частых запросов.

## 16. Корректная работа расписания

Рассчитывай занятость по:

* графику работы;
* часовой зоне;
* выходным;
* разовым исключениям;
* длительности услуги;
* времени подготовки;
* доступности боксов;
* существующим бронированиям;
* отменённым записям;
* многодневным работам.

Многочасовая и многодневная работа должна занимать бокс на всём интервале.

Учитывай переходы на летнее и зимнее время там, где они существуют.

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

Используй `date-fns` и `date-fns-tz` с явной логикой часового пояса каждой студии.

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

## 17. Атомарное бронирование

Это один из самых критических участков проекта.

Не реализуй бронирование как две независимые операции:

1. запрос на проверку доступности;
2. отдельная вставка заказа без защиты от конкуренции.

Создание записи должно выполняться атомарно на стороне PostgreSQL.

Используй подходящие транзакции, блокировки и/или ограничения целостности. Рассмотри exclusion constraint PostgreSQL для запрета пересечений активных интервалов одного бокса.

Операция бронирования должна:

* проверять корректность студии и услуги;
* проверять актуальность цены и длительности по правилам приложения;
* рассчитывать полный интервал занятости;
* учитывать время подготовки;
* проверять конфликты;
* атомарно резервировать ресурс;
* создавать запись;
* возвращать подтверждённый результат.

Если интервал уже занят, возвращай контролируемый конфликт, например HTTP 409, и предлагай обновить свободные слоты.

Не допускай частично созданных заказов.

### Идемпотентность

Повторный запрос с тем же ключом идемпотентности должен возвращать результат исходной операции.

Ключ должен быть привязан к корректному контексту операции. Не допускай повторного использования ключа для другого тела заказа без обнаружения конфликта.

Если клиент не получил ответ из-за таймаута, он должен иметь возможность безопасно повторить запрос, не создав вторую заявку.

Защита не должна зависеть только от отключения кнопки после нажатия.

Перенос, отмена и ручное создание записи владельцем также должны учитывать доступность ресурсов.

---

# ЧАСТЬ VII. КАБИНЕТ ВЛАДЕЛЬЦА

## 18. Авторизация

Реализуй отдельный вход владельца по электронной почте и паролю через Supabase Auth.

Предусмотри корректную обработку:

* неверного пароля;
* истёкшей сессии;
* выхода;
* обновления сессии;
* восстановления доступа;
* отсутствия прав;
* перехода к несуществующей студии.

Не допускай доступа в кабинет только на основании изменения URL.

Владелец должен иметь подтверждённое членство в своей студии.

## 19. Расписание и заказы

Владелец видит:

* записи на день;
* записи на неделю;
* предстоящие заезды;
* статусы автомобилей;
* завершённые работы;
* отмены;
* зарегистрированные оплаты;
* возвраты;
* основные итоги за выбранный период.

Пагинируй большие списки. Не загружай всю историю бесконтрольно.

Владелец может:

* вручную создать запись;
* перенести запись;
* отменить запись;
* принять автомобиль;
* отметить работу завершённой;
* отметить автомобиль готовым;
* добавить комментарий;
* зарегистрировать оплату;
* зарегистрировать возврат.

Каждая операция проверяет права и состояние записи.

Изменение статуса должно проходить по согласованной модели переходов. Не разрешай случайные противоречивые статусы.

## 20. Настройки студии

Владелец изменяет:

* название;
* описание;
* адрес;
* телефон;
* график;
* выходные;
* часовой пояс;
* услуги;
* цены;
* длительности;
* боксы;
* время подготовки;
* логотип;
* главное изображение;
* три информационные карточки;
* фотографии и подписи;
* правила записи и отмены.

Все изменения сохраняются в PostgreSQL.

Изменения должны появляться на публичной странице после корректного обновления данных без необходимости вручную редактировать исходный код или пересобирать всё приложение.

Обрабатывай состояние сохранения, ошибки валидации и конфликты изменений.

---

# ЧАСТЬ VIII. ФОТОГРАФИИ И STORAGE

## 21. Управление галереей

Для фотографий работ создай три независимых действия:

1. Добавить карточку с новой фотографией.
2. Заменить фотографию конкретной существующей карточки.
3. Изменить подпись конкретной карточки.

Замена одной фотографии не должна удалять остальные работы.

Каждая карточка должна иметь устойчивый идентификатор и явную принадлежность студии.

Загруженные фотографии сохраняются в Supabase Storage.

Проверяй:

* допустимые типы;
* MIME-тип и сигнатуру файла;
* размер;
* ограничения доступа;
* принадлежность студии;
* корректность ссылок;
* поведение при ошибке загрузки.

Не доверяй расширению файла.

Не делай все объекты публичными по умолчанию. Публично доступными могут быть только фотографии, предназначенные для сайта.

Предусмотри безопасное удаление устаревших файлов и не удаляй используемое изображение до успешной замены.

Проверь отображение изображений на узких экранах, загрузку и резервные состояния при недоступности фотографии.

---

# ЧАСТЬ IX. ФИНАНСЫ

## 22. Финансовые операции

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

Создай отдельный журнал финансовых операций.

Сохраняй:

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

Используй целые минимальные единицы валюты либо точный десятичный числовой тип.

Не используй обычный floating-point для точных денежных итогов.

Возврат не удаляет исходную оплату. Он регистрируется отдельной операцией.

Показывай раздельно:

* стоимость работ;
* зарегистрированные поступления;
* возвраты;
* чистые поступления;
* количество завершённых работ;
* число заездов.

Для денежных отчётов фиксируй временной интервал и часовой пояс студии.

Все операции проверяются на сервере.

Если деньги внесены вручную владельцем, показывай их как зарегистрированные вручную. Не называй это банковским подтверждением без платёжной интеграции.

---

# ЧАСТЬ X. ИИ-ПОМОЩНИКИ

## 23. Помощник клиента

Добавь чат, который понимает обычные вопросы:

* «Когда ближайшее окно?»
* «Сколько стоит полировка?»
* «Как найти студию?»
* «Сколько занимает мойка?»

Отобрази примеры вопросов кнопками быстрого старта.

Помощник отвечает по конкретной студии.

Создай ограниченные серверные инструменты для:

* получения опубликованных услуг;
* получения актуальных цен и длительности;
* получения адреса и графика;
* получения актуального списка свободных интервалов.

Сначала получай проверенные данные из серверных функций, затем формируй ответ модели.

Модель не имеет произвольного SQL-доступа и не получает список всех клиентов.

Не позволяй помощнику придумывать цены, адреса, свободное время или статус бронирования.

Если информации недостаточно, задавай уточняющий вопрос.

Если нужная интеграция не настроена, честно сообщай о недоступности. Не имитируй настоящий ответ языковой модели без явного обозначения демонстрационного режима.

### Защита

Ограничивай:

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

Ключ модели хранится только в серверных секретах.

Защищай инструменты от prompt injection из пользовательских сообщений и содержимого конфигурации.

Не разрешай клиентскому помощнику менять запись, цены, расписание, статусы или финансовые данные.

Если помощник предложил свободное время, сервер должен повторно проверить доступность при фактическом создании бронирования.

### Устойчивость

При недоступности AI API:

* клиент может продолжать оформлять запись;
* кабинет владельца продолжает работать;
* основной функционал не зависит от языковой модели;
* пользователь получает понятное сообщение об ошибке;
* временная ошибка не запускает бесконечные повторы запросов.

## 24. Помощник владельца

Добавь отдельный помощник для владельца.

Вопросы:

* «Что у меня завтра?»
* «Сколько машин было на неделе?»
* «Сколько денег получено?»
* «Сколько было отмен за месяц?»

Ответы рассчитываются по реальным данным конкретной студии.

Количество работ зависит от согласованных правил статусов, а суммы поступлений и возвратов — от финансового журнала.

Все данные предварительно получают разрешённые серверные функции.

Помощник работает в режиме чтения и не изменяет данные по собственной инициативе.

Запрос на перенос, отмену, изменение цены или финансовую операцию должен направляться к соответствующей форме кабинета с явным подтверждением пользователя.

---

# ЧАСТЬ XI. PWA, УВЕДОМЛЕНИЯ И ОФЛАЙН

## 25. Установка приложения на телефон

Используй `vite-plugin-pwa` и Workbox.

Для каждой студии предусмотрены:

* имя;
* короткое имя;
* иконки;
* цветовая тема;
* `id`;
* `start_url`;
* `scope`;
* web app manifest.

Публичные адреса должны иметь вид:

`/s/<slug>/`

Клиент должен открывать нужное приложение по ссылке без обязательной установки.

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

### Важный технический нюанс

Vite обычно генерирует общую frontend-сборку и базовый PWA-манифест. Не предполагай, что простой React-компонент автоматически меняет идентичность установленного приложения на каждом URL.

До реализации изучи фактический механизм манифестов, HTML и service worker.

Найди и реализуй надёжный способ индивидуального имени, иконки и стартового URL для каждой студии.

Рассмотри динамически обслуживаемые манифесты, специализированные HTML-маршруты или автоматизированную генерацию необходимой статики, если это требуется для корректной установки.

Проверь фактическое поведение минимум в целевых браузерах, доступных для тестирования.

Если определённый браузер не поддерживает нужный сценарий, опиши ограничение. Не заявляй об одинаковом поведении на всех телефонах без проверки.

## 26. Офлайн-режим

Кешируй необходимые статические ресурсы и публичный контент, если это безопасно.

Не кешируй чувствительные данные владельца, закрытые ответы API или информацию о клиентах в общедоступном кеше.

При отсутствии соединения:

* показывай понятное состояние;
* не показывай устаревший слот как гарантированно свободный;
* не подтверждай новую запись;
* не теряй конфигурацию установленного приложения;
* не смешивай данные разных студий.

Проверь обновление Service Worker, очистку устаревших кешей и корректное обновление версии приложения.

## 27. Напоминание за сутки

После записи предложи клиенту включить напоминание.

Для реального уведомления при закрытом приложении используй серверный механизм Web Push, если он полностью настроен.

Обеспечь:

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

Не обещай, что локальный таймер сработает при закрытом браузере.

Если Web Push ещё не настроен, обязательно реализуй экспорт события в календарь через файл ICS.

Не изображай неотправленное или недоставленное уведомление как подтверждённое.

---

# ЧАСТЬ XII. ПРОИЗВОДИТЕЛЬНОСТЬ И НАГРУЗКА

## 28. Цель нагрузки

Проверь, что система способна обрабатывать следующие сценарии:

1. Обычный просмотр страниц 100 виртуальными пользователями.
2. Одновременную работу клиентов с расписанием.
3. Не менее 100 конкурентных уникальных отправок заказов.
4. 100 попыток бронирования одного и того же временного интервала.
5. Резкое увеличение нагрузки.
6. Продолжительную нагрузку.
7. Параллельную работу с несколькими студиями.
8. Запросы к AI API в пределах предусмотренных лимитов.

Разделяй обычных виртуальных пользователей и реальную конкурентную нагрузку на создание заказов. Эти сценарии не взаимозаменяемы.

## 29. Nагрузочные тесты k6

Создай отдельные сценарии:

* `smoke`;
* `10 users`;
* `100 users`;
* `100 concurrent bookings`;
* `100 conflicting bookings`;
* `spike`;
* `soak`.

Реализуй их как настоящие тестовые файлы и команды в `package.json`.

Тестируй production-сборку локального приложения и тестовую базу данных. Не выдавай dev-сервер за окончательную оценку производительности.

У каждой тестовой заявки должны быть свои данные, если она представляет независимый заказ.

### Тест независимых записей

Создай 100 валидных уникальных заявок для разных доступных интервалов.

Проверь:

* HTTP-ответы;
* количество записей до теста;
* количество записей после теста;
* отсутствие дублей;
* отсутствие потерь;
* длительность запросов;
* отсутствие ошибок исчерпания ресурсов.

### Тест конкурентного конфликта

Создай 100 конкурентных попыток забронировать один бокс на один и тот же интервал.

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

Проверь фактическое состояние PostgreSQL.

### Предварительные цели производительности

Используй следующие предварительные пороги:

* p95 критических запросов не более 2 секунд;
* p99 не более 5 секунд;
* менее 1% неожиданных ошибок HTTP;
* отсутствие потерянных и дублированных записей;
* отсутствие необъяснённых ошибок исчерпания ресурсов.

Ожидаемый HTTP 409 для занятого времени не считается неожиданной ошибкой.

Показатели должны подтверждаться запуском теста. Укажи среду, оборудование, длительность, число виртуальных пользователей и точный сценарий.

Не утверждай, что локальное тестирование гарантирует такую же производительность будущего хостинга.

## 30. Проверка стабильности

Во время нагрузочных тестов наблюдай:

* CPU и память;
* задержки серверных функций;
* соединения PostgreSQL;
* долгие SQL-запросы;
* таймауты;
* размер очередей;
* частоту повторов;
* ошибки интеграций.

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

Настрой пагинацию списков, подходящие индексы и эффективную загрузку данных.

Не добавляй сложное кеширование, если оно способно показать старую цену, устаревшую доступность или данные другой студии.

---

# ЧАСТЬ XIII. АВТОМАТИЧЕСКОЕ ТЕСТИРОВАНИЕ

## 31. Обязательные виды тестов

### Vitest

Покрой бизнес-логику тестами:

* расчёт длительности;
* учёт подготовки;
* переходы статусов;
* календарные границы;
* расчёт денег;
* подсчёт оплат и возвратов;
* ограничения бронирования;
* валидацию конфигураций;
* отображение состояний ошибок.

### Интеграционные тесты

Проверь:

* работу с PostgreSQL;
* миграции;
* транзакционность бронирования;
* идемпотентность;
* RLS;
* права доступа к студиям;
* хранение фотографий;
* финансовые операции;
* ошибки Edge Functions.

### Playwright

Проверь:

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

### Безопасность

Протестируй:

* подстановку чужого ID;
* изменение `tenant_id`;
* доступ к чужому заказу;
* попытку чтения закрытых финансовых данных;
* обход проверки роли;
* некорректные входные данные;
* чрезмерно длинные сообщения;
* повторные запросы;
* запрещённые Storage-операции.

### Исправление ошибок

Если тест провалился:

1. Сохрани сообщение об ошибке.
2. Найди причину.
3. Исправь минимально необходимый участок.
4. Запусти провалившийся тест повторно.
5. Запусти связанный набор регрессионных тестов.
6. Зафиксируй результат.

Не удаляй падающий тест только для того, чтобы получить зелёный отчёт.

Не обходи проверки с помощью фиктивных ответов.

---

# ЧАСТЬ XIV. ЛОКАЛЬНАЯ РАЗРАБОТКА

## 32. Запуск без покупки хостинга

Весь основной сценарий должен работать локально на компьютере разработчика.

Используй локальный Supabase CLI и Docker, если они доступны.

Подготовь:

* `README.md` на русском языке;
* `.env.example`;
* конфигурацию локальной базы;
* миграции;
* seed-данные;
* две демонстрационные студии;
* инструкции создания тестовых пользователей;
* команды запуска и остановки;
* команды тестирования;
* команды просмотра логов;
* инструкции устранения распространённых ошибок.

Должна быть возможность проверить создание новой студии без публикации в интернет.

Если Docker или локальный Supabase не запускается на машине пользователя, не делай вид, что локальный backend работает. Диагностируй проблему и объясни, какие действия необходимы.

Не выполняй автоматический сброс базы без предупреждения.

## 33. Команды проекта

Реализуй согласованные команды:

* `pnpm dev`;
* `pnpm lint`;
* `pnpm typecheck`;
* `pnpm test`;
* `pnpm test:e2e`;
* `pnpm build`;
* `pnpm preview`;
* `pnpm load:smoke`;
* `pnpm load:10`;
* `pnpm load:100`;
* `pnpm load:burst`.

Все команды должны реально существовать в `package.json` либо иметь чётко документированную замену.

Добавь команды для работы с tenant-конфигурациями и локальной базой.

Настрой необходимую конфигурацию Playwright и установи браузеры, если они отсутствуют.

Настрой k6 так, чтобы тесты случайно не запускались против production.

---

# ЧАСТЬ XV. ПЛАН РЕАЛИЗАЦИИ

## 34. Работай по этапам и не останавливайся после составления плана

Не пытайся реализовать всё огромным неделимым изменением.

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

Не ограничивайся написанием рекомендаций или красивого прототипа. Фактически создавай файлы, запускай команды и проверяй результат.

### Этап 1. Аудит

* изучить текущий проект;
* проверить skills и MCP;
* изучить Astryx и shadcn;
* проверить доступные зависимости;
* выбрать единую архитектуру интерфейса;
* подготовить таблицу требований;
* подготовить модель данных и порядок миграций.

### Этап 2. Основа проекта

* настроить TypeScript и Vite;
* подключить согласованную дизайн-систему;
* настроить маршрутизацию;
* настроить TanStack Query;
* подключить Zod;
* подготовить базовую тему;
* настроить локальный Supabase;
* подготовить миграции;
* настроить базовые тесты.

### Этап 3. Полный вертикальный сценарий

Сначала реализуй один полностью работающий путь:

1. Открытие студии.
2. Просмотр услуги.
3. Получение доступных интервалов.
4. Создание записи.
5. Сохранение в PostgreSQL.
6. Отображение записи в кабинете.
7. Проверка прав доступа.
8. Проверка отсутствия дубля.

Не переходи к дополнительным необязательным функциям, если этот сценарий не работает.

### Этап 4. Интерфейс

Реализуй:

* главную страницу;
* каталог услуг;
* галерею;
* формы записи;
* календарь;
* нижнюю навигацию;
* стеклянную кнопку;
* состояния загрузки и ошибки;
* мобильную и десктопную верстку.

Используй полученные рекомендации ui-ux-pro-max, Astryx и shadcn.

### Этап 5. Кабинет владельца

Реализуй:

* авторизацию;
* расписание;
* изменение записей;
* изменение настроек;
* галерею;
* боксы;
* услуги и цены;
* финансовый журнал;
* отчёты.

Проверь каждую защищённую операцию.

### Этап 6. Быстрое создание студий

Реализуй шаблоны, конфигурации, CLI, загрузку изображений и статусы публикации.

Создай минимум две тестовые студии с разными данными и визуально разными конфигурациями.

Докажи, что смена студии не смешивает записи, настройки и права.

### Этап 7. Помощники и PWA

Добавь серверные инструменты помощников, интеграцию модели с лимитами, генерацию манифестов, service worker и сценарии офлайн-работы.

Если отсутствуют реальные API-ключи, подготовь корректную инфраструктуру и тестовый режим, но не выдавай его за работающую production-интеграцию.

### Этап 8. Испытания

Запусти:

* lint;
* typecheck;
* unit-тесты;
* интеграционные тесты;
* build;
* Playwright;
* сценарии конкурентного бронирования;
* нагрузочные тесты k6.

Исправь ошибки и повтори соответствующие тесты.

### Этап 9. Подготовка к публикации

Подготовь конфигурацию Vercel и Supabase для дальнейшего развёртывания.

Не выполняй платные и потенциально необратимые действия без разрешения.

Если пользовательские аккаунты уже подключены, не считай это автоматическим разрешением на публикацию в production.

При успешном тестировании можно подготовить preview-развёртывание, если оно доступно и не создаёт неожиданных расходов.

### Этап 10. Итоговая документация

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

---

# ЧАСТЬ XVI. ОБРАБОТКА ОШИБОК И РЕГРЕССИЯ

## 35. Обязательные проверки перед каждым крупным изменением

Перед изменением критических файлов:

* проверь Git-статус;
* сохрани безопасную точку восстановления;
* изучи зависимости файла;
* не перезаписывай пользовательские изменения.

После изменения:

* проверь типы;
* запусти соответствующие тесты;
* проверь сборку;
* просмотри ошибочные сообщения;
* проверь связанные сценарии.

Не устанавливай новые библиотеки без понимания, зачем они нужны.

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

Не изменяй бизнес-логику бронирования ради косметического исправления интерфейса.

Не удаляй существующие тесты для обхода ошибок.

Если MCP возвращает ошибку, проверь схему инструмента и документацию вместо многократного вызова с выдуманными параметрами.

Если внешняя интеграция недоступна, изолируй её и продолжи локальную реализацию там, где это возможно.

---

# ЧАСТЬ XVII. ПУБЛИКАЦИЯ И РАСХОДЫ

## 36. Подготовка к Vercel

Используй Vercel для frontend, если выбранная архитектура с Supabase и маршрутизацией совместима с реальными возможностями платформы.

Перед публикацией проверь:

* корректность сборки;
* SPA fallback для маршрутов `/s/<slug>/`;
* отсутствие утечек секретов в `dist`;
* переменные окружения;
* доступность серверных функций;
* корректность manifest и иконок;
* работу авторизации;
* CORS;
* доступность базы;
* безопасность публичных маршрутов.

Не заявляй, что приложение опубликовано, если URL не проверен фактически.

Не покупай тарифы и не создавай платные ресурсы без разрешения.

Учитывай, что локальная проверка не подтверждает доступность будущего production-сервера.

Перед коммерческим запуском проверь актуальные условия выбранных тарифов и необходимые лимиты.

---

# ЧАСТЬ XVIII. ФИНАЛЬНАЯ ПРИЁМКА

## 37. Функциональные критерии

Работу можно считать завершённой только после подтверждения следующих пунктов:

* [ ] Клиент открывает персональное приложение студии.
* [ ] Клиент видит правильное название и услуги.
* [ ] Клиент может создать запись.
* [ ] Запись реально сохраняется в PostgreSQL.
* [ ] Владелец видит её в своём кабинете.
* [ ] Повторный запрос не создаёт дубли.
* [ ] Двойное бронирование одного недоступного интервала исключено.
* [ ] Многодневная услуга занимает ресурс на всём необходимом интервале.
* [ ] Владелец может редактировать настройки.
* [ ] Фотографии заменяются независимо.
* [ ] Оплаты и возвраты учитываются раздельно.
* [ ] Клиентский помощник использует реальные данные.
* [ ] Помощник владельца отвечает на основе базы.
* [ ] Данные студий изолированы.
* [ ] PWA-манифест и иконки проверены в поддерживаемых сценариях.
* [ ] Новую студию можно создать без изменения бизнес-кода.
* [ ] Автоматические тесты запущены.
* [ ] Проведены нагрузочные испытания.
* [ ] Подготовлена инструкция локального запуска.
* [ ] Подготовлена инструкция создания новой студии.

## 38. Статусы

Используй:

* `PASS` — проверка выполнена и пройдена;
* `FAIL` — проверка выполнена и провалена;
* `NOT TESTED` — проверка не запускалась;
* `BLOCKED` — проверку невозможно завершить из-за конкретного препятствия.

Не помечай пункт как `PASS` только на основании просмотра исходного кода или предположения.

## 39. Финальный отчёт

В конце предоставь:

1. Архитектуру проекта.
2. Основные файлы и структуру.
3. Список действительно использованных Skills и MCP.
4. Информацию о применении Astryx и shadcn.
5. Реализованные функции.
6. Результаты lint, typecheck, unit-тестов, интеграционных тестов и Playwright.
7. Результаты нагрузочных тестов, включая p95, p99 и количество запросов.
8. Результаты проверки дублей и конкурентного бронирования.
9. Результаты проверки изоляции студий.
10. Известные ошибки и ограничения.
11. Инструкцию запуска на Windows.
12. Инструкцию создания следующей студии.
13. Необходимые переменные окружения без раскрытия секретов.
14. Необходимые дальнейшие действия для публикации.
15. Стоимость и ограничения сервисов, если они были проверены.
16. Фактически работающую публичную ссылку, только если публикация действительно состоялась.

Не скрывай ошибки и не придумывай результаты.

**Главный критерий успеха:** один качественный базовый продукт должен позволять создавать отдельные брендированные приложения для реальных студий. Клиент действительно записывается, владелец управляет своим бизнесом, безопасность и конкурентное бронирование подтверждены тестами, а новые студии создаются воспроизводимым процессом без ручного переписывания приложения.