10 KiB
10 KiB
📤 API загрузки файлов с квотами - Точная документация
Обзор
Quoter предоставляет API для загрузки файлов с системой квот и автоматической обработкой различных типов медиа.
Базовый URL
http://localhost:8080
Аутентификация
Все эндпоинты загрузки требуют JWT токен в заголовке:
Authorization: Bearer <jwt-token>
📤 Загрузка файлов (УЛУЧШЕННАЯ ВЕРСИЯ)
POST /
Загружает файл(ы) в S3-совместимое хранилище (Storj) с улучшенной проверкой квот и валидацией.
Заголовки запроса
Authorization: Bearer <jwt-token>
Content-Type: multipart/form-data
Параметры
- file (required) - файл(ы) для загрузки в multipart/form-data
Поддерживаемые форматы
Автоматическое определение MIME-типа из содержимого файла:
- Изображения: JPEG, PNG, GIF, WebP, HEIC
- Видео: MP4, WebM, AVI
- Аудио: MP3, WAV, OGG
- Документы: PDF
🔄 Улучшенная логика обработки
- Проверка авторизации - извлечение и валидация JWT токена
- Получение текущей квоты пользователя из Redis
- Предварительная проверка квоты - пользователь не достиг лимита
- Streaming чтение файла с проверками на каждом chunk:
- Проверка лимита одного файла (500 МБ)
- Проверка общей квоты пользователя
- Пропуск пустых файлов
- Определение MIME-типа из содержимого (не из расширения!)
- Генерация UUID имени файла с правильным расширением
- Загрузка в Storj S3
- Обновление квоты пользователя
- Сохранение метаданных в Redis (с обработкой ошибок)
Ограничения
- Максимальная квота на пользователя: 5 ГБ (5,368,709,120 байт)
- Максимальный размер одного файла: 500 МБ (524,288,000 байт)
- Проверка квоты происходит во время чтения (streaming)
- Поддержка множественных файлов в одном запросе
Успешные ответы
Один файл:
HTTP/1.1 200 OK
Content-Type: text/plain
uuid-filename.ext
Несколько файлов:
HTTP/1.1 200 OK
Content-Type: application/json
{
"uploaded_files": ["uuid1.jpg", "uuid2.png"],
"count": 2
}
Коды ошибок (ИСПРАВЛЕННЫЕ)
| Код | Условие | Описание |
|---|---|---|
| 400 Bad Request | Нет файлов | "No files provided or all files were empty" |
| 401 Unauthorized | Отсутствует токен | "Authorization token required" |
| 401 Unauthorized | Неверный токен | "Invalid authorization token" |
| 413 Payload Too Large | 🎯 Превышена квота | "Author quota limit exceeded" |
| 413 Payload Too Large | 🎯 Большой файл | "Single file size limit exceeded" |
| 413 Payload Too Large | 🎯 Превышение при загрузке | "Author quota limit would be exceeded" |
| 415 Unsupported Media Type | Неподдерживаемый MIME | "Unsupported file format" |
| 415 Unsupported Media Type | Нет расширения для MIME | "Unsupported content type" |
| 500 Internal Server Error | Ошибка S3 | "File upload failed" |
| 500 Internal Server Error | Ошибка квоты | "Failed to update user quota" |
✅ Исправленные проблемы
- Правильный код ошибки для квоты: 413 Payload Too Large
- Efficient memory usage: streaming с проверками на каждом chunk
- Предварительная проверка квоты перед началом загрузки
- Лимит размера одного файла: 500 МБ
- Улучшенная обработка ошибок с детальными сообщениями
- Поддержка множественных файлов в одном запросе
- Детальное логирование с процентом использования квоты
🔄 Как это работает
- JWT декодирование - извлекается
user_idиз токена - Redis lookup - опциональный поиск сессии по ключу
session:{user_id}:{token} - Quota lookup - получение квоты по ключу
quota:{user_id}из Redis - Activity update - обновление
last_activitytimestamp (если сессия найдена) - Response building - объединение данных пользователя и квоты
Заголовки запроса
Authorization: Bearer <jwt-token>
Успешный ответ
HTTP/1.1 200 OK
Content-Type: application/json
{
"user_id": "user_12345",
"username": "john_doe",
"token_type": "session",
"created_at": "1642248600",
"last_activity": "1642335000",
"auth_data": "{\"roles\": [\"user\"], \"permissions\": [...]}",
"device_info": "{\"platform\": \"web\", \"browser\": \"Chrome\"}",
"quota": {
"current_quota": 1073741824,
"max_quota": 5368709120,
"usage_percentage": 20.0
}
}
Поля ответа
| Поле | Тип | Описание |
|---|---|---|
user_id |
string | Уникальный ID пользователя |
username |
string | null | Имя пользователя |
token_type |
string | null | Тип токена (обычно "session") |
created_at |
string | null | Unix timestamp создания сессии |
last_activity |
string | null | Unix timestamp последней активности |
auth_data |
string | null | JSON-строка с данными авторизации |
device_info |
string | null | JSON-строка с информацией об устройстве |
quota.current_quota |
number | Текущее использование квоты в байтах |
quota.max_quota |
number | Максимальная квота в байтах |
quota.usage_percentage |
number | Процент использования квоты |
Коды ошибок
| Код | Условие | Описание |
|---|---|---|
| 401 Unauthorized | Отсутствует токен | "Authorization token required" |
| 401 Unauthorized | Неверный JWT | "Invalid or expired session token" |
| 401 Unauthorized | Сессия не найдена | "Session not found or expired" |
Примеры использования
# Получение информации о текущем пользователе
curl -H "Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGc..." \
http://localhost:8080/
📊 Управление квотами
GET /quota
Получает информацию о квоте пользователя.
Параметры запроса
GET /quota?user_id=<user_id>
Ответ
{
"user_id": "user123",
"current_quota": 1073741824,
"max_quota": 5368709120
}
POST /quota/increase
Увеличивает квоту пользователя (admin-only).
Тело запроса
{
"user_id": "user123",
"additional_bytes": 1073741824
}
Валидация
additional_bytesдолжно быть > 0- Требуется админский токен
POST /quota/set
Устанавливает абсолютное значение квоты (admin-only).
Тело запроса
{
"user_id": "user123",
"new_quota_bytes": 2147483648
}
🔍 Получение файлов
GET /{filename}
Возвращает файл по имени с возможными трансформациями.
Параметры URL
filename- имя файла или имя_размер.расширение для миниатюр
Query параметры
s=<shout_id>- добавляет оверлей с данными shout (только изображения)
Примеры
GET /uuid-file.jpg # Оригинальный файл
GET /uuid-file_300.jpg # Миниатюра 300px
GET /uuid-file_300.jpg/webp # Миниатюра в WebP
GET /uuid-file.jpg?s=123 # С оверлеем shout
🧪 Примеры использования
Загрузка файла
curl -X POST http://localhost:8080/ \
-H "Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGc..." \
-F "file=@photo.jpg"
Ответ при успехе:
c4ca4238-a0b9-23f1-8429-81dc9bdb9a1f.jpg
Ответ при превышении квоты:
HTTP/1.1 401 Unauthorized
Quota exceeded
Проверка квоты
curl "http://localhost:8080/quota?user_id=user123" \
-H "Authorization: Bearer admin-token"
Увеличение квоты (admin)
curl -X POST http://localhost:8080/quota/increase \
-H "Authorization: Bearer admin-token" \
-H "Content-Type: application/json" \
-d '{"user_id": "user123", "additional_bytes": 1073741824}'
🔧 Рекомендации по улучшению
- Исправить код ошибки квоты: 401 → 413
- Добавить предварительную проверку размера из Content-Length
- Streaming загрузка вместо полного чтения в память
- Лимит размера одного файла
- Детальная валидация MIME-типов
- Метрики использования квот
Документация актуальна для версии кода на момент создания. Для изменений см. CHANGELOG.md.