Failed to authenticate. API Error: 401 Invalid authentication credentials
[2026-05-16] vault sync
This commit is contained in:
@@ -156,4 +156,4 @@ updated: 2026-05-16
|
||||
|
||||
## 📅 Ближайшие даты
|
||||
|
||||
- **23 мая** — День рождения Лизы 🎂 (8 лет). Напоминание по крону 22 мая: набрать Happy Birthday на музыкальной шкатулке Lego
|
||||
- **23 мая** — День рождения Лизы 🎂 (7 лет). Напоминание по крону 22 мая: набрать Happy Birthday на музыкальной шкатулке Lego
|
||||
|
||||
@@ -460,6 +460,106 @@ docker run --rm \
|
||||
|
||||
---
|
||||
|
||||
## Архитектура: Agentic Flow (agent subcommand)
|
||||
|
||||
> Записано 2026-05-16. Это главная спека `media-pipeline agent` subcommand.
|
||||
|
||||
### Входные данные агента (для каждого unresolved item)
|
||||
|
||||
Агент получает **всё что можно извлечь без баз**:
|
||||
|
||||
1. **Файловые метаданные** — имя папки/файла, набор файлов в папке (для TV show), длительность, формат, битрейт, разрешение (через `ffprobe` или `AVFoundation`)
|
||||
2. **Транскрипция речи** — `ffmpeg` вырезает первые 60–120 сек аудио → **Whisper API** → текст (речь дикторов, диалоги, announcer voice)
|
||||
3. **OCR титров** — `ffmpeg` захватывает 5–10 кадров из начала → **tesseract** или Vision API → текст с title card, студия, год
|
||||
4. **Имена файлов** как уже есть (query names из UnresolvedEntry)
|
||||
|
||||
### Инструменты агента (function calling / tool use)
|
||||
|
||||
LLM получает инструменты и итеративно их вызывает до 10 шагов:
|
||||
|
||||
| Tool | Параметры | Описание |
|
||||
|------|-----------|----------|
|
||||
| `search_tmdb` | `title, year?, language?` | Поиск в TMDb API |
|
||||
| `search_kinopoisk` | `title, year?` | Поиск в KP API |
|
||||
| `search_imdb` | `title, year?` | IMDb full-text search |
|
||||
| `fetch_page` | `url` | Фетч и возврат текста страницы (IMDb, Wikipedia, BBC, Rutracker, etc.) |
|
||||
| `search_web` | `query` | Веб-поиск (DuckDuckGo / SerpAPI) |
|
||||
|
||||
### Выходные данные агента — одно из трёх
|
||||
|
||||
**Вариант A — DB-bound resolve** (нашёл в базе):
|
||||
```json
|
||||
{
|
||||
"tmdb_id": 12345,
|
||||
"kp_id": 678,
|
||||
"imdb_id": "tt1234567"
|
||||
}
|
||||
```
|
||||
→ Pipeline пишет NFO стандартно через TMDb/KP fetch
|
||||
|
||||
**Вариант B — full metadata без DB binding** (BBC/редкие доки):
|
||||
```json
|
||||
{
|
||||
"title": "The Frozen Kingdom of the Snow Leopard",
|
||||
"original_title": "...",
|
||||
"year": 2020,
|
||||
"description": "...",
|
||||
"genres": ["Documentary"],
|
||||
"poster_url": "https://...",
|
||||
"source_url": "https://bbc.com/programmes/...",
|
||||
"duration_min": 59
|
||||
}
|
||||
```
|
||||
→ Pipeline пишет custom NFO с этими данными (без tmdb/kp ID). Jellyfin подхватит.
|
||||
|
||||
**Вариант C — manual resolve**:
|
||||
```json
|
||||
{
|
||||
"category": "unrecognized",
|
||||
"reason": "Не удалось идентифицировать после всех источников"
|
||||
}
|
||||
```
|
||||
→ Остаётся в unresolved.json с agent_hint для ручного разбора
|
||||
|
||||
### Выход для TV show / папки с несколькими фильмами
|
||||
|
||||
Агент возвращает **список результатов**, по одному на файл/эпизод. Структура аналогична тому что делает media sync — те же поля что и NFO.
|
||||
|
||||
### Приоритет обработки
|
||||
|
||||
1. Сначала `The.Frozen.Kingdom.of.the.Snow.Leopard.(2020)` — самый сложный кейс, нет в TMDb/KP
|
||||
2. Остальные BBC/Soviet docs из unresolved.json
|
||||
3. Все остальные unresolved
|
||||
|
||||
### Реализация
|
||||
|
||||
#### Шаг 1: `MediaFileInspector` (новый модуль)
|
||||
- `ffprobe` / AVFoundation → duration, format, resolution, audio tracks
|
||||
- `ffmpeg` → extract frames → Vision/tesseract OCR → title card text
|
||||
- `ffmpeg` → extract 60s audio → Whisper API → speech transcript
|
||||
- Все результаты упакованы в `MediaFileContext` struct
|
||||
|
||||
#### Шаг 2: `ChatGPTAPI.resolveMedia(context: MediaFileContext)` (новый метод)
|
||||
- OpenAI function calling loop (max 10 iterations)
|
||||
- Системный промпт включает все данные из `MediaFileContext`
|
||||
- LLM итеративно вызывает tools пока не придёт к выводу
|
||||
- Возвращает `AgentResolutionResult` (A/B/C)
|
||||
|
||||
#### Шаг 3: `Agent.swift` subcommand расширен
|
||||
- Запускает `MediaFileInspector` для каждого unresolved item
|
||||
- Передаёт `MediaFileContext` в `resolveMedia`
|
||||
- По результату: пишет NFO (A/B) или обновляет hint (C)
|
||||
|
||||
#### Шаг 4: Tier 6 в sync pipeline (опционально)
|
||||
- После Tier 5 (AIAgentStrategy) — запускает VideoAnalysis для застрявших
|
||||
- Добавляет найденные variants как новые QueryNameFact → передаёт через Tier 0–4
|
||||
|
||||
### Зависимости (Linux/arm64 на Кракене)
|
||||
- `ffprobe` / `ffmpeg` — уже установлен на Кракене
|
||||
- `whisper-cpp` или OpenAI Whisper API (через ChatGPTAPI)
|
||||
- `tesseract` — нужно установить (`apt install tesseract-ocr tesseract-ocr-rus`)
|
||||
- Vision API (macOS only) — для Linux использовать tesseract
|
||||
|
||||
## План: CV/Whisper для Tier 6 (для оценки)
|
||||
|
||||
> Идея: когда все тиры исчерпаны — использовать сам медиафайл как источник сигнала для идентификации.
|
||||
|
||||
Reference in New Issue
Block a user