-- Migration 002 (doza) — busca híbrida e leitura cirúrgica no schema `doza`. -- -- É a mesma mudança já aplicada ao schema `tigre` (migrations 002 e 003), -- reunida num arquivo só porque aqui as duas vão juntas desde o início. -- -- Motivo, medido no índice legado (694 trechos / 93 arquivos): -- O índice ivfflat com lists=100 sobre 694 linhas dá ~7 linhas por lista. -- Com o padrão ivfflat.probes=1 a busca varre quase nada, e o resultado é -- ruído: procurar `SpineSegment` devolvia requirements.txt e CLA.md, -- enquanto a busca exata põe doza_assist/fcpxml/parser.py em 1º. -- recall@5 do conjunto dourado (rag/bench_doza.sh): 0%. Zero de 18. -- -- Idempotente: seguro rodar mais de uma vez. -- -- COMO RODAR (precisa ser rag_admin — o rag_doza_indexer não tem DDL): -- rag/migrate_doza.sh -- -- DEPOIS DE RODAR: reindexar do zero é obrigatório. -- rag/index_doza.sh --full -- Os embeddings passam a usar os prefixos do nomic-embed-text; vetores -- antigos e novos não são comparáveis entre si. BEGIN; -- 1. Índice vetorial: ivfflat -> HNSW --------------------------------- DROP INDEX IF EXISTS doza.code_chunks_embedding_idx; CREATE INDEX IF NOT EXISTS code_chunks_embedding_hnsw_idx ON doza.code_chunks USING hnsw (embedding vector_cosine_ops) WITH (m = 16, ef_construction = 64); -- 2. Metadados de trecho ---------------------------------------------- ALTER TABLE doza.code_chunks ADD COLUMN IF NOT EXISTS start_line int; ALTER TABLE doza.code_chunks ADD COLUMN IF NOT EXISTS end_line int; ALTER TABLE doza.code_chunks ADD COLUMN IF NOT EXISTS symbols text; ALTER TABLE doza.code_chunks ADD COLUMN IF NOT EXISTS module text; ALTER TABLE doza.code_chunks ADD COLUMN IF NOT EXISTS kind text; ALTER TABLE doza.code_chunks ADD COLUMN IF NOT EXISTS file_mtime double precision; -- 3. Índices lexicos (pg_trgm) — o lado keyword da busca híbrida ------- CREATE INDEX IF NOT EXISTS code_chunks_file_path_trgm_idx ON doza.code_chunks USING gin (file_path gin_trgm_ops); CREATE INDEX IF NOT EXISTS code_chunks_symbols_trgm_idx ON doza.code_chunks USING gin (symbols gin_trgm_ops); CREATE INDEX IF NOT EXISTS code_chunks_module_idx ON doza.code_chunks (module); CREATE INDEX IF NOT EXISTS idx_code_chunks_file_path ON doza.code_chunks (file_path); -- 4. Mapa de arquivos, com embedding do resumo ------------------------ CREATE TABLE IF NOT EXISTS doza.file_index ( file_path text PRIMARY KEY, module text, main_type text, public_symbols text[], summary text, n_lines int, content_hash text, summary_embedding vector(768), updated_at timestamp DEFAULT now() ); CREATE INDEX IF NOT EXISTS file_index_module_idx ON doza.file_index (module); CREATE INDEX IF NOT EXISTS file_index_path_trgm_idx ON doza.file_index USING gin (file_path gin_trgm_ops); CREATE INDEX IF NOT EXISTS file_index_summary_hnsw_idx ON doza.file_index USING hnsw (summary_embedding vector_cosine_ops) WITH (m = 16, ef_construction = 64); -- 5. Permissões do usuário de indexação/busca ------------------------- GRANT SELECT, INSERT, UPDATE, DELETE ON doza.file_index TO rag_doza_indexer; GRANT USAGE, SELECT ON ALL SEQUENCES IN SCHEMA doza TO rag_doza_indexer; COMMIT;