The transactional document database for AI agents and apps.
Give every AI agent, tenant, or app its own logical database in a single cluster. One transaction still commits across all of them.
BEGIN # An agent stores a memory, vector and all. NAMESPACE USE agents.support-bot BUCKET.INSERT memories DOCS '{"text": "prefers email", "embedding": [0.12, 0.07, 0.91]}' # Same commit bumps a shared usage counter. NAMESPACE USE billing ZINC.I64 support-bot:tokens 1240 COMMIT
An isolated, transactional document database with built-in vector search, for every AI agent and app, on one cluster.
Shared database: a tenant_id on every query. One missing filter leaks one tenant's data into another's.
Database per tenant: clean isolation, but nobody runs thousands of real databases.
Scaling out: horizontal scale is either hard to operate, or it means a third-party plugin or a separate product.
A logical database is just a prefix in the keyspace, which Kronotop calls a namespace, so creating one is free. Each one is isolated by the prefix, not by application code, and millions run on one horizontally scalable cluster, with no plugins or separate products.
It is a full document database: BQL queries, secondary indexes, sorting. Vector search is built in, so similarity queries run on the same data without a separate engine. ZMap, an ordered key-value store, shares the same transaction. Commits are strictly serializable and span any namespace.
Isolated databases are usually islands. Crossing them means two-phase commit, sagas, or eventual consistency. Kronotop keeps one commit across every namespace and across both data models, documents and ordered key-value, so writes either all land or none do, with conflict detection from FoundationDB.
Documents and an ordered key-value store share a transaction, with vector search over document fields.
BSON documents with a query language (BQL), secondary indexes, and sorting.
Key-valueOrdered key-value model with range scans and conflict-free atomic counters.
ConsistencyStrictly serializable by default, inherited from FoundationDB. Auto-commit or explicit BEGIN/COMMIT.
IsolationPer-tenant databases, called namespaces, with keyspace-level isolation on FoundationDB directories.
SearchApproximate nearest-neighbor search over document vector fields, powered by JVector (HNSW).
OperationsSharded, distributed deployment with primary-standby replication. Coordination is handled by FoundationDB.
Find documents by what they contain, or by what they mean. BQL covers structured filters; vector search covers similarity.
// structured filter with BQL
NAMESPACE USE agents.support-bot BUCKET.QUERY memories '{"importance": {"$gte": 0.5}}' 1# "cursor_id" => (integer) 1 2# "entries" => 1) {"_id": "...", "kind": "preference", "importance": 0.8, "text": "prefers email"}
// vector similarity + structured filter
BUCKET.VECTOR memories embedding '[0.10, 0.09, 0.88]' FILTER '{"kind": "preference"}' TOP 3 1) 1# "score" => (double) 0.9981 2# "entry" => {"_id": "...", "text": "prefers email"}
Kronotop speaks Redis wire protocol, so the client libraries and tooling you already use connect straight to it. Open a connection, encode BSON, run a document query, and read a RESP3 map back. Nothing new to learn.
import redis
from bson import encode as bson_encode, decode as bson_decode
# Connect to Kronotop using RESP3
r = redis.Redis(host="127.0.0.1", port=5484, protocol=3)
# Encode the filter to BSON and run BUCKET.QUERY
query = bson_encode({"user_id": "alice"})
res = r.execute_command("BUCKET.QUERY", "my_collection", query, "LIMIT", 10)
# Extract the cursor and document list from the RESP3 map
# RESP3 -> {"cursor_id": ..., "entries": [<bson>, ...]}
cursor_id = res[b"cursor_id"]
entries = res[b"entries"] or []
# Decode and print each raw BSON entry
for raw in entries:
doc = bson_decode(raw)
print(doc) import { createClient } from 'redis';
import { serialize, deserialize } from 'bson';
// Connect to Kronotop using RESP3
const r = createClient({ url: 'redis://127.0.0.1:5484', RESP: 3 });
await r.connect();
// Encode the filter to BSON and run BUCKET.QUERY
const query = serialize({ user_id: 'alice' });
const res = await r.sendCommand(['BUCKET.QUERY', 'my_collection', query, 'LIMIT', '10']);
// Extract the cursor and document list from the RESP3 map
// RESP3 -> { cursor_id: ..., entries: [<bson>, ...] }
const cursorId = res.cursor_id;
const entries = res.entries ?? [];
// Decode and print each raw BSON entry
for (const raw of entries) {
console.log(deserialize(raw));
} Namespace-level isolation, vector search, and transactional updates for agent memory.
A horizontally scalable document store backed by strictly serializable transactions.
Lease-based locks with atomic acquire, safe release, and fencing tokens from versionstamped commits.
Range scans, counters, and conflict-free atomic mutations on the ZMap model.
FoundationDB in single-redundancy mode on EC2. See the full results and deployment setup.
| Query | Throughput | p99 |
|---|---|---|
| Indexed equality | 11,751 qps | 6.12 ms |
| Compound index | 11,082 qps | 6.49 ms |
| Sort + limit 10 | 23,008 qps | 2.88 ms |
| Full scan (unindexed) | 1,958 qps | 50.02 ms |
Copy two commands and you have a local cluster running.
$ curl -O https://kronotop.com/kronotop-quickstart.yaml $ docker compose -f kronotop-quickstart.yaml up