Skip to main content
cognee-rust is built on trait abstractions so each storage/compute backend can be swapped via configuration. Pick providers with the env vars / config keys in Configuration; the trait + adapter detail is in rustdoc (cargo doc -p <crate> --no-deps --open). Notes:
  • Embedded by default. A plain build runs entirely locally: LanceDB vector index (on disk), embedded Ladybug (graph), SQLite (relational), local file storage. The in-memory brute-force vector index is used on Android or with VECTOR_DB_URL=:memory:.
  • Feature gates. lancedb, pgvector, pggraph/postgres, onnx, ladybug, and the hf-tokenizer/tiktoken counters are cargo features, on by default in cognee/cognee-cli (as is bedrock) — see Architecture: feature strategy.
  • pgvector indexing. Each collection gets an HNSW index when it is created, over vector::halfvec(dim) with halfvec_cosine_ops and m = 24, ef_construction = 128 (tunable — see Configuration: pgvector index tuning), so similarity search is not a sequential scan. The column itself stays vector (the Python SDK’s schema): only candidate selection sees fp16, and scores are the full-precision distance, re-sorted. Each search raises hnsw.ef_search to cover its own top_k (an HNSW scan returns at most ef_search rows, default 40, and then stops — a larger LIMIT is otherwise silently unmet) and runs with hnsw.iterative_scan = relaxed_order, which keeps scanning until the LIMIT is met over dead tuples and tightly clustered vectors. Two pgvector version floors, both probed. The adapter reads pg_extension.extversion once when it connects. hnsw.iterative_scan needs pgvector 0.8+; below that the setting is simply not sent, so searches do not iterate but do not fail. halfvec needs 0.7.0+ (CREATE EXTENSION IF NOT EXISTS vector does not upgrade a database that already carries 0.5.x or 0.6.x); below it the adapter logs a warning and puts both the index and the search ordering back on full-precision vector / vector_cosine_ops (under the legacy <coll>_vector_hnsw name) — a larger index and slower scans, identical results. To move such a store onto the half-precision index, install a pgvector 0.7+ binary, run ALTER EXTENSION vector UPDATE, and then cognee-cli vector-reindex. Three exceptions, and in all three the candidate ordering drops back to full-precision vector and the scan is exact: collections wider than 2000 dimensions are not indexed; a top_k above 1000 exceeds the largest ef_search pgvector accepts; and a collection whose index is dropped for a bulk-load scope (see bulk loads below) is indexless until the scope ends. The 2000-dimension ceiling is this adapter’s choice, not pgvector’s limit (the half-precision index allows 4000): at 3072 dimensions an exact scan measured faster than the HNSW index on uniform random vectors, so text-embedding-3-large collections keep the exact scan for now. search_similar_filtered stays exact filter-then-limit, but no longer by disabling index scans: each collection carries a GIN index over cognee_vector_set_names(metadata) (a function with node_filter’s exact semantics), and the filter is && (OR) / @> (AND) against it, so the membership predicate is an index lookup while the ordering keeps the HNSW post-filtering scan out.
  • pgvector bulk loads. VectorDB::begin_bulk_load / end_bulk_load (a nestable, no-op-by-default hint that cognify wraps a pipeline run in) let the adapter stop maintaining an HNSW index row by row during a load: once the points written to a collection inside the scope reach 25% of its live row count its index is dropped, and it is built once — in parallel, under a sized maintenance_work_mem — when the last scope ends, followed by an ANALYZE of every collection written. Because the threshold counts live rows, an append load defers at about a third of the collection’s starting size and an all-overwrite load at a quarter; the live count is re-read only when the cached one cannot decide. A caller that splits one logical write into several index_points calls (cognify does, in ~16 MiB windows) calls VectorDB::announce_bulk_write first, so the first window is decided as one call of the whole write would have been; the hint lapses when the innermost scope ends and is a no-op by default. A collection without its index is still correct: a search of it runs with index scans off and orders by the full-precision distance, so it is an exact scan returning the true top k. An interrupted load (a crash, a process killed between begin and end) leaves every written row in place and searchable, and the one repair is cognee-cli vector-reindex / create_missing_vector_indexes(), which is idempotent. Collections created before per-collection HNSW indexing existed have only their primary key, and so does any collection whose index build failed — creation is best-effort (it logs a warning and continues, because failing there would leave the table created and unregistered), so pgvector too old for the hnsw access method, a restricted role or too little maintenance_work_mem all yield a working, silently sequential-scan collection. cognee-cli vector-reindex backfills both cases with CREATE INDEX CONCURRENTLY (online, idempotent, and it rebuilds an index left invalid by an interrupted build); embedders can call PgVectorAdapter::create_missing_vector_indexes() directly, or reach it through VectorDB::create_missing_vector_indexes() on any backend — it defaults to a no-op returning 0 for the ones that have no such index. It is not automatic: building HNSW over a large collection is expensive, so the operator chooses when.
  • Upgrading an existing pgvector store. The halfvec index is a new index under a new name (<coll>_halfvec_hnsw), so a store built by an older version carries the old full-precision <coll>_vector_hnsw, which the halfvec-ordered searches no longer use. Results stay correct — those searches fall back to a sequential scan and a sort, which returns the true top k — but every search on such a store is that scan, with no error. The adapter therefore warns once per collection, the first time it touches one, naming the collection and vector-reindex. cognee-cli vector-reindex is the repair: it builds <coll>_halfvec_hnsw with CREATE INDEX CONCURRENTLY and then drops the superseded <coll>_vector_hnsw (CONCURRENTLY as well, and only once the new index is confirmed valid — on a pgvector below 0.7 that name is the active index, so there it is left alone). Until then every upsert pays two HNSW inserts. The bulk-load path never drops the legacy index itself. The same name change applies to a collection whose name is longer than 50 bytes: index names now reserve room for their suffix and trim the collection part, so such a collection’s index name changes. cognee-cli vector-reindex builds the index under the new name; an index under an old trimmed name is not recognised as superseded and is left on disk for the operator to drop.
  • Postgres graph tables. PgGraphAdapter creates graph_node / graph_edge with their key columns COLLATE "C" and without the redundant source-side covering index. Both apply to new tables only — CREATE TABLE IF NOT EXISTS never rewrites one that exists — so a store created by an older build keeps the locale collation and the extra index, and keeps working. A migration additionally sets per-table autovacuum scale factors (vacuum 0.05, insert 0.05, analyze 0.02) on both tables; it touches no server setting. PgGraphAdapter requires PostgreSQL 13 or newer, because that migration sets autovacuum_vacuum_insert_scale_factor (added in PostgreSQL 13); on 12 the migration fails and the adapter refuses to initialise. The vector adapter and the relational store have no such requirement. Both graph-adapter constructors run with plan_cache_mode = force_custom_plan: PgGraphAdapter::new sets it as a connection option on the pool it opens, and from_connection (used by the shared-Postgres layout, where the pool belongs to the caller) sends it as a SET LOCAL with each parameterised statement, in a transaction so it cannot leak to the next borrower of that connection.
  • Not in OSS. Embedded Qdrant and on-device LiteRT inference (Android) are not part of the cognee-rs repository.
  • Full Postgres stack (relational + graph + vector on one Postgres) is the one remaining adapter milestone — see roadmap/.
MockEmbeddingEngine, MockGraphDB, MockVectorDB, and MockStorage (the testing feature) back the test suite — see test patterns.