Files
wiki_embedding/README.md
Тимур Абайдулин 84b8246562 Init
2026-03-10 16:33:39 +03:00

4.7 KiB
Raw Permalink Blame History

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. Установить зависимости

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. Сохранить браузерную сессию (один раз)

python wiki_auth.py

Откроется браузер — залогинься в wiki.yandex.ru, нажми Enter.

Запуск

Полная синхронизация

python wiki_sync.py

Обходит все 642 slug-а из ROOT_SLUGS, обновляет wiki_pages, генерирует embeddings.

Обнаружить новые страницы через Playwright

python wiki_tree_crawler.py

Открывает страницы с {% tree %} в headless-браузере, находит дочерние slug-и которых нет в базе.

Проверить покрытие

python wiki_check_slugs.py

Показывает какие {% tree %} страницы не покрыты ROOT_SLUGS.

Семантический поиск (из кода)

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 векторов даёт плохие результаты).

Схема БД

-- Содержимое страниц
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))