feat: index semantic records in qdrant
This commit is contained in:
@@ -2,9 +2,15 @@ from pathlib import Path
|
||||
|
||||
import typer
|
||||
|
||||
from tht.cli._guards import has_vector_write_rest, require_server_profile, require_vector_write_allowed
|
||||
from tht.cli._guards import (
|
||||
has_vector_write_rest,
|
||||
require_server_profile,
|
||||
require_vector_write_allowed,
|
||||
)
|
||||
from tht.cli.config_cmd import CONFIG_OPT
|
||||
from tht.cli.schema_cmd import _load_config_or_exit, annotations_path, physical_path
|
||||
from tht.ports.vector import VectorWriteRecord
|
||||
from tht.vectorstore.store import SyncStats, content_hash
|
||||
|
||||
vector_app = typer.Typer(help="Indice semantico pgvector (derivato, rigenerabile)")
|
||||
|
||||
@@ -69,6 +75,31 @@ def open_searcher(cfg):
|
||||
return AdapterSearcher()
|
||||
|
||||
|
||||
def sync_canonical_records(collection, records, *, store, embedder):
|
||||
kinds = sorted({record.kind for record in records})
|
||||
existing = store.existing_hashes(collection, kinds)
|
||||
pending = []
|
||||
stats = SyncStats()
|
||||
changed = []
|
||||
for record in records:
|
||||
hashed = content_hash(record.content)
|
||||
current = existing.get(record.id)
|
||||
if current == hashed:
|
||||
stats.unchanged += 1
|
||||
continue
|
||||
changed.append((record, hashed, current is None))
|
||||
if changed:
|
||||
embeddings = embedder.embed_documents([record.content for record, *_ in changed])
|
||||
for (record, hashed, is_added), embedding in zip(changed, embeddings, strict=True):
|
||||
pending.append(VectorWriteRecord(record=record, embedding=embedding, content_hash=hashed))
|
||||
if is_added:
|
||||
stats.added += 1
|
||||
else:
|
||||
stats.updated += 1
|
||||
store.upsert(collection, pending)
|
||||
return stats
|
||||
|
||||
|
||||
def _print_stats(stats) -> None:
|
||||
typer.secho(
|
||||
f"OK: {stats.added} nuovi, {stats.updated} aggiornati, "
|
||||
@@ -88,7 +119,6 @@ def init_cmd(
|
||||
from sqlalchemy.exc import OperationalError
|
||||
|
||||
from tht.vectorstore.embeddings import EmbeddingsError
|
||||
|
||||
from tht.vectorstore.reader import ALL_TABLES
|
||||
|
||||
cfg = _load_config_or_exit(config)
|
||||
@@ -131,8 +161,12 @@ def index_schema_cmd(config: Path = CONFIG_OPT) -> None:
|
||||
physical = PhysicalSchema.from_yaml(phys_file)
|
||||
annotations = Annotations.from_yaml(annotations_path(cfg))
|
||||
records = schema_records(physical, annotations)
|
||||
store = open_store(cfg, "schema_records")
|
||||
stats = store.sync(
|
||||
records, make_embedder(cfg.embeddings), kinds={"schema_table", "schema_column"}
|
||||
from tht.adapters.factory import build_vector_store
|
||||
|
||||
stats = sync_canonical_records(
|
||||
"schema_records",
|
||||
records,
|
||||
store=build_vector_store(cfg, require_write=True),
|
||||
embedder=make_embedder(cfg.embeddings),
|
||||
)
|
||||
_print_stats(stats)
|
||||
|
||||
Reference in New Issue
Block a user