Docs

Knowledge Graph (AGE)

Sulcus uses Apache AGE — a temporal knowledge graph extension for PostgreSQL — as the structural backbone for memory relationships. Memories are vertices, relationships are edges. Every store, recall, and entity extraction writes to AGE automatically. The graph is self-healing.

Sulcus v2.9 · Apache AGE Knowledge Graph · age_graph capability

Overview

A temporal knowledge graph built on Apache AGE — Postgres-native, self-healing

Every other memory system stores text. Sulcus stores structured knowledge. The AGE graph tracks not just what memories exist, but how they relate to each other — and when those relationships were formed.

This is fundamentally different from vector similarity (which answers "what is near this?") or BM25 text search (which answers "what contains this word?"). The knowledge graph answers: "What does the agent know about X, and how does X connect to everything else?"

Postgres-Native

Apache AGE runs as a Postgres extension. No separate graph database. Same ACID guarantees. Same backups.

Self-Healing

Every store, recall, and entity extraction writes to AGE automatically. The graph is always consistent with the memory store.

Cypher Queries

Full Cypher query language. Traverse relationships, filter by heat or type, find paths between memories.

SILU — Entity Extraction

Store Intelligence Labeling Unit: GPT-5.4-nano extracts entities and relationships on every store

SILU runs automatically on every memory store. It sends the memory content to GPT-5.4-nano and extracts:

  • entities — Named things: people, tools, services, concepts, projects
  • relationships — How entities relate: USES, PART_OF, RELATES_TO, DEPENDS_ON
  • triples — Entity → Relation → Entity, written to AGE as graph edges

The result: every memory is automatically enriched with structured knowledge. A procedural memory about deployment becomes a node connected to "ACR", "Azure", and "az containerapp" via typed edges.

// Entity triples extracted by SILU from:
// "Deploy: push to ACR then az containerapp update — Azure project"
//
// Extracted triples:
//   (Memory) --[HAS_ENTITY]--> (Entity: "ACR", type: "service")
//   (Memory) --[HAS_ENTITY]--> (Entity: "az containerapp", type: "tool")
//   (Memory) --[HAS_ENTITY]--> (Entity: "Azure", type: "platform")
//   (Entity: "ACR") --[PART_OF]--> (Entity: "Azure")
//   (Entity: "az containerapp") --[USES]--> (Entity: "ACR")
graph

Graph Structure

Vertex and edge schema — what's stored in the AGE graph

Memory Verticeslabel: Memory

Every memory node is a vertex in the AGE graph. Properties mirror the memory store:

PropertyDescription
idUUID — matches the memory node ID
labelMemory content label (searchable)
memory_typeepisodic, semantic, procedural, fact, preference
namespaceAgent/tenant namespace
heatCurrent heat value (0–1, updated on tick and recall)
base_utilitySIVU utility score (0–1)
created_atISO timestamp of creation
updated_atISO timestamp of last update
Entity Verticeslabel: Entity

Named entities extracted by SILU. Properties: name, type (person, tool, service, concept, platform), namespace, mention_count.

Edge Types
RELATES_TO
HAS_ENTITY
PART_OF
USES
DEPENDS_ON
CO_RECALLED

Cypher Queries

Full openCypher query language — traverse relationships, filter by heat or type

Find related memories by traversal

// Find all memories related to "deployment" within 2 hops
MATCH (m:Memory)-[r:RELATES_TO*1..2]-(related:Memory)
WHERE m.label CONTAINS 'deploy'
  AND m.heat > 0.3
RETURN m, r, related
ORDER BY related.heat DESC
LIMIT 20
cypher

Find entities extracted from a memory type

// Find all entities extracted from procedural memories
MATCH (m:Memory {memory_type: 'procedural'})-[:HAS_ENTITY]->(e:Entity)
WHERE m.namespace = 'my-agent'
RETURN e.name, e.type, COUNT(m) as mention_count
ORDER BY mention_count DESC
cypher

Temporal Traversal

Query the graph at a point in time — what did the agent know before a given date?

Every vertex and edge carries timestamps. You can traverse the graph at any point in time — asking questions like "what did this agent know about deployment before the incident?" or "which facts were hot during last quarter?"

This is the AGE advantage over pure vector stores: temporal validity windows. Not just "what is similar" but "what was true at this moment."

// Temporal traversal — find what was known before a date
MATCH (m:Memory)
WHERE m.created_at < '2026-03-01T00:00:00Z'
  AND m.heat > 0.2
  AND m.namespace = 'my-agent'
RETURN m.label, m.memory_type, m.heat, m.created_at
ORDER BY m.heat DESC
cypher

Self-Healing Graph Writes

Every memory operation keeps the AGE graph in sync automatically

The AGE graph is not a separate system you need to maintain. Every operation that touches the memory store also updates the graph:

memory_storeCreates vertex with all properties; SILU extracts entities and writes triples
memory_recallUpdates vertex heat in AGE; creates CO_RECALLED edges between co-occurring memories
memory_deleteRemoves vertex and all incident edges; entities are orphaned (not deleted — may be shared)
memory_boostUpdates heat property on vertex immediately
tick (300s)Batch-updates heat on all vertices to match the memory store after decay
entity extractionSILU runs asynchronously post-store; adds HAS_ENTITY edges and Entity vertices

Zero configuration required. The AGE graph writes are built into the memory engine. When you store a memory via SDK, REST API, MCP, or OpenClaw plugin, the graph is updated automatically. The age_graph: true capability flag in the server status confirms the graph backend is active.

REST API

HTTP endpoints for graph queries and entity access

POST/api/v1/graph/query
GET/api/v1/graph/nodes/:id
GET/api/v1/graph/nodes/:id/entities
GET/api/v1/graph/entities
GET/api/v1/graph/entities/:name/memories
# Query the AGE graph via REST
curl -X POST https://api.sulcus.ca/api/v1/graph/query \
  -H "Authorization: Bearer sk-..." \
  -H "Content-Type: application/json" \
  -d '{
    "cypher": "MATCH (m:Memory) WHERE m.heat > 0.5 RETURN m.label, m.heat LIMIT 10",
    "namespace": "my-agent"
  }'

# Get entity relationships for a memory
curl https://api.sulcus.ca/api/v1/graph/nodes/node_01J.../entities \
  -H "Authorization: Bearer sk-..."
bash

MCP Tools

Query the knowledge graph from any MCP-compatible agent

The Sulcus MCP server exposes graph tools alongside the standard memory tools. Your agents can traverse the knowledge graph, find related memories, and query entity relationships directly from conversation context.

graph_query
get_memory_entities
list_entities
find_related
// MCP tool — graph_query
{
  "cypher": "MATCH (m:Memory)-[r:RELATES_TO]-(n:Memory) WHERE m.id = 'node_01J...' RETURN n",
  "namespace": "my-agent"
}
json

Memory that knows itself.

The AGE knowledge graph is active in Sulcus v2.9. Check your server status for age_graph: true to confirm the graph backend is running. No configuration required — store a memory, and the graph updates automatically.