Give your coding agent a brain. One
pgpm deployand Claude, Claude Code, Cursor, or Devin get persistent memory, chat history, a skill library, a tool registry, rules, tasks, runtime observability, and a full CRM/life-OS knowledge graph — all inside a Postgres database.
Once deployed, you can ask your agent questions in plain English and it translates them into semantic, keyword, fuzzy, and spatial queries against the schema:
- "What did Alice and I decide about the acquisition last month?"
- "Pull up every conversation where we debugged the embedding worker."
- "Which tasks are still open on the Q2 launch project?"
- "Find memories from conferences near San Francisco last spring."
- "Remember who I met with at the partner summit last month?"
- "Show me notes where I wrote about RAG architecture."
- "Who have I met with more than three times this quarter?"
- "What's the latest status on deals tagged
enterprise?"
No glue code, no separate vector DB, no RAG service to stand up — the agent just reads and writes Postgres through the typed SDK, CLI, or GraphQL.
Conversations, messages, tool calls, long-term memories, rules, skills, prompts, tasks, runtime state, and a full personal CRM/life-OS live side-by-side. Every embeddable table is auto-indexed for semantic + keyword + fuzzy + spatial search, and a background worker keeps embeddings fresh via Ollama (or your LLM of choice). Deploy it next to your agent, wire it up through the typed SDK/CLI or the included Agent Skills, and your agent instantly has persistent memory, chat history, a skill library, and structured knowledge of the user's world.
| Need for an agent | What agentic-db ships |
|---|---|
| Long-term memory | memories + agent-scoped memories with vector + BM25 + chunked embeddings |
| Working memory / conversation state | conversations + messages + tool_calls + tool_results |
| Skills / tools registry | skills, tool_definitions, tool_executions, prompts (versioned) |
| Behavior rules | rules with semantic trigger_concept matching |
| Task queue | tasks with priority, status, agent assignment |
| Observability | agent_logs, runtime_states, runtime_logs, runtime_metrics, runtime_artifacts |
| Scheduling | runtime_schedules (cron) + runtime_events (event bus) |
| Config | runtime_config (with is_secret flag) |
| World model (people, orgs, places) | Full CRM + Life-OS + Email/Calendar |
| Retrieval | Unified search: vector (pgvector HNSW) + BM25 + tsvector + trigram + PostGIS |
| Auto-embed | Postgres triggers enqueue embedding jobs; Ollama worker processes them |
It's all in one database, with vector + BM25 + full-text + trigram + PostGIS search baked in.
┌─────────────────────────────────────────────────────────┐
│ Your Agent (Claude / Claude Code / │
│ Cursor / Devin / …) │
└───────────────┬─────────────────────────┬───────────────┘
│ │
writes / reads invokes
│ │
▼ ▼
┌─────────────────────────────────────────────────────────┐
│ agentic-db (Postgres, one DB) │
│ │
│ conversations ──┬── messages ── tool_executions │
│ │ │
│ agents ─── tasks ─── rules ─── skills ─── prompts │
│ │
│ memories ── autonomy_records ── notes (chunked) │
│ │
│ contacts · companies · events · places · emails · … │
│ │
│ [ vector · BM25 · FTS · trigram · PostGIS, unified ] │
└───────────────▲─────────────────────────▲───────────────┘
│ │
auto-embed GraphQL / SDK / CLI
│ │
@agentic-db/worker @agentic-db/sdk · cli
│
Ollama
memories(Life-OS) — long-term episodic memory with title, content, location, timestamp, mood, tags. Unified search (vector + BM25) + PostGIS spatial so the agent can ask "what happened near here last spring?".autonomy_records— self-managed knowledge units the agent writes for itself (goals, notes-to-self, learned facts), with self-referential many-to-many links (autonomy_record_links) so the agent builds its own knowledge graph.notes— long-form knowledge with chunked embeddings: a single note gets split into multiple vector rows automatically so retrieval works on long documents.- Cross-domain memory junctions —
contact_memories,company_memoriestie memories to the people/orgs they're about, so the agent can pull "everything I remember about Alice" in one query. - Agent-attributed memories — every memory can carry an
agent_idFK so multi-agent setups get isolated or shared memory. - Chunk-aware search —
contacts_chunksandnotes_chunkslet the agent retrieve the relevant paragraph of a long record, not the whole record. - Tags as first-class citizens —
citext[]tag columns on every memory-ish table, GIN-indexed, so filtering by['hackathon','kris-floyd']is fast.
conversations— titled, agent-scoped chat sessions with status + metadata. Indexed and searchable (find that conversation from 3 weeks ago by vibe).messages— role (user/assistant/tool), content,token_count,tool_callsjsonb,tool_resultsjsonb, full metadata. Unified search means you can semantically query across every message the agent has ever seen.tool_executions— every tool invocation recorded: input, output, status, timings, errors, with FK back to the message that triggered it. Full audit trail of what the agent actually did.- Thread-able — FK relations let you reconstruct conversation trees;
conversations ↔ messages ↔ tool_executionsforms a replayable event log. - Token accounting built in — per-message
token_countgives you real context-window budgeting and cost reporting.
skills— named capabilities withintent_triggerembedding so the agent can semantically pick the right skill for a user utterance ("help me plan a trip" → skill with closestintent_trigger_embedding).tool_definitions— JSON-schema-validated tool specs (works great as an OpenAI/Anthropic tools payload source of truth).skill_toolsjunction — skills compose from multiple tools.prompts— versioned, tagged, semantically searchable prompt library.agent_promptsjunction lets you bind prompts to agents.rules— declarative trigger/action pairs (trigger_type,trigger_config,action_type,action_config) with priority + semantictrigger_conceptmatching. This is how you give the agent a behavioral policy layer.
agents— named agents withsystem_prompt,model,temperature,config, tags. Multi-agent out of the box.agent_collaborators— agents can reference other agents (delegation, sub-agents).tasks— priority queue with status, result, started/completed timestamps, agent assignment. Doubles as a todo list the human can read.runtime_states— hierarchical state machine rows (parent_id) for long-running workflows; attach logs, metrics, artifacts.runtime_logs/runtime_metrics/runtime_artifacts— structured observability per run.runtime_schedules— cron-style scheduled jobs inside the DB.runtime_events— event bus table (type + payload + status) for async orchestration.runtime_config— key/value config withis_secretflag.agent_logs— free-form agent telemetry with context jsonb and optional task linkage.
-
Unified Search API per table: one query can combine vector similarity, BM25 ranking, weighted tsvector full-text, and trigram fuzzy — all exposed through the generated GraphQL SDK.
-
Auto-embedding pipeline — Postgres triggers enqueue jobs on insert/update; the
@agentic-db/workerpackage processes them via Ollama (nomic-embed-text, 768-dim). Your agent never has to remember to embed anything. -
HNSW vector indexes (pgvector) with cosine/L2/inner-product metrics.
-
BM25 via
pg_textsearch— statistical relevance ranking, not just similarity. -
Weighted FTS —
A/B/Cweights per field soname > headline > bionaturally. -
Trigram fuzzy matching for typo-tolerant name search.
-
PostGIS spatial on contacts, events, venues, places, memories, trips —
Pointgeography columns auto-backed by aGISTindex. Scalar filters (bboxIntersects2D,isNull) ship on every geom column today; single-table radius queries are a schema decision away. -
Cross-table spatial relations (
@spatialRelation) — FK-less spatial joins exposed as namedwhere:filters. The blueprint ships 5 out of the box (seepackages/provision/src/schemas/spatial-relations.ts):memory.nearbyPlaces— memories within N metres of anyplace(5 km default)memory.nearbyContacts— memories within N metres of anycontact(2 km default)trip.nearbyVenues— trips whosedestination_geois within N metres of avenue(1 km default)event.nearbyVenues— events within N metres of avenue, no FK needed (500 m default)memory.nearbyMemories— self-join, "what else happened near this memory?" (1 km default)
All 5 use
st_dwithinwith a per-querydistanceparam, so radius is a query-time input not a schema constant. Each renders server-side as anEXISTS (… ST_DWithin(geo_a, geo_b, $distance) …)subquery — zero GeoJSON on the wire. -
Chunked long-doc retrieval on contacts and notes.
- CRM:
contacts(with denormalized primary email/phone/location + normalizedcontact_emails/contact_phones/contact_addresseschildren),companies,deals,events,venues,notes,interactions,touchpoints,tags, image galleries. - Life-OS:
goals,habits,activity_logs,memories,trips,places. - Projects & expenses:
projects,expenses, with cross-relations to contacts, trips, tasks. - Email & Calendar:
email_threads,emails,email_attachments,calendars,calendar_events,calendar_attendees,provider_sync_states(for Gmail / Google Calendar-style provider sync). - Staging tables (
raw_contacts,raw_contact_emails, etc.) for messy import pipelines before normalizing intocontacts. - ~25 cross-domain M:N junctions so your agent can answer "notes about Alice from the partner summit" without schema gymnastics.
- One command to deploy:
pgpm deploy --createdb --database agentic-db --yes --package agentic-db. @agentic-db/sdk— Prisma-like typed ORM generated from the GraphQL schema (covers all 91 tables).@agentic-db/cli— CRUD + search + admin commands for every table.@agentic-db/rag— hybrid search, batch embedding, multi-pass Q&A CLI tools.@agentic-db/worker— background embedding worker.- Agent Skills included — ships with skill files (
skills/agent/memories.md,skills/agent/tasks.md,skills/rag-query.md, etc.) that install into Claude, Claude Code, Cursor, Copilot, Windsurf, Codex, or Devin vianpx skills add constructive-io/agentic-db. The DB teaches your agent how to use it. - Schema-as-code — blueprints in
packages/provision/src/schemas/*.tsdefine every table, so you fork, add a table,pnpm run provision && pnpm run export, and you have a new versioned pgpm module. - Standalone or multi-tenant — deploy clean into its own DB, or run inside the Constructive platform with RLS / Safegres policies.
- GraphQL API auto-exposed via PostGraphile v5 with the Constructive search plugin (vector / BM25 / trigram / spatial unified).
- Docker-first —
pgpm docker start --ollamagets you Postgres + Ollama in one command (CPU or GPU).
End-to-end: Docker → deploy schema → run GraphQL server → use CLI → use SDK.
See Constructive Quickstart → Prerequisites for Node.js, pnpm, Docker, and psql setup. Then install the three CLIs you'll use below:
npm install -g pgpm
npm install -g @constructive-io/cli
npm install -g @agentic-db/clipgpm docker start runs constructiveio/postgres-plus:18 (Postgres with pgvector, pg_textsearch, PostGIS, and the other extensions agentic-db uses) with 2 GB shared memory:
pgpm docker start # Postgres
pgpm docker start --ollama # Postgres + Ollama (CPU) for auto-embedding
pgpm docker start --ollama --gpu # same, NVIDIA GPU
pgpm docker stop # stop everythingAlready have an LLM running? Just use pgpm docker start and point OLLAMA_URL at your existing instance. A tuned docker-compose.yml is also provided if you prefer docker compose up -d.
# First time: bootstrap admin roles in the cluster
eval "$(pgpm env)"
pgpm admin-users bootstrap --yes
# Create a workspace + install the agentic-db pgpm module
pgpm init workspace
cd my-app && pgpm init && cd packages/my-module
pgpm install agentic-db
# Create the database and deploy all 91 tables + indexes + triggers
pgpm deploy --createdb --database agentic-db --yes --package agentic-dbSee the agentic-db package README for the full deployment guide and schema details.
The CLI and SDK both talk to the database through a GraphQL endpoint, so you need a PostGraphile server pointed at the deployed DB. The Constructive CLI (cnc) spins up PostGraphile with the same plugin bundle used in tests — vector search, BM25, trigram, PostGIS, meta-API — all preconfigured:
# Point it at the database you just deployed (standard PG env vars)
export PGHOST=localhost PGPORT=5432 PGUSER=postgres PGPASSWORD=password
export PGDATABASE=agentic-db
# GraphQL at http://localhost:5555/graphql
cnc server
# In another shell: open GraphiQL to poke at the schema
cnc explorerSee the Constructive CLI docs for options (port, CORS origin, toggling PostGIS/meta-API, etc.).
With the server running, point the agentic-db CLI at it and your agent has a typed CRUD + search surface over every table:
# Create a context once
agentic-db context create local --endpoint http://localhost:5555/graphql
agentic-db context use local
agentic-db auth set-token "$AGENTIC_DB_TOKEN" # optional — anonymous also works
# Unified search (vector + BM25 + FTS + trigram) across one or more tables
agentic-db search "postgres distributed systems" \
--tables contacts,memories,notes --json --tty false
# RAG question-answering across embedded tables
agentic-db ask "Who did I meet about the Q2 launch?" --tty false
# Typed CRUD — one subcommand per table (contact, note, task, memory, …)
agentic-db contact create --firstName Alice --lastName Smith --select id --tty false
agentic-db contact list --select id,firstName,lastName --json --tty false
agentic-db note create --title "Kickoff" --content "Discussed Q2 roadmap" --tty false
agentic-db task list --where.status.equalTo open --json --tty false
agentic-db memory create --title "Met Alice" --content "Discussed acquisition" --tty falseEvery command supports --tty false (non-interactive / scripted) and --json (machine-readable) — which is what agents almost always want. Full command surface in the cli-default skill; known-good examples in the CLI E2E tests.
The @agentic-db/sdk is a type-safe, Prisma-like ORM generated from the same GraphQL schema — it hits the same cnc server endpoint:
npm install @agentic-db/sdkimport { createClient } from '@agentic-db/sdk';
const db = createClient({ endpoint: 'http://localhost:5555/graphql' });
// Typed CRUD with `select` = which fields to return
const alice = await db.contact
.create({
data: { firstName: 'Alice', lastName: 'Smith', headline: 'Engineer' },
select: { id: true, firstName: true },
})
.execute();
// Unified search (vector + BM25 + FTS + trigram)
const results = await db.contact
.findMany({
where: { unifiedSearch: 'postgres distributed systems' },
first: 10,
select: { id: true, firstName: true, searchScore: true },
})
.execute();
// Unified search + cross-table PostGIS spatial filter, composed in one where:
// "Memories whose content semantically matches 'conference keynote' AND are
// within 5 km of a place tagged as a market — return each with its
// relevance score and stored GeoJSON point, all in one round-trip."
const ranked = await db.memory
.findMany({
where: {
unifiedSearch: 'conference keynote retrieval',
nearbyPlaces: {
distance: 5000, // metres — columns are geography so distance is metric
some: { category: { equalTo: 'market' } },
},
},
first: 10,
select: {
id: true,
title: true,
searchScore: true,
locationGeo: { select: { geojson: true, srid: true } },
},
})
.execute();The server compiles that into a single SQL statement: a unified_search(...) ranked CTE joined against an EXISTS (… ST_DWithin(memory.location_geo, place.location_geo, 5000) …) subquery. No GeoJSON goes over the wire on the spatial side, and the text-search score comes back as searchScore.
That exact combined shape is exercised end-to-end by an integration test: packages/agentic-db/__tests__/unified-spatial-combined.test.ts. It boots a real deploy of the agentic-db pgpm package, seeds three memories and two market-category places at known coordinates, runs the same memory.findMany({ where: { unifiedSearch, nearbyPlaces } }) call through the generated SDK, and asserts that only the positive-match memory comes back with a non-null searchScore.
Supporting single-axis coverage lives alongside:
- Spatial-only —
nearbyPlaces/nearbyContacts/nearbyVenues/nearbyMemoriesare each exercised inpackages/integration-tests/__tests__/orm.test.tsunder theRelationSpatial via ORMdescribe block (all 5 relations declared in the blueprint). - Unified-search only —
unifiedSearch+searchScoreranking behavior is covered bypackages/agentic-db/__tests__/rag-unified-search.test.tsagainst pre-bakednomic-embed-textfixtures (no Ollama required).
Full ORM reference in the orm-default skill.
| Package | npm | Description |
|---|---|---|
agentic-db |
agentic-db |
pgpm SQL module -- the core database schema with 90+ tables and search indexes |
@agentic-db/services |
@agentic-db/services |
pgpm SQL module -- API endpoint and domain routing metadata |
@agentic-db/sdk |
@agentic-db/sdk |
Type-safe Prisma-like ORM client generated from the GraphQL schema |
@agentic-db/cli |
@agentic-db/cli |
CLI tool for CRUD, search, and admin operations |
| Package | Description |
|---|---|
@agentic-db/provision |
SDK-based blueprint provisioning (tables, relations, search) |
@agentic-db/export |
pgpm export wrapper (extracts provisioned schema as SQL modules) |
@agentic-db/rag |
RAG CLI tools (hybrid search, batch embedding, multi-pass Q&A) |
@agentic-db/worker |
Background worker for auto-generating embeddings via Ollama |
@agentic-db/schemas |
GraphQL schema files (.graphql) used by codegen |
@agentic-db/integration-tests |
Integration test suite (ORM, embeddings, RAG, unified search) |
@agentic-db/cli-e2e-tests |
End-to-end CLI test suite |
The schema is developed using the Constructive SDK provisioning pipeline:
- Edit blueprints in
packages/provision/src/schemas/-- define tables, fields, relations, search nodes - Provision --
cd packages/provision && pnpm run provisionapplies blueprints against the platform DB - Export --
cd packages/export && pnpm run exportextracts the schema as pgpm SQL modules - Deploy --
pgpm deploy --package agentic-dbinstalls into any Postgres database - Regenerate codegen --
pnpm run generate:allupdates the SDK and CLI from the live schema
Postgres triggers automatically enqueue embedding jobs when records are created or updated. The background worker processes them via Ollama:
# Start the embedding worker
cd packages/worker
pnpm run startThe worker generates embeddings for all tables with SearchUnified or SearchVector nodes. Contacts and notes also get chunked embeddings for long-document search.
# Run all tests (from repo root)
pnpm test
# Run a specific test suite
cd packages/agentic-db && pnpm test # pgpm deploy + schema tests
cd packages/integration-tests && pnpm test # ORM, embeddings, RAG, unified search
cd packages/cli-e2e-tests && pnpm test # CLI end-to-endThis repo ships with Agent Skills that teach AI assistants (Claude, Claude Code, Cursor, Devin, Copilot, etc.) how to work with the SDK, CLI, and pgpm.
| Skill | Description |
|---|---|
pgpm |
Install and deploy agentic-db using pgpm |
cli-default |
CLI command reference for all 91 tables |
orm-default |
Type-safe ORM client reference for all 91 tables |
agent/memories |
Storing and retrieving long-term agent memories |
agent/tasks |
Managing agent task queues |
rag-query |
Multi-collection RAG query patterns |
embeddings |
Generating embeddings via Ollama |
crm/* |
CRM primitives — contacts, companies, events, venues |
accounting/* |
Expense tracking primitives |
Install skills into your project using npx skills:
# Install all skills from this repo
npx skills add constructive-io/agentic-db
# Install a specific skill
npx skills add constructive-io/agentic-db --skill pgpm
# List available skills without installing
npx skills add constructive-io/agentic-db --listThis works with Claude, Claude Code, Cursor, Copilot, Windsurf, Codex, and 40+ other AI agents. Skills are installed into the appropriate directory for your tool (.claude/skills/, .cursor/skills/, etc.).
Devin -- Connect the constructive-io/agentic-db repo to your Devin organization. Skills are indexed automatically and available in every session.
Once installed, you can ask your AI assistant things like:
- "Deploy agentic-db to a new database" -- triggers the
pgpmskill - "Remember that Alice is my co-founder at Acme" -- triggers the
agent/memoriesskill - "What do I know about the partner summit?" -- triggers the
rag-queryskill - "Query contacts using the ORM" -- triggers the
orm-defaultskill - "Search for deals using the CLI" -- triggers the
cli-defaultskill
Built by the Constructive team -- creators of modular Postgres tooling for secure, composable backends. Contribute on GitHub.
AS DESCRIBED IN THE LICENSES, THE SOFTWARE IS PROVIDED "AS IS", AT YOUR OWN RISK, AND WITHOUT WARRANTIES OF ANY KIND.
No developer or entity involved in creating this software will be liable for any claims or damages whatsoever associated with your use, inability to use, or your interaction with other users of the code, including any direct, indirect, incidental, special, exemplary, punitive or consequential damages, or loss of profits, cryptocurrencies, tokens, or anything else of value.