# Alpinbet Signals Platform

Платформа для сбора, обработки и доставки сигналов Alpinbet.

## Состав проекта

- `backend/` — Express + Prisma API, авторизация, сигналы, push, админские маршруты.
- `frontend/` — Nuxt-клиент, лента сигналов, настройки, PWA/mobile shell.
- `parser/` — парсер Alpinbet, который читает HTML, извлекает сигналы и синхронизирует их в PostgreSQL.
- `forecast-ocr-service/` — OCR-сервис для распознавания прогноза с изображения.
- `traefik/` — reverse proxy, TLS и роутинг доменов.
- `docker-compose.yml` — основной способ запуска.

## Как это работает

1. `parser` получает страницы Alpinbet через сохраненную сессию.
2. Из HTML извлекаются сигналы, коэффициенты, команды и изображения прогноза.
3. Если у сигнала есть картинка прогноза, `parser` скачивает ее и отправляет multipart-запросом в `forecast-ocr-service`.
4. OCR-сервис возвращает `rawForecast` и нормализованный `forecast`.
5. `parser` сохраняет сигнал в PostgreSQL.
6. `backend` отдает API и отправляет push-уведомления.
7. `frontend` показывает сигналы, доступы и настройки пользователя.

## Безопасность в текущем состоянии

- JWT для веба хранится в `HttpOnly` cookie.
- Веб-клиент больше не хранит токен в `localStorage`.
- OCR больше не принимает произвольный `imageUrl`, только файл.
- Наружу должны смотреть только `80` и `443`.
- `adminer` и `dockmon` сейчас закомментированы в `docker-compose.yml`.
- Traefik dashboard использует `usersFile`, а не пароль, зашитый в репозиторий.

## Быстрый старт

1. Скопируйте `.env.example` в `.env`.
2. Заполните `.env` реальными значениями.
3. Проверьте `parser/.env`.
4. Поднимите стек:

```bash
docker compose up -d --build
```

5. Примените схему БД:

```bash
docker compose exec backend npx prisma db push
```

## Полезные команды

Сборка:

```bash
npm run build
cd backend && npm run build
cd frontend && npm run build
```

Проверка итогового compose-конфига:

```bash
docker compose config
```

Проверка OCR локально:

```bash
curl http://localhost:4010/health
curl -X POST http://localhost:4010/ocr/forecast -F "image=@./forecast-ocr-service/tmp-forecast-test.png"
```

## Переменные окружения

Корневой `.env`:

- `POSTGRES_DB`
- `POSTGRES_USER`
- `POSTGRES_PASSWORD`
- `JWT_SECRET`
- `PARSER_INTERNAL_SECRET`
- `NUXT_PUBLIC_API_BASE`
- `APP_PUBLIC_URL`
- `CORS_ORIGIN`
- `TRAEFIK_ACME_EMAIL`
- `SMTP_*`
- `VAPID_*`
- `FIREBASE_*`

`parser/.env`:

- `DATABASE_URL`
- `ALPINBET_BASE_URL`
- `ALPINBET_TARGET_URL`
- `ALPINBET_BOTS`
- `AUTH_ENABLED`
- `AUTH_LOGIN_URL`
- `AUTH_USERNAME`
- `AUTH_PASSWORD`
- `SESSION_FILE`
- `STATE_FILE`
- `POLL_INTERVAL_MS`
- `FORECAST_OCR_URL`
- `FORECAST_OCR_TIMEOUT_MS`
- `FORECAST_OCR_ENABLED`
- `BACKEND_INTERNAL_URL`
- `PARSER_INTERNAL_SECRET`

## Чеклист Перед Деплоем

- Заполните `.env` реальными секретами и не оставляйте `change_me_*`.
- Смените `JWT_SECRET`, `PARSER_INTERNAL_SECRET`, `POSTGRES_PASSWORD`, SMTP и Firebase credentials, если они уже где-то светились.
- Создайте `traefik/secrets/dashboard-users` на сервере.
- Проверьте, что наружу открыты только `80` и `443`.
- Убедитесь, что `adminer` и `dockmon` остаются закомментированными.
- Выполните `docker compose config` перед запуском.
- Поднимите стек через `docker compose up -d --build`.
- После старта выполните `docker compose exec backend npx prisma db push`.
- Проверьте `https://antigol.ru`, `https://api.antigol.ru/health` и обычный логин.
- Автобэкап PostgreSQL включён сервисом `postgres-backup`, архивы складываются в `./backups`.
- Сделайте контрольный backup PostgreSQL перед следующими продовыми изменениями.

## Полезные файлы

- [docker-compose.yml](/C:/Users/vlad/Documents/Projects/alpinbet-parser/docker-compose.yml)
- [traefik/dynamic/routes.yml](/C:/Users/vlad/Documents/Projects/alpinbet-parser/traefik/dynamic/routes.yml)
- [backend/prisma/schema.prisma](/C:/Users/vlad/Documents/Projects/alpinbet-parser/backend/prisma/schema.prisma)
- [parser/src/forecast-ocr.js](/C:/Users/vlad/Documents/Projects/alpinbet-parser/parser/src/forecast-ocr.js)
- [forecast-ocr-service/src/index.js](/C:/Users/vlad/Documents/Projects/alpinbet-parser/forecast-ocr-service/src/index.js)
