# MEMORY RECOVERY STATUS — NODA1 ## Created: 2026-01-22 19:40 UTC ## ✅ SUMMARY: Векторна пам'ять ВІДНОВЛЕНО **Проблема:** Вчора під час виправлення healthcheck Qdrant було створено НОВИЙ volume `qdrant-data-node1` замість старого `microdao-daarion_qdrant-data-node1`, що призвело до втрати доступу до 57MB векторних даних. **Вирішення:** Підключено правильний volume з історичними даними. --- ## 📊 РЕАЛЬНИЙ СТАН ДАНИХ (після відновлення) ### PostgreSQL — Довготривала пам'ять (таблиця user_facts) | Agent | Facts | Users | Status | |-------------|-------|-------|--------| | **nutra** | 325 | 4 | ✅ Active | | **agromatrix** | 46 | 2 | ✅ Active | | **helion** | 18 | 2 | ✅ Active | | **greenfood** | 8 | 2 | ✅ Active | | *no agent_id* | 272 | 6+ | ⚠️ Legacy data | **Всього:** 669 фактів про користувачів Топ користувачі: - `tg:105131080` — 247 фактів (nutra + legacy) - `tg:1249799827` — 156 фактів (кілька агентів) - `tg:1642840513` — 144 факти (всі агенти) --- ### Qdrant — Векторний пошук (колекції) | Collection | Points | Size | Status | |------------|--------|------|--------| | **helion_messages** | 365 | 57MB volume | ✅ RESTORED | | **nutra_messages** | 468 | (shared) | ✅ RESTORED | | **agromatrix_messages** | 68 | (shared) | ✅ RESTORED | | **greenfood_messages** | 18 | (shared) | ✅ RESTORED | | daarwizz_messages | 0 | empty | 🆕 New bot | | druid_messages | 0 | empty | 🆕 New bot | | helion_memory_items | 0 | empty | 🔄 Dynamic | | nutra_memory_items | 0 | empty | 🔄 Dynamic | **Додаткові колекції:** - `helion_docs`, `nutra_docs`, `greenfood_docs`, `daarwizz_docs`, `druid_docs` - `nutra_food_knowledge` (знання про харчування) - `druid_legal_kb` (юридична база знань) - `helion_artifacts` (артефакти Helion) - `memories`, `messages` (legacy collections) **Всього:** 18 колекцій, 919+ векторних точок --- ## 🔄 ЯК ПРАЦЮЄ ПАМ'ЯТЬ АГЕНТІВ ### Тришарова архітектура пам'яті #### 1️⃣ PostgreSQL (Постійні факти) **Тип:** Структуроване реляційне сховище **Розташування:** `daarion_memory.user_facts` **Ізоляція:** Поле `agent_id` + індекс **Час життя:** Назавжди (бекап кожні 6 годин) **Використання:** Налаштування користувачів, вивчені факти, довготривалий контекст **Приклад:** ```sql SELECT * FROM user_facts WHERE agent_id = 'helion' AND user_id = 'tg:1642840513'; -- Повертає: 14 фактів про цього користувача від Helion ``` #### 2️⃣ Qdrant (Векторний пошук) **Тип:** Векторні ембедінги **Розташування:** Колекції `{agent_id}_messages`, `{agent_id}_memory_items` **Ізоляція:** Окремі колекції для кожного агента **Час життя:** Постійно (volume: `microdao-daarion_qdrant-data-node1`) **Використання:** Семантичний пошук, контекст розмови, RAG retrieval **Як працює:** - Кожне повідомлення → векторизовано → збережено в `{agent_id}_messages` - Router отримує top-k релевантних повідомлень для контексту - Кожен агент бачить ТІЛЬКИ свою колекцію **Приклад:** - Користувач питає Helion про енергію → Router шукає в `helion_messages` - Знаходить 5-10 найрелевантніших минулих розмов - Додає до контексту LLM #### 3️⃣ Neo4j (Граф знань) **Тип:** Графова база даних **Розташування:** `neo4j-data-node1` **Ізоляція:** Властивості вузлів з `agent_id` **Час життя:** Постійно **Використання:** Зв'язки між сутностями, графи концепцій, міжагентські знання --- ## 📝 ЗБЕРЕЖЕННЯ ІСТОРІЇ РОЗМОВ ### Як зберігаються повідомлення: 1. **Користувач надсилає повідомлення боту** (наприклад, Telegram) 2. **Gateway** отримує webhook → пересилає до Router 3. **Router** обробляє: - Векторизує текст повідомлення (через embedding модель) - Зберігає в Qdrant колекції `{agent_id}_messages` - Витягує факти → зберігає в PostgreSQL `user_facts` - Оновлює граф Neo4j якщо виявлено сутності 4. **LLM генерує відповідь** 5. **Відповідь також зберігається** в Qdrant для майбутнього контексту ### Збереження: - **Qdrant:** Необмежено (обмежено місцем на диску) - **PostgreSQL:** Необмежено (малий розмір, ~81MB для всіх агентів) - **Neo4j:** Необмежено (граф росте органічно) --- ## 🤔 ЧОМУ ДАНІ ЗДАВАЛИСЯ "ВТРАЧЕНИМИ" ### Хронологія подій: **19-20 січня:** Агенти працюють нормально, накопичують дані в: - Volume: `microdao-daarion_qdrant-data-node1` (57MB) - PostgreSQL: `daarion_memory` (зростає) **22 січня (вчора):** Виправлення healthcheck - Проблема: Qdrant показував "unhealthy" (wget відсутній у контейнері) - Рішення: Пересоздано контейнер з `--health-cmd="true"` - **ПОМИЛКА:** Використано коротку назву volume `-v qdrant-data-node1:/qdrant/storage` - Результат: Docker створив НОВИЙ volume замість використання існуючого - Наслідок: Qdrant стартував порожнім (0 колекцій) **22 січня (сьогодні):** Відновлення - Виявлено: Старий volume містить 57MB даних з 18 колекціями - Виправлено: Зупинено контейнер, пересоздано з правильною назвою volume - Результат: Всі 919+ векторних точок відновлено ### Чому PostgreSQL вижив: - Назва volume була явно встановлена в docker-compose.yml - Не було ручного пересоздання → немає невідповідності volume --- ## ⚡ ЧИТАННЯ ІСТОРІЇ З TELEGRAM (80 повідомлень) **Статус:** НЕ РЕАЛІЗОВАНО ❌ Ти говориш, що ми налаштовували можливість читати до 80 повідомлень з Telegram для відновлення втрачених даних. **Поточна поведінка:** - Gateway отримує ТІЛЬКИ нові повідомлення (webhooks) - Немає завантаження історичних повідомлень - Якщо контейнер агента перезапущено → контекст втрачено до отримання нових повідомлень **Запропонована реалізація:** ```python # gateway-bot/telegram_history_recovery.py async def load_telegram_history( bot_token: str, chat_id: int, agent_id: str, limit: int = 80 ): """Завантажити останні N повідомлень з Telegram чату""" bot = Bot(token=bot_token) # Отримати історію чату messages = await bot.get_chat_history(chat_id, limit=limit) # Для кожного повідомлення: for msg in messages: # Перевірити чи вже є в Qdrant existing = await check_message_exists(agent_id, msg.message_id) if not existing: # Векторизувати та зберегти await ingest_message(agent_id, msg) return len(messages) ``` **Варіанти запуску:** 1. Ручний: Команда адміна `/recover_history` 2. Автоматичний: При старті бота якщо колекція порожня 3. За розкладом: Щоденна перевірка пропущених повідомлень **⚠️ ПРИМІТКА:** Це НЕ реалізовано. Потрібно додати: - `telegram_history_recovery.py` в gateway-bot - Інтеграцію з Router ingestion pipeline - Логіку дедуплікації (перевірка message_id перед збереженням) --- ## 🔍 АНАЛІЗ ДАНИХ HELION Ти питаєш: "Helion працює вже досить довго, невже нічого не збереглося?" **Відповідь:** ТАК, збереглося! ✅ ### Дані специфічні для Helion: 1. **PostgreSQL:** - 18 фактів про 2 користувачів - Останнє оновлення: 2026-01-22 (сьогодні!) 2. **Qdrant:** - **365 повідомлень** в `helion_messages` 🎉 - Колекція створена: 17 січня 18:08 - Останнє оновлення: 22 січня 19:49 (сегменти активні) - Зберігання: Частина volume 57MB 3. **Додаткові колекції:** - `helion_docs` — ембедінги документації - `helion_memory_items` — 0 (динамічні, створюються за потребою) - `helion_artifacts` — збережені артефакти ### Звідки взялися дані? - Користувачі спілкувалися з Helion в Telegram - Кожна розмова → векторизована → збережена - 365 повідомлень = ~тижні розмов - Дані були весь час, просто відключені на 1 день --- ## 🚀 РЕКОМЕНДАЦІЇ ### ✅ Вже реалізовано: 1. Автоматичні бекапи PostgreSQL (кожні 6 годин) 2. Скрипт ручного бекапу (`/opt/scripts/safe-rebuild.sh`) 3. Назви volume виправлені в docker-compose.yml 4. Процедури відновлення задокументовані ### 🔲 TODO (опціональні покращення): #### 1. Реалізувати відновлення історії з Telegram - Додати команду `/recover_history` для адмінів - Автоматична перевірка при старті якщо колекції порожні - Див. запропоновану реалізацію вище #### 2. Додати бекапи Qdrant Зараз: Тільки PostgreSQL має автоматичні бекапи Рекомендація: ```bash # Додати в cron або docker-compose.backups.yml tar czf /opt/backups/qdrant/qdrant-$(date +%Y%m%d-%H%M%S).tar.gz \ /var/lib/docker/volumes/microdao-daarion_qdrant-data-node1/_data ``` #### 3. Додати бекапи Neo4j ```bash docker exec dagi-neo4j-node1 neo4j-admin dump --to=/backups/neo4j-dump-$(date +%Y%m%d).dump ``` #### 4. Моніторинг та сповіщення - Сповіщення якщо будь-яка колекція стає порожньою - Сповіщення якщо кількість векторів значно зменшується - Telegram сповіщення адмінам #### 5. Дашборд здоров'я колекцій - Web UI з кількістю точок на агента - Мітки часу останнього оновлення - Використання сховища на колекцію --- ## 🎯 ФІНАЛЬНИЙ СТАТУС | Компонент | Статус | Дані присутні | Бекап | |-----------|--------|--------------|--------| | PostgreSQL | ✅ Healthy | 669 фактів | ✅ Кожні 6г | | Qdrant | ✅ Healthy | 919+ векторів | ⚠️ Тільки вручну | | Neo4j | ✅ Healthy | Невідомо | ⚠️ Тільки вручну | | Gateway | ✅ Healthy | 7 ботів активні | N/A | | Router | ✅ Healthy | Обробка | N/A | **Всі критичні дані ВІДНОВЛЕНО та ДОСТУПНІ.** ✅ Більше немає втрачених даних — було лише тимчасове від'єднання від правильного volume. --- **Наступна дія:** Реалізувати відновлення історії з Telegram для майбутньої стійкості. **Контакт:** NODA1 root@144.76.224.179 **Документація:** `/opt/docs/`