# Brief Bench FastAPI - Текущий статус проекта **Дата:** 17 декабря 2025 **Статус:** Базовая структура реализована, готова к продолжению --- ## Что реализовано ### 1. Структура проекта ``` brief-bench-fastapi/ ├── app/ │ ├── api/ │ │ └── v1/ │ │ ├── __init__.py │ │ └── auth.py POST /api/v1/auth/login │ ├── models/ │ │ ├── __init__.py │ │ ├── auth.py LoginRequest, LoginResponse, UserResponse │ │ ├── settings.py EnvironmentSettings, UserSettings │ │ ├── analysis.py SessionCreate, SessionResponse, SessionList │ │ └── query.py BenchQueryRequest, BackendQueryRequest │ ├── services/ │ │ ├── __init__.py │ │ └── auth_service.py AuthService (login logic) │ ├── interfaces/ │ │ ├── __init__.py │ │ ├── base.py TgBackendInterface (ЗАГЛУШКА - нужна реализация) │ │ └── db_api_client.py DBApiClient (методы для DB API) │ ├── middleware/ │ │ └── __init__.py │ ├── utils/ │ │ ├── __init__.py │ │ └── security.py JWT encode/decode │ ├── __init__.py │ ├── config.py Settings из .env │ ├── dependencies.py DI: get_db_client, get_current_user │ └── main.py FastAPI app с CORS ├── static/ Пусто (нужно скопировать из rag-bench) ├── tests/ Полный набор тестов (unit/integration/e2e) ├── certs/ Не создана (для mTLS) ├── .env.example ├── .gitignore ├── requirements.txt ├── Dockerfile ├── docker-compose.yml ├── DB_API_CONTRACT.md Полный контракт для DB API ├── README.md └── PROJECT_STATUS.md Этот файл ``` --- ## Реализованные компоненты ### 1. Configuration (app/config.py) - Загрузка из .env через pydantic-settings - Настройки для 3 окружений RAG (IFT, PSI, PROD) - JWT конфигурация - DB API URL ### 2. Pydantic Models (app/models/) **auth.py:** - `LoginRequest` - login (8 цифр) + client_ip - `UserResponse` - user_id, login, last_login_at, created_at - `LoginResponse` - access_token + user - `TokenPayload` - user_id, login, exp **settings.py:** - `EnvironmentSettings` - настройки для одного окружения (apiMode, bearerToken, platformUserId, etc.) - `UserSettings` - настройки пользователя для всех 3 окружений - `UserSettingsUpdate` - обновление настроек **analysis.py:** - `SessionCreate` - создание сессии анализа - `SessionResponse` - полная сессия - `SessionListItem` - элемент списка сессий - `SessionList` - список с total **query.py:** - `QuestionRequest` - body + with_docs - `BenchQueryRequest` - environment + questions[] - `BackendQueryRequest` - environment + questions[] + reset_session - `QueryResponse` - request_id, timestamp, environment, response ### 3. Interfaces (app/interfaces/) **base.py (ЗАГЛУШКА!):** ```python class TgBackendInterface: def __init__(self, api_prefix: str, **kwargs) async def get(path, params, response_model) async def post(path, body, response_model) async def put(path, body, response_model) async def delete(path) ``` **Требует реализации пользователем!** Должна включать: - httpx.AsyncClient для HTTP запросов - Автоматическую сериализацию/десериализацию Pydantic моделей - Error handling и retry logic - Логирование **db_api_client.py:** Наследуется от TgBackendInterface, методы: - `login_user(LoginRequest) -> UserResponse` - `get_user_settings(user_id) -> UserSettings` - `update_user_settings(user_id, settings) -> UserSettings` - `save_session(user_id, session_data) -> SessionResponse` - `get_sessions(user_id, environment, limit, offset) -> SessionList` - `get_session(user_id, session_id) -> SessionResponse` - `delete_session(user_id, session_id) -> dict` ### 4. Services (app/services/) **auth_service.py:** - `AuthService.login(login, client_ip)` - авторизация через DB API + генерация JWT ### 5. Security & Auth (app/utils/security.py) - `create_access_token(data, expires_delta)` - создание JWT - `decode_access_token(token)` - валидация JWT ### 6. Dependencies (app/dependencies.py) - `get_db_client()` - DI для DBApiClient - `get_current_user(credentials)` - middleware для auth ### 7. API Endpoints (app/api/v1/) **auth.py:** - `POST /api/v1/auth/login?login=12345678` - авторизация - Возвращает JWT token + user info - Фиксирует IP клиента ### 8. Main App (app/main.py) - FastAPI app с CORS - Include router для auth - Health endpoint: GET /health - Root endpoint: GET / ### 9. Docker (Dockerfile, docker-compose.yml) - Multi-stage build - Порт 8000 - Volumes: certs/ (ro), static/ - Network: brief-bench-network ### 10. Documentation - **DB_API_CONTRACT.md** - полный контракт для DB API сервиса - **README.md** - инструкции по запуску и разработке - **.env.example** - пример конфигурации --- ## Что НЕ реализовано (TODO) ### 1. TgBackendInterface реализация (КРИТИЧНО!) Файл: `app/interfaces/base.py` Нужно реализовать: ```python class TgBackendInterface: def __init__(self, api_prefix: str, **kwargs): self.api_prefix = api_prefix self.client = httpx.AsyncClient( timeout=kwargs.get('timeout', 30), # ... другие настройки ) async def get(self, path, params=None, response_model=None, **kwargs): url = f"{self.api_prefix}{path}" response = await self.client.get(url, params=params) response.raise_for_status() data = response.json() if response_model: return response_model(**data) return data # аналогично post, put, delete ``` ### 2. API Endpoints для Settings Файл: `app/api/v1/settings.py` (создать!) ```python @router.get("/settings") async def get_settings(user: dict = Depends(get_current_user)): # Получить настройки пользователя из DB API @router.put("/settings") async def update_settings(settings: UserSettingsUpdate, user: dict = Depends(get_current_user)): # Обновить настройки через DB API ``` ### 3. API Endpoints для Query Файл: `app/api/v1/query.py` (создать!) ```python @router.post("/query/bench") async def bench_query(request: BenchQueryRequest, user: dict = Depends(get_current_user)): # Отправить batch запрос к RAG backend через RagService @router.post("/query/backend") async def backend_query(request: BackendQueryRequest, user: dict = Depends(get_current_user)): # Отправить вопросы по одному через RagService ``` ### 4. API Endpoints для Analysis Sessions Файл: `app/api/v1/analysis.py` (создать!) ```python @router.post("/analysis/sessions") async def create_session(session: SessionCreate, user: dict = Depends(get_current_user)): # Сохранить сессию через DB API @router.get("/analysis/sessions") async def get_sessions(environment: str = None, user: dict = Depends(get_current_user)): # Получить список сессий @router.get("/analysis/sessions/{session_id}") async def get_session(session_id: str, user: dict = Depends(get_current_user)): # Получить конкретную сессию @router.delete("/analysis/sessions/{session_id}") async def delete_session(session_id: str, user: dict = Depends(get_current_user)): # Удалить сессию ``` ### 5. RAG Service Файл: `app/services/rag_service.py` (создать!) ```python class RagService: def __init__(self): # Создать 3 httpx.AsyncClient для IFT, PSI, PROD # Настроить mTLS из config async def send_bench_query(self, environment: str, questions: list, user_settings: dict): # Отправить batch запрос к RAG backend # Headers: Request-Id, System-Id, Bearer token (из user_settings) async def send_backend_query(self, environment: str, questions: list, user_settings: dict): # Отправить вопросы по одному # После каждого вопроса: reset session если resetSessionMode=true ``` ### 6. Services для Settings и Analysis Файлы: - `app/services/settings_service.py` (создать!) - `app/services/analysis_service.py` (создать!) ### 7. Frontend Integration - Скопировать `index.html`, `app.js`, `styles.css` из rag-bench в `static/` - Создать `static/api-client.js` для работы с FastAPI API - Добавить login screen в index.html - Обновить app.js для использования api-client.js ### 8. Middleware (опционально) - `app/middleware/logging.py` - логирование запросов - `app/middleware/error_handler.py` - глобальная обработка ошибок ### 9. Tests COMPLETED - **Unit Tests** (119 tests, 99% coverage) - `tests/unit/` - All services, models, utilities tested in isolation - All external dependencies mocked - Run: `.\run_unit_tests.bat` - **Integration Tests** (DB API integration) - `tests/integration/` - FastAPI endpoints with real DB API - Requires DB API service running - Run: `.\run_integration_tests.bat` - **End-to-End Tests** (Full stack) - `tests/e2e/` - Complete workflows: auth → query → save → retrieve - Requires all services (FastAPI + DB API + RAG backends) - Real network calls to RAG backends - Run: `.\run_e2e_tests.bat` - **Test Documentation** - `TESTING.md` - Comprehensive testing guide - Setup instructions for each test level - Troubleshooting and best practices --- ## Важные детали для продолжения ### Архитектура авторизации 1. Пользователь отправляет POST /api/v1/auth/login?login=12345678 2. FastAPI вызывает DB API: POST /users/login 3. DB API возвращает UserResponse (user_id, login, ...) 4. FastAPI генерирует JWT token с {user_id, login, exp} 5. Возвращает {access_token, user} 6. Клиент сохраняет token в localStorage 7. Все последующие запросы: Authorization: Bearer {token} 8. Middleware get_current_user проверяет token ### Настройки пользователя - **В .env** (не редактируются из UI): хосты RAG, порты, endpoint'ы, пути к сертификатам - **В БД** (индивидуальны для каждого пользователя): bearerToken, systemPlatform, platformUserId, withClassify, resetSessionMode - Каждый пользователь имеет свои настройки для 3 окружений (IFT, PSI, PROD) ### RAG Backend Integration **Bench mode:** ```python POST https://{IFT_RAG_HOST}:{IFT_RAG_PORT}/{IFT_RAG_ENDPOINT} Headers: Content-Type: application/json Request-Id: {uuid} System-Id: brief-bench-ift Authorization: Bearer {user_settings.bearerToken} # если задан System-Platform: {user_settings.systemPlatform} # если задан Body: [ {"body": "вопрос", "with_docs": true}, ... ] ``` **Backend mode:** ```python # Для каждого вопроса: POST https://{host}:{port}/{backendAskEndpoint} Headers: Platform-User-Id: {user_settings.platformUserId} Platform-Id: {user_settings.platformId} Authorization: Bearer {user_settings.bearerToken} # если задан Body: { "question": "вопрос", "user_message_id": 1, "user_message_datetime": "2025-12-17T12:00:00Z", "with_classify": false } # Если resetSessionMode=true: POST https://{host}:{port}/{backendResetEndpoint} Body: { "user_message_datetime": "2025-12-17T12:00:00Z" } ``` ### DB API Endpoints (см. DB_API_CONTRACT.md) - POST /users/login - GET /users/{user_id}/settings - PUT /users/{user_id}/settings - POST /users/{user_id}/sessions - GET /users/{user_id}/sessions - GET /users/{user_id}/sessions/{session_id} - DELETE /users/{user_id}/sessions/{session_id} --- ## План дальнейшей работы ### Этап 1: Реализовать TgBackendInterface **Приоритет:** ВЫСОКИЙ **Файл:** app/interfaces/base.py Без этого DB API клиент не будет работать. ### Этап 2: Добавить недостающие API endpoints **Приоритет:** ВЫСОКИЙ **Файлы:** - app/api/v1/settings.py - app/api/v1/query.py - app/api/v1/analysis.py Зарегистрировать в app/main.py: ```python from app.api.v1 import auth, settings, query, analysis app.include_router(settings.router, prefix="/api/v1") app.include_router(query.router, prefix="/api/v1") app.include_router(analysis.router, prefix="/api/v1") ``` ### Этап 3: Реализовать RAG Service **Приоритет:** ВЫСОКИЙ **Файл:** app/services/rag_service.py Нужно для query endpoints. ### Этап 4: Реализовать Settings & Analysis Services **Приоритет:** СРЕДНИЙ **Файлы:** - app/services/settings_service.py - app/services/analysis_service.py ### Этап 5: Frontend Integration **Приоритет:** СРЕДНИЙ - Скопировать static/ файлы из rag-bench - Создать api-client.js - Добавить login screen - Обновить app.js ### Этап 6: Testing & Deployment **Приоритет:** НИЗКИЙ - Создать .env из .env.example - Добавить mTLS сертификаты в certs/ - docker-compose up - Тестирование --- ## Dependencies (requirements.txt) ``` fastapi==0.104.1 uvicorn[standard]==0.24.0 python-multipart==0.0.6 httpx==0.25.2 pydantic==2.5.0 pydantic-settings==2.1.0 python-jose[cryptography]==3.3.0 passlib[bcrypt]==1.7.4 anyio==4.1.0 python-dotenv==1.0.0 fastapi-cors==0.0.6 ``` --- ## Команды для разработки ```bash # Установить зависимости pip install -r requirements.txt # Запустить локально uvicorn app.main:app --reload --host 0.0.0.0 --port 8000 # Docker docker-compose up -d docker-compose logs -f fastapi docker-compose down # Проверить здоровье curl http://localhost:8000/health ``` --- ## Примечания 1. **TgBackendInterface** - это ваша реализация, которая будет использоваться во всех клиентах (DBApiClient, возможно RagClient в будущем) 2. **api_prefix** - каждый клиент инициализируется с базовым URL (например, http://db-api:8080/api/v1) 3. **Pydantic схемы** - используются везде для type-safety и валидации 4. **JWT токены** - 30-дневная экспирация, содержат user_id и login 5. **mTLS** - настраивается в .env, пути к сертификатам для каждого окружения 6. **CORS** - сейчас allow_origins=["*"], нужно настроить для production 7. **Ошибки** - возвращаются в формате FastAPI HTTPException с detail --- ## Готово к продолжению! Вся базовая структура создана. Следующий шаг - реализация TgBackendInterface и остальных endpoints. **Следующий чат:** начните с реализации TgBackendInterface или создания недостающих API endpoints.