Agent Inbox Design — HCS-10/11 Compliant Messaging
Agent Inbox Design — HCS 10/11 Compliant Messaging Date: 2026 04 25 Status: Approved for implementation Overview Every agent (and Justin) has a persistent, on chain inbox. Agent to agent messages are posted to HCS topic topics first — Supabase is the fast read mirror. The listener bridges HCS → Supabase. The runner polls Supabase inbox as the fast path each ...
Date: 2026-04-25 Status: Approved for implementation
---
Every agent (and Justin) has a persistent, on-chain inbox. Agent-to-agent messages are posted to HCS topic topics first — Supabase is the fast-read mirror. The listener bridges HCS → Supabase. The runner polls Supabase inbox as the fast path each cycle.
---
Each agent gets two HCS topics, created once and stored in agent_definitions:
| Topic | Memo Format | Purpose |
|---|---|---|
| Inbound | hcs-10:0:3600:0:{accountId} | Receives messages from other agents and system |
| Outbound | hcs-10:0:3600:1 | Agent's public activity log (future use) |
agent_definitions gains two new columns: inbound_topic_id, outbound_topic_id.
Existing hcs_topic_id column is retired (was never populated).
Justin (slug: justin) gets topics too — he is a first-class participant.
---
Messages posted to an agent's inbound topic:
``json
{
"p": "hcs-10",
"op": "message",
"operator_id": "{sender_inbound_topic}@{sender_account}",
"data": {
"message_type": "task.blocked | task.complete | task.note | phase.note | project.note | feedback | fyi | review.request",
"subject": "Human-readable subject line",
"payload": {},
"ref_id": "0.0.XXXXX",
"ref_type": "task | phase | stage | project | agent",
"priority": 1
},
"ts": "ISO8601"
}
``
Priority: 1=urgent, 2=high, 3=normal, 4=low, 5=fyi
Internal shortcut: Trusted internal agents can post directly without the full HCS-10 connection handshake. External agent interop (connection_request → connection_created → connection topic) is a future enhancement.
---
Agents can post notes directly to entity topics (tasks, phases, stages, projects):
``json
{
"type": "task.note | phase.note | project.note",
"from_agent": "quinn",
"note": "markdown content",
"notify": ["mindy", "justin"],
"ts": "ISO8601"
}
``
The listener routes *.note messages → inbox of agents in notify list.
---
Fast-read mirror. Runner polls this each cycle.
``sql
inbox (
id uuid PK,
to_agent text NOT NULL, -- agent slug or 'ALL'
from_agent text NOT NULL, -- agent slug or 'system'
message_type text NOT NULL,
subject text NOT NULL,
payload jsonb,
context jsonb, -- additional context for rich info sharing
ref_id text, -- entity topic_id or UUID
ref_type text, -- task | phase | stage | project | agent
priority int DEFAULT 3,
processed bool DEFAULT false,
processed_at timestamptz,
processed_by_session uuid,
created_at timestamptz DEFAULT now()
)
``
Indexes: (to_agent, processed, created_at), (ref_id), (from_agent, created_at desc)
---
- Queries
agent_definitionsfor allinbound_topic_idvalues - Polls each, processes
op: "message"→ writes to Supabaseinbox - Handles
*.noteon entity topics → routes tonotifylist inboxes
Direct Supabase write for system-originated notifications (no round-trip through HCS):
| Event observed | Who gets inbox message | Priority |
|---|---|---|
| task.blocked | mindy + justin | 1 (urgent) |
| task.complete | engine | 3 (normal) |
| phase.complete | engine + mindy | 2 (high) |
| *.note | agents in notify field | per note |
---
fetch_inbox() in base.py already queries inbox table — no change needed once migration is applied and table exists.
---
Agents call this during sessions to send a message to another agent or Justin:
``json
{
"name": "send_message",
"description": "Send a message to another agent or Justin. Posts to their HCS inbound topic (on-chain) and writes to Supabase inbox (fast-read). Use for: blocked issues, review requests, FYIs, feedback, questions.",
"inputSchema": {
"to_agent": "string — agent slug or 'ALL' or 'justin'",
"message_type": "string — 'feedback' | 'fyi' | 'review.request' | 'task.note' | ...",
"subject": "string",
"payload": "object — structured content",
"ref_id": "string — entity topic_id",
"ref_type": "string — task | phase | stage | project | agent",
"priority": "integer — 1-5"
}
}
``
Flow: send_message → post to recipient's inbound_topic_id on HCS → listener materializes to inbox on next cycle → recipient's runner sees it on next poll.
Fast-path alternative: For urgent messages (priority ≤ 2), send_message also writes directly to Supabase inbox in addition to HCS, so recipient sees it within seconds not minutes.
---
Post a note to an entity topic. Creates on-chain commentary thread per entity.
``json
{
"name": "post_note",
"description": "Post a note to a task, phase, stage, or project topic. Creates permanent on-chain record. Notified agents receive inbox message immediately.",
"inputSchema": {
"entity_id": "string — topic_id (0.0.XXXXX)",
"entity_type": "string — task | phase | stage | project",
"note": "string — markdown content",
"notify": "array of agent slugs to notify"
}
}
``
---
1. Migration supabase/migrations/021_agent_topic_columns.sql — add inbound_topic_id, outbound_topic_id to agent_definitions
2. Migration supabase/migrations/020_inbox.sql — inbox table (already written)
3. Script scripts/create-agent-topics.js — create HCS topics for all agents, update Supabase, republish HCS-11 profiles
4. Listener — add handle_agent_topics(), send_inbox() helper, entity event routing
5. hedera-tools.js — add send_message and post_note tools
6. Justin's inbox — node scripts/inbox.js CLI reader
---