Архитектура и состав монорепы
Репозиторий — npm workspaces + Turborepo. Node 20+ (витрина требует 22.13+), npm 10.
Приложения
| Каталог | Пакет | Что это |
|---|---|---|
apps/backend | @dtc/backend | MedusaJS v2 (2.17.2): Store/Admin API, админка на /app, фоновые задачи |
apps/web | @auto-paint-store/web | Витрина, Next.js App Router + Tailwind |
apps/cms | @auto-paint-store/cms | Strapi: содержимое главной страницы, баннеры, вкладки |
apps/e2e | @auto-paint-store/e2e | Playwright |
apps/docs | — | Эта документация (Docusaurus) |
:::note apps/docs вне workspace
В корневом package.json он исключён ("!apps/docs"): корневой overrides: { ajv: ^8 }
конфликтует с ajv@6, который тянет Docusaurus. Зависимости ставятся отдельно —
cd apps/docs && npm install.
:::
Инфраструктура
docker-compose.yml поднимает postgres, redis, meilisearch, minio, backend, cms, web
и одноразовые сервисы migrate, backend-init, minio-init, cms-db-init, cms-minio-init.
- Redis обязателен: на нём кэш, шина событий и движок workflow (
medusa-config.ts). - PostgreSQL — источник истины. Meilisearch — только публичный поисковый индекс каталога,
он синхронизируется по событиям (
subscribers/catalog-index-sync.ts). Любое расхождение решается в пользу данных Medusa: карточка товара дополнительно проверяет доступность через backend, чтобы снятый с публикации товар давал 404 даже при устаревшем индексе. - MinIO / S3 — изображения товаров и загрузки Strapi.
Как данные ходят между частями
Каталог и заказы. Витрина ходит в backend: стандартные Store API для корзины, чекаута,
заказов и аккаунтов; кастомные catalog/* — там, где стандартного API не хватает (поиск,
карточка товара, валидация корзины). См. Кастомные API.
Контент. Редактор пишет в Strapi → Strapi зовёт вебхук backend → backend перечитывает снимок. См. Контент из Strapi на витрину.
Остатки и заказы склада. Модуль moysklad-integration тянет остатки по расписанию и
отправляет заказы покупателей. См. Модуль МойСклад.
Фоновые задачи
apps/backend/src/jobs — расписание в config.schedule каждого файла:
| Задача | Расписание | Что делает |
|---|---|---|
cms-snapshot-refresh | каждую минуту | подстраховка вебхука Strapi |
moysklad-order-sync-retry | каждую минуту | повтор неудачной отправки заказа |
moysklad-stock-sync | каждые 15 минут | остатки из МойСклад |
expire-catalog-payment-carts | ежечасно | сброс корзин с брошенной оплатой |
poll-apiship-tracking-status | ежечасно | статусы отправлений ApiShip |
abandoned-cart-reminder | 03:00 | письмо о брошенной корзине |
sync-cdek-pickup-points-daily | 03:00 | справочник ПВЗ СДЭК |
Кастомные модули
apps/backend/src/modules: moysklad-integration, cms-snapshot, meilisearch,
site-content, payment-provider-config, shipping-provider-registry,
abandoned-cart-reminder, wishlist, notification-smtp.
Правило проекта: сначала стандартное решение Medusa, кастомный модуль — только там, где стандартного API действительно нет.