architect/decisions/002-platform-architecture.md

ADR-002: Архитектура Unified Commerce Platform

Дата: 2025-12-19
Статус: Draft


1. ДОМЕНЫ: Один домен vs Поддомены

Вариант A: Один домен с путями

app.0kt.ru/
├── /products     → PIM
├── /orders       → ORDERS
├── /ozon         → MARKETPLACE
├── /clients      → CRM
├── /suppliers    → DROPSHIP
├── /finance      → FINANCE
├── /robots       → ROBOTS
└── /analytics    → ANALYTICS

Плюсы:
- Единый SSL сертификат
- Общие cookies/сессии (auth из коробки)
- Один деплой
- Проще nginx конфиг
- Пользователь не замечает переходов

Минусы:
- Монолит (если упал — упало всё)
- Сложнее масштабировать отдельный модуль
- Один процесс = один uvicorn


Вариант B: Поддомены

pim.app.0kt.ru      → PIM
orders.app.0kt.ru   → ORDERS
ozon.app.0kt.ru     → MARKETPLACE
crm.app.0kt.ru      → CRM

Плюсы:
- Независимые деплои
- Можно масштабировать отдельно
- Изоляция ошибок (упал CRM — PIM работает)
- Разные технологии на разных поддоменах

Минусы:
- Сложная аутентификация (нужен SSO или shared cookies)
- Несколько SSL сертификатов (или wildcard)
- CORS при API запросах между доменами
- Сложнее разработка и отладка


Вариант C: Гибрид (РЕКОМЕНДУЕТСЯ)

app.0kt.ru/              ← Единый UI (монолит)
├── /products
├── /orders
└── /settings

api.0kt.ru/v1/           ← Единый API Gateway
├── /pim/
├── /orders/
└── /marketplace/

Плюсы:
- UI единый = простая навигация и auth
- API можно разбить на микросервисы позже
- Один entry point для фронта
- Гибкость масштабирования

Минусы:
- Нужен API Gateway (но FastAPI справится)


РЕШЕНИЕ: Вариант C — Гибрид

app.0kt.ru       → Единый FastAPI с UI (Jinja2 + HTMX)
                   Все модули как роутеры внутри одного приложения

Позже (Q3+):
api.0kt.ru       → API Gateway для внешних интеграций

2. БАЗА ДАННЫХ: Одна vs Много vs Префиксы

Вариант A: Одна общая БД, одна схема

-- Все таблицы в public или pt7k98pv0fwi1el
pim_products
pim_categories
ozon_orders
ozon_accounts
crm_clients
dropship_suppliers

Плюсы:
- Простые JOIN между модулями
- Одно подключение
- Единые миграции
- Уже есть (NocoDB работает так)

Минусы:
- Нет изоляции модулей
- Сложно понять границы
- Риск конфликтов миграций


Вариант B: Одна БД, разные схемы

-- PostgreSQL schemas
pim.products
pim.categories
orders.orders
orders.shipments
crm.clients
dropship.suppliers

Плюсы:
- Логическая изоляция
- Можно делать бэкап по схемам
- JOIN всё ещё работает (schema.table)
- Разные права на схемы

Минусы:
- Сложнее ORM настройка
- NocoDB может не понять


Вариант C: Префиксы таблиц (РЕКОМЕНДУЕТСЯ)

-- Текущая схема pt7k98pv0fwi1el
pim_products          -- PIM модуль
pim_categories
pim_prices
ozon_orders           -- MARKETPLACE модуль
ozon_products
ozon_accounts
crm_clients           -- CRM модуль
crm_segments
fin_transactions      -- FINANCE модуль

Плюсы:
- Уже используется (pim_, ozon_)
- NocoDB понимает
- Простые JOIN
- Понятно какой модуль владеет таблицей
- Одно подключение SQLAlchemy

Минусы:
- Нет физической изоляции
- Длинные имена


Вариант D: Отдельные БД

database: pim_db        pim_*
database: orders_db     orders_*
database: crm_db        crm_*

Плюсы:
- Полная изоляция
- Независимые бэкапы
- Разные настройки производительности

Минусы:
- Нет JOIN между модулями (нужен API)
- Сложная синхронизация
- Больше подключений
- Ovekill для текущего масштаба


РЕШЕНИЕ: Вариант C — Префиксы

Одна БД: NocoDB PostgreSQL (pt7k98pv0fwi1el)

Префиксы:
pim_      — товары, категории, атрибуты
ozon_     — OZON данные
wb_       — Wildberries (Q3)
ym_       — Яндекс.Маркет (Q4)
ord_      — заказы (универсальные)
crm_      — клиенты
drop_     — поставщики
fin_      — финансы
bot_      — роботы

3. UI/НАВИГАЦИЯ: Меню сверху vs слева

Вариант A: Горизонтальное меню сверху

┌──────────────────────────────────────────────────┐
 [Logo] [Товары ▼] [Заказы] [CRM ▼] [Настройки]  
├──────────────────────────────────────────────────┤
                                                  
              Контент страницы                    
                                                  
└──────────────────────────────────────────────────┘

Плюсы:
- Привычно (как в веб-приложениях)
- Больше места для контента
- Хорошо для 5-7 пунктов

Минусы:
- При 9+ модулях — тесно
- Выпадающие меню неудобны
- Нет места для подпунктов


Вариант B: Боковое меню (sidebar) 2 уровня

┌────────┬─────────────────────────────────────────┐
│ PIM    │  [Header: Товары > Список]             │
│ ├ Товары│                                        │
│ ├ Цены  │  Контент страницы                      │
│ └ Склад │                                        │
│        │                                        │
│ ORDERS │                                        │
│ ├ Список│                                        │
│ └ Отгруз│                                        │
│        │                                        │
│ CRM    │                                        │
│ ├ Клиен │                                        │
│ └ Воронк│                                        │
└────────┴─────────────────────────────────────────┘

Плюсы:
- Видна вся структура сразу
- Удобно для 10+ пунктов
- Привычно для админ-панелей (1C, Bitrix24)
- Не нужны выпадающие меню

Минусы:
- Занимает 200-250px слева
- На мобильных нужен burger


Вариант C: Комбинированное (РЕКОМЕНДУЕТСЯ)

┌──────────────────────────────────────────────────┐
│ [≡] Logo     [🔍 Search]    [User ▼] [⚙️]       │ ← Компактный header
├────────┬─────────────────────────────────────────┤
│ □ PIM  │  Breadcrumb: Товары > Каталог          │
│   Товары│                                        │
│   Цены  │  ┌─────────────────────────────────┐  │
│   Склад │  │     Контент страницы            │  │
│        │  │                                  │  │
│ □ Заказы│  │                                  │  │
│   Список│  └─────────────────────────────────┘  │
│   Отгруз│                                        │
│        │                                        │
│ □ CRM  │                                        │
│ □ Закуп│                                        │
│ □ Робот│                                        │
│────────│                                        │
│ ⚙️ Наст│                                        │
└────────┴─────────────────────────────────────────┘

[≡] — Скрыть/показать sidebar
□ — Иконка модуля (можно свернуть до иконок)

Плюсы:
- Сворачиваемый sidebar (icons only / full)
- Header только для глобальных действий
- 2 уровня навигации
- Адаптив: burger на мобильных

Минусы:
- Чуть сложнее реализация


РЕШЕНИЕ: Вариант C — Комбинированное

Header (48px):
- Logo
- Global search
- Notifications
- User menu

Sidebar (240px, collapsible to 64px):
- Modules (PIM, Orders, CRM...)
- Subpages под каждым модулем
- Settings внизу

Content area:
- Breadcrumbs
- Page title + actions
- Main content

4. ДИЗАЙН: Какой взять за основу

Варианты

Вариант Описание
Tailwind UI Платный, но качественный
DaisyUI Бесплатный, на Tailwind
Flowbite Бесплатный, компоненты для Tailwind
AdminLTE Bootstrap, классика
Свой на Tailwind Полный контроль

РЕШЕНИЕ: Tailwind + DaisyUI + свои компоненты

Base: TailwindCSS 3.x
Components: DaisyUI (бесплатный, 50+ компонентов)
Icons: Heroicons или Lucide
Charts: Chart.js или ApexCharts

Цветовая схема:
- Primary: blue-600
- Sidebar bg: slate-900
- Content bg: slate-50
- Cards: white

Почему DaisyUI:
- Бесплатный
- Готовые компоненты (button, card, table, modal)
- Темы из коробки (light/dark)
- Работает с HTMX


5. ТЕХНОЛОГИИ: Полный стек

Backend

Компонент Технология Почему
Framework FastAPI Уже используем, async, быстрый
ORM SQLAlchemy 2.0 Async поддержка, type hints
Migrations Alembic Стандарт для SQLAlchemy
Validation Pydantic v2 Встроен в FastAPI
Auth python-jose + passlib JWT токены
Background Celery или arq Для роботов (Q3)

Frontend

Компонент Технология Почему
Templates Jinja2 Встроен в FastAPI
Interactivity HTMX Без JavaScript, SPA-like
CSS TailwindCSS + DaisyUI Утилитарный, быстро
Icons Heroicons SVG, от Tailwind
Charts Chart.js Простой, легкий

Infrastructure

Компонент Технология Почему
Database PostgreSQL Уже есть (NocoDB)
Cache Redis Сессии, очереди (Q2+)
Server Uvicorn + Gunicorn Production-ready
Reverse Proxy Nginx Уже настроен
Process Manager systemd Стандарт Linux

Структура проекта

unified-platform/
├── app/
│   ├── __init__.py
│   ├── main.py              ← FastAPI app
│   ├── config.py            ← Settings
│   ├── database.py          ← SQLAlchemy setup
│   │
│   ├── core/                ← Общее
│   │   ├── auth/            ← JWT, sessions
│   │   ├── middleware/      ← Logging, errors
│   │   └── deps/            ← Dependencies
│   │
│   ├── modules/             ← Модули
│   │   ├── pim/
│   │   │   ├── router.py    ← API endpoints
│   │   │   ├── views.py     ← HTML endpoints
│   │   │   ├── models.py    ← SQLAlchemy
│   │   │   ├── schemas.py   ← Pydantic
│   │   │   └── services.py  ← Business logic
│   │   ├── orders/
│   │   ├── marketplace/
│   │   ├── crm/
│   │   └── ...
│   │
│   └── web/                 ← UI
│       ├── templates/
│       │   ├── base.html
│       │   ├── components/  ← Jinja macros
│       │   └── modules/     ← По модулям
│       └── static/
│           ├── css/
│           └── js/
│
├── migrations/              ← Alembic
├── tests/
├── requirements.txt
├── .env
└── CLAUDE.md

6. СТРАТЕГИЯ: С нуля vs Доработка

Вариант A: С нуля

Что делаем:
Новый проект unified-platform/, пишем с чистого листа.

Плюсы:
- Чистая архитектура
- Нет legacy кода
- Правильная структура сразу
- Консистентный код

Минусы:
- Дольше до первого результата
- Нужно переписывать рабочий код
- Потеря времени на базовые вещи

Оценка: ~2-3 недели до MVP


Вариант B: Доработка pro1

Что делаем:
Берём pro1/@admin.service как базу, расширяем.

Плюсы:
- Уже есть auth, структура
- Быстрее старт
- Рабочий код не теряется

Минусы:
- Возможно кривая архитектура
- Нужно рефакторить по ходу
- Legacy решения

Оценка: ~1-2 недели до MVP


Вариант C: Гибрид (РЕКОМЕНДУЕТСЯ)

Что делаем:
1. Новый проект со структурой из п.5
2. Копируем рабочий код из pro1 (auth, models)
3. Переносим логику из @mp1.service (API)
4. Новый UI с нуля (DaisyUI)

unified-platform/           Новый проект
├── app/
   ├── core/auth/         из pro1 (адаптировать)
   ├── modules/
      ├── pim/           новый, данные из NocoDB
      ├── orders/        из @mp1.service
      └── marketplace/   из @mp1.service + @ozon.api
   └── web/templates/     новый UI

Плюсы:
- Чистая структура
- Рабочий код переиспользуется
- Новый UI без legacy
- Быстрый старт с правильным фундаментом

Минусы:
- Нужно аккуратно переносить код

Оценка: ~1.5-2 недели до MVP


РЕШЕНИЕ: Вариант C — Гибрид

План действий:

Шаг 1: Скаффолдинг (1 день)
├─ Создать unified-platform/ со структурой
├─ Настроить FastAPI + SQLAlchemy + Alembic
├─ Подключить к NocoDB PostgreSQL
└─ Базовый Tailwind + DaisyUI

Шаг 2: Auth (1 день)
├─ Перенести auth из pro1
├─ JWT + сессии
├─ Login/logout UI
└─ Middleware защиты

Шаг 3: Layout (1 день)
├─ base.html с sidebar
├─ Navigation component
├─ Breadcrumbs
└─ Responsive

Шаг 4: PIM модуль (2 дня)
├─ Список товаров (pim_products)
├─ Карточка товара
├─ Редактирование
└─ Поиск/фильтры

Шаг 5: Orders модуль (2 дня)
├─ Перенести из @mp1.service
├─ Список заказов
├─ Детали заказа
└─ Смена статуса

Шаг 6: OZON интеграция (2 дня)
├─ Перенести из @ozon.api
├─ Синхронизация
├─ Этикетки
└─ Отгрузки

ИТОГОВЫЕ РЕШЕНИЯ

Вопрос Решение
Домены Один домен app.0kt.ru с путями
База данных Одна БД с префиксами таблиц (pim_, ozon_, crm_)
Навигация Sidebar 2 уровня + compact header
Дизайн TailwindCSS + DaisyUI
Стек FastAPI + Jinja2 + HTMX + SQLAlchemy
Стратегия Гибрид — новый проект + перенос кода

Следующий шаг

Согласен с решениями? Если да — создаю структуру проекта.