A Vector index stores embeddings (lists of numbers a model produced from text, images or anything else) together with metadata, and answers "which stored vectors are closest to this one" in milliseconds. That is the building block of semantic search, retrieval for AI answers (RAG) and long-term memory for agents. The API has the shape of Cloudflare Vectorize.
Create an index under Vector with the width of your embedding model (1536 for text-embedding-3-small, 3072 for -large) and a metric (cosine suits most models). Bind it to an app, or declare it in the config and let rr deploy create it:
// Make the vectors with env.AI, store them with their metadata, search by meaning
const [vec] = await env.AI.embed("text-embedding-3-small", chunk.text);
await env.DOCS.upsert([{ id: chunk.id, values: vec, metadata: { title: doc.title, url: doc.url } }]);
const [q] = await env.AI.embed("text-embedding-3-small", question);
const { matches } = await env.DOCS.query(q, { topK: 5, returnMetadata: "all" });
const context = matches.map((m) => m.metadata.title).join("\n");
insert skips ids that exist, upsert replaces them; both take up to 1000 vectors per call. query and queryById return { matches: [{ id, score, values?, metadata? }] } best first (score is similarity for cosine and dot-product, distance for euclidean). getByIds, deleteByIds, describe() and list() complete the set; the bindings reference has every option, including metadata filters such as { lang: "en", stars: { $gte: 3 } } and namespaces.
Writes go to the control plane, which keeps the authoritative copy and a change log. Edge nodes that run your apps hold replicas and apply the log within seconds; queries are answered on the node, so they do not cross the ocean.
Small indexes are searched exactly; large ones use an HNSW graph, with exact search as the fallback when filters prune the neighbourhood.
Dimensions and metric are fixed when the index is created. Vectors of the wrong width are rejected with a clear error.
From the terminal: rr vectorize create|list|insert|upsert|query|delete, and POST /api/edge/v1/vector/<id>/<op> with a token for scripts.