booting
imelabs
← the notebook
paper · apr 2026

rag on a budget: pgvector vs the rest

you do not need a managed vector database to do rag. pgvector inside the postgres you already run handles small-to-mid corpora fine. the real argument is operational, plus the signals that tell you when to graduate.


the default advice for retrieval-augmented generation is to reach for a managed vector database: pinecone, weaviate, qdrant, chroma cloud. for a large corpus under real concurrency, that advice is right. for the small-to-mid corpus that most actual products start with, it adds a second bill and a second system to operate, to solve a problem the database you already run can handle.

pgvector is an extension for postgres. if you are already running postgres (neon, supabase, rds, plain), you can store and query embeddings in the same place as the rest of your data.

the argument is operational, not just the bill

the cost saving is real but it is the small part. the bigger case is surface area:

  • one system to back up, secure, monitor and connection-pool, not two.
  • your vectors live next to your application data, so a query can filter on both in one place, no sync pipeline keeping a separate store in step.
  • no extra network hop, no extra sdk, no extra failure mode at 2am.

a second datastore is not just a second cost. it is a second thing that can be down, out of sync, or misconfigured. for a small team that is the expensive part, not the monthly invoice.

how to evaluate it for your case

do not take anyone's benchmark, including this one, as gospel; recall and latency depend on your corpus and your queries. measure with:

  • your real corpus size and document length, not a toy set.
  • the embedding model you actually ship.
  • query patterns that match production (filtered or not, the top-k you actually use).
  • the right index: in pgvector, hnsw for recall and query speed, ivfflat for faster builds and lower memory. tune m / ef_search (hnsw) or lists / probes (ivfflat) and re-measure.

what we found (your numbers)

| | pgvector (hnsw) | managed (named) | |---|---|---| | recall@10 | [fill] | [fill] | | p50 latency | [fill] | [fill] | | p95 under load | [fill] | [fill] | | cost / month | [fill] | [fill] |

those cells are deliberately blank. publishing made-up benchmark figures would be worse than publishing none, and our setup is not your setup. run the table above against your own corpus and the named alternative you are actually weighing. the finding that holds across setups is qualitative: for small-to-mid corpora, pgvector's recall is competitive and its latency is fine, and the gap that matters appears later than people expect.

when to graduate

real signals, not "when it feels slow":

  • your vector count is heading into the millions and index build or rebuild time starts hurting.
  • p95 query latency under your actual concurrency creeps past your budget after you have already tuned the index.
  • you need something pgvector does not do well at scale: heavy metadata filtering combined with vector search, or horizontal sharding across nodes.
  • the vector workload is now contending with your transactional load on the same instance and you want to isolate it.

until one of those is true, the second system is cost and complexity buying you headroom you are not using. graduate when the numbers tell you to, and you will have the numbers because you measured.

doing rag and unsure where your corpus sits on this curve? we've built this.

hey, i'm pebble. the imelabs chatbot. wiring me up properly soon, for now i just watch the cursor.