Once you've decided your vector store should run inside your process — no Qdrant pod, no Milvus cluster, no Weaviate server to babysit — the shortlist collapses to two names: Chroma and LanceDB. Both are Apache-2.0. Both are "AI-native." Both start with one pip install and a local directory. And the benchmark screenshots that pit them against each other are, mostly, the wrong artifact — at the scale where you'd choose an embedded store, recall quality is a wash. The real decision is made one layer down, on storage. Chroma and LanceDB optimize two different things, and naming which one you actually care about picks your database for you.

Chroma: optimize the path to shipping#

AI-native open-source embedding database with a serverless cloud path
★ 28.8kRustchroma-core/chroma

Chroma's whole design pressure is time to first query, and then time to production. You pip install chromadb, get a collection, add documents, and query — embedded, in-memory, persisted to disk with a flag. The same API runs as a local client-server (chroma run) and, unchanged, against Chroma Cloud, its managed serverless tier. That single mental model — one client, three deployment shapes — is the product.

What's easy to miss is that "embedded and easy" no longer means "toy." Chroma's core was rewritten in Rust (the repo is now majority-Rust), and Chroma Cloud is a distributed, object-storage-tiered engine, not a hosted single node. So the honest framing isn't "prototype in Chroma, then migrate to something serious." It's: prototype in Chroma, and when you're ready, flip to a managed serverless backend that's the same API and priced on usage — a cited ~$0.02/GB-month of object storage, a free tier, and startup credits. The value you're buying is the path: the least infrastructure and the least code-change between a notebook and a running product. If your hard problem is "ship a working RAG loop this week and don't think about ops," Chroma is the shorter road. (Chroma's move onto object storage is itself a design bet worth understanding before you commit — we pulled it apart in Chroma's object-storage bet.)

LanceDB: optimize the format the data lives in#

Embedded multimodal retrieval library built on the versioned Lance columnar format
★ 10.9kRustlancedb/lancedb

LanceDB inverts the emphasis. The database is almost a thin, friendly layer over the thing that actually matters: the Lance columnar format. Lance is on-disk, object-storage-native (it reads and writes vectors directly against S3, not a local SSD it has to warm), versioned (every write produces a new immutable snapshot of the table), zero-copy, and interoperable with Apache Arrow and DuckDB. LanceDB is embedded like Chroma — no server — but you point it at a bucket and it operates on the format in place.

That choice pays off exactly where Chroma's convenience stops mattering and the data becomes the hard part. Three cases:

Chroma's durable value is the road out of your laptop. LanceDB's durable value is that your data is already sitting in an open format you could query with DuckDB even if LanceDB vanished tomorrow.

The lock-in that actually shows up later#

Both are Apache-2.0 and self-hostable, so neither hands you a bill or a server on day one. The lock-in that matters arrives later, and it's asymmetric. Chroma's enduring value is its managed cloud path — which means the day you want to leave Chroma Cloud is an export-and-migrate day. LanceDB's enduring value is that your vectors already live in the open Lance format: portable by construction, readable by Arrow and DuckDB tooling with or without LanceDB in the loop. Neither is a trap. But "what does my data look like if I remove this dependency?" has two genuinely different answers here, and it's worth answering before you've written a million rows.

The decision, made plainly#

Don't run the recall benchmark first. Ask which problem is actually yours — the road or the cargo — and the embedded vector store picks itself. Then, and only then, tune the index.