Files
wiki/tasks/apps-portal/docs/BRD.md
2026-04-12 21:55:33 +03:00

9.7 KiB
Raw Blame History

Бизнес-требования: Портал приложений (apps.mva154.duckdns.org)

1. Проблема

Сейчас веб-приложения разбросаны по разным адресам: • openclaw.mva154.duckdns.org/noisemap/openclaw.mva154.duckdns.org/snowbike-rag/ • и т.д.

Нет единой точки входа. При добавлении нового приложения нужно править конфиг nginx.


2. Что хотим получить

Страницу-портал по адресу apps.mva154.duckdns.org, на которой отображаются кнопки/карточки наших приложений. Нажал — перешёл на нужное приложение.

Главное требование: добавление нового приложения — это только добавление строки в конфиг-файл приложения, без правки nginx.


3. Функциональные требования

3.1 Главная страница

• Адрес: apps.mva154.duckdns.org • Сетка карточек приложений (grid, 24 колонки на десктопе, 1 колонка на мобильном) • Каждая карточка:

  • Иконка (emoji или SVG)
  • Название приложения
  • Краткое описание (1 строка)
  • Клик → переход на приложение

3.2 Карточки приложений

• Приложения загружаются из JSON-конфига (не из кода) • Новые приложения добавляются в конфиг — портал обновляется автоматически • Порядок: из конфига (поле order) • Активные/неактивные: поле enabled: true/false — скрыть если false

3.3 Навигация

• Клик по карточке → переход на URL приложения • Открывается в той же вкладке (или в новой — настройка в конфиге) • URL приложений — относительные пути на openclaw.mva154.duckdns.org


4. Архитектура

4.1 Схема

apps.mva154.duckdns.org
        │
        ▼
    Nginx (location /)
        │
        ▼
    Flask (порт 5560)  ← читает config.json
        │
        ▼
    HTML (карточки приложений)
        │
        ▼
    Клик → переход на openclaw.mva154.duckdns.org/{путь}

4.2 Конфиг приложений

Файл: config/apps.json

[
  {
    "id": "noisemap",
    "name": "Карта шума",
    "description": "Карта шумового загрязнения от авиации",
    "icon": "🛩️",
    "url": "https://openclaw.mva154.duckdns.org/noisemap/",
    "enabled": true,
    "order": 1
  },
  {
    "id": "snowbike-rag",
    "name": "Snowbike Поиск",
    "description": "Семантический поиск по базе знаний сноубайков",
    "icon": "🏔️",
    "url": "https://openclaw.mva154.duckdns.org/snowbike-rag/",
    "enabled": true,
    "order": 2
  }
]

Поля:id — уникальный ID (используется для имени файла аватарки) • name — название • description — описание • icon — emoji для аватарки (используется при генерации) • url — ссылка на приложение • enabled — показывать на портале • order — порядок сортировки • avatar — (опционально) путь к кастомной аватарке; если отсутствует — генерируется автоматически

4.3 Добавление нового приложения

  1. Добавить строку в config/apps.json
  2. При первом запуске Flask автоматически сгенерирует аватарку в static/avatars/{id}.png
  3. Готово — портал показывает новое приложение

НЕ нужно: • Править nginx • Перезапускать Flask (конфиг перечитывается при старте) • Создавать аватарку вручную


5. Требования к дизайну

5.1 Стиль

• Светлая тема (по мотивам snowbike-rag, но светлее) • Фон: #F8FAFC (светло-серый) • Карточки: белые (#FFFFFF), скруглённые углы (16px), лёгкая тень • Шрифт: Inter • Акцентный цвет: #3B82F6 (синий) • Текст: #0F172A (тёмный)

5.2 Карточка приложения

┌────────────────────────┐
│                        │
│    ┌──────────┐        │
│    │ аватарка │        │
│    │  80×80   │        │
│    └──────────┘        │
│                        │
│  Название приложения   │
│  Краткое описание      │
│                        │
└────────────────────────┘

• Аватарка: квадратная, скруглённая (12px), 80×80px, по центру карточки • Название: жирный шрифт, 18px, тёмный • Описание: обычный шрифт, 14px, серый (#64748B) • Hover: подсветка рамки синим, lift-эффект (тень), масштаб 1.02 • Аватарка — первое что бросается в глаза

5.3 Аватарки приложений

Автоматическая генерация при добавлении нового приложения:

При добавлении строки в config/apps.json Flask автоматически генерирует аватарку, если файл не существует.

Способ генерации: • Градиентный фон (по хэшу названия приложения → уникальный цвет) • По центру — первая буква названия или emoji иконка (крупно, белым цветом) • Сохраняется в static/avatars/{app_id}.png • Генерация: Python PIL/Pillow (без внешних API) • Размер: 200×200px (масштабируется в CSS)

Примеры:

🛩️ на синем градиенте → «Карта шума»
🏔️ на зелёном градиенте → «Snowbike Поиск»
🔍 на оранжевом градиенте → «Портал поиска»

Правила: • Если в конфиге указано поле avatar — используется указанное изображение • Если avatar отсутствует — генерируется автоматически • Цвет градиента определяется по хэшу name (детерминированно — всегда одинаковый для одного названия) • Формат: PNG, 200×200px

5.4 Заголовок

• Название портала: «Мои приложения» • Подзаголовок: «N активных приложений» • Светлый фон, тёмный текст

5.5 Адаптивность

• Десктоп: 34 колонки • Планшет: 2 колонки • Мобильный: 1 колонка


6. Технические требования

6.1 Стек

• Flask (порт 5560) • HTML + CSS + JS (один файл, inline) • Tailwind CSS через CDN • Google Fonts (Inter) через CDN

6.2 Nginx

• Домен apps.mva154.duckdns.org → location / → proxy_pass http://172.19.0.2:5560/ • Один location block, без правок при добавлении приложений • SSL через Certbot (как у основного домена)

6.3 Flask

GET / — главная страница (рендерит HTML из конфига) • GET /api/apps — JSON-список приложений (для отладки) • Конфиг: config/apps.json


7. Что НЕ входит

• Авторизация • Админка для добавления приложений (через JSON-файл) • Мониторинг статуса приложений (online/offline) • Уведомления о новых приложениях


8. Критерии приёмки

Открывается apps.mva154.duckdns.org — видно карточки приложений Клик по карточке — переход на нужное приложение Добавил строку в apps.json — портал показывает новое приложение с аватаркой Аватарка генерируется автоматически (градиент + emoji) НЕ нужно править nginx для нового приложения Хорошо выглядит на телефоне Светлая тема, похожая на snowbike-rag


9. Приоритет

Сейчас: Главная страница + карточки + автогенерация аватарок Позже: Анимации, кастомные аватарки, мониторинг статуса