# wiki_embedding Семантический поиск по страницам Яндекс Вики через pgvector + OpenAI embeddings. ## Что делает - Обходит раздел «Управление Аналитики» Яндекс Вики через API и Playwright - Сохраняет содержимое страниц в Supabase (PostgreSQL) - Генерирует векторные embeddings через OpenAI `text-embedding-3-small` - Позволяет делать семантический поиск по ~700 страницам на русском и английском ## Стек | Компонент | Технология | |-----------|-----------| | Хранилище | Supabase (PostgreSQL 17) | | Векторный поиск | pgvector, cosine similarity (`<=>`) | | Embeddings | OpenAI `text-embedding-3-small` (1536 dims) | | Wiki API | Яндекс Вики API v1 (`api.wiki.yandex.net/v1`) | | Браузерный краулер | Playwright + Chromium headless | | Язык | Python 3.12 | ## Структура файлов ``` wiki_embedding/ ├── wiki_sync.py # Главный скрипт синхронизации (API → Supabase → embeddings) ├── wiki_embeddings.py # Генерация embeddings и семантический поиск ├── yandex_wiki.py # Краулер через Яндекс Вики API v1 ├── wiki_tree_crawler.py # Playwright-краулер для страниц с {% tree %} ├── wiki_check_slugs.py # Проверка покрытия ROOT_SLUGS ├── wiki_auth.py # Сохранение браузерной сессии для Playwright ├── supabase.py # SupabaseManager — подключение и операции с БД ├── requirements.txt # Зависимости └── .env # Credentials (не коммитить) ``` ## Настройка ### 1. Установить зависимости ```bash pip install -r requirements.txt playwright install chromium ``` ### 2. Создать .env ``` # Яндекс OAuth-токен (работает для Трекера и Вики) YT=y0_... ORG_ID=7405124 # Supabase SUPABASE_HOST=aws-1-eu-north-1.pooler.supabase.com SUPABASE_PORT=5432 SUPABASE_USER=postgres.xeakxxnriopsmaxdioke SUPABASE_PASSWORD=... SUPABASE_DB=postgres # OpenAI OPENAI_API_KEY=sk-... ``` ### 3. Сохранить браузерную сессию (один раз) ```bash python wiki_auth.py ``` Откроется браузер — залогинься в wiki.yandex.ru, нажми Enter. ## Запуск ### Полная синхронизация ```bash python wiki_sync.py ``` Обходит все 642 slug-а из `ROOT_SLUGS`, обновляет `wiki_pages`, генерирует embeddings. ### Обнаружить новые страницы через Playwright ```bash python wiki_tree_crawler.py ``` Открывает страницы с `{% tree %}` в headless-браузере, находит дочерние slug-и которых нет в базе. ### Проверить покрытие ```bash python wiki_check_slugs.py ``` Показывает какие `{% tree %}` страницы не покрыты ROOT_SLUGS. ### Семантический поиск (из кода) ```python import sys sys.path.insert(0, '/Users/at/code/wiki_embedding') from supabase import SupabaseManager from wiki_embeddings import search db = SupabaseManager() db.connect() results = search(db, 'твой запрос', limit=5) for r in results: print(r['similarity'], r['title']) print(r['content_text'][:500]) db.close() ``` Similarity > 0.5 — хорошее совпадение. ## Cron (ежедневная синхронизация) ``` 0 3 * * * cd /Users/at/code/wiki_embedding && /usr/bin/python3 wiki_sync.py >> logs/wiki_sync.log 2>&1 ``` ## Как устроен поиск 1. При индексировании каждая страница → вектор через OpenAI (title + content) 2. При поиске запрос → вектор тем же способом 3. pgvector находит страницы с минимальным косинусным расстоянием (`<=>`) 4. Возвращается `1 - distance` как similarity (0..1) Точный поиск без индекса (IVFFlat не используется — при < 10k векторов даёт плохие результаты). ## Схема БД ```sql -- Содержимое страниц wiki_pages (id, slug, title, page_type, modified_at, content_hash, value JSONB) -- Векторные embeddings wiki_embeddings (id, slug, title, content_text, content_hash, embedding vector(1536)) ```