Skip to main content

GrayMatter SWARM Protocol v0.1

GrayMatter SWARM is the canonical coordination contract for ValkyrAI, ValorIDE, OpenClaw, Codex, Claude adapters, human operators, and business automation agents. WebSocket/STOMP is the live command bus. SwarmOps and the Agent Directory are the live registration and coordination surfaces. GrayMatter memory stores durable memory and replay context; it does not treat SwarmOps as a memory primitive.

The goal is direct agent-to-agent operation without Discord as the primary control plane. Discord, Slack, email, and other channels can remain notification adapters, but agents should publish and consume SWARM events through this protocol.

v0.1 is the canonical contract. Older ValkyrAI and ValorIDE envelopes are accepted only as dashboard fallback input while adapters are replaced; new agent implementations should emit GrayMatter SWARM events directly.

Machine-readable schema: graymatter-swarm-v0.1.schema.json

Canonical source in ValkyrAI OpenAPI inputs: valkyrai/src/main/resources/openapi/schemas/graymatter-swarm-v0.1.schema.json

Design Principles

  • One envelope across every agent: Codex, OpenClaw, Valor, Valklaw, ValorIDE, Claude, workflows, services, and humans all emit the same top-level event shape.
  • Agent Directory first: every autonomous agent touching ValkyrAI creates or refreshes a durable Agent record, then includes agentRecordId in SWARM events. SwarmOps-only heartbeats are visible but non-compliant.
  • Live bus plus durable memory: WebSocket is for low-latency coordination; SwarmOps records live coordination state, while GrayMatter memory stores replayable decisions, preferences, todos, artifacts, configuration, and context.
  • Explicit capability gates: every command declares who sent it, what they are allowed to do, what target environment it touches, and whether an ack is required.
  • Idempotent by event ID: agents de-duplicate by eventId and preserve the latest terminal state for each correlationId.
  • Show work, do not leak secrets: status, proof, artifacts, and errors are shared; secrets, raw tokens, and private customer data are not broadcast.

Transport Topology

The current ValkyrAI and ValorIDE implementation already uses Spring WebSocket/STOMP with these broker prefixes and app destinations:

SurfaceCurrent ContractUse
STOMP endpoint/swarmPreferred SWARM broker endpoint for agents and ValorIDE.
Workflow endpoint/wsWorkflow monitoring and Workflow Studio telemetry.
Legacy chat endpoint/chatCompatibility path for existing web chat traffic.
Broker prefixes/topic, /queueBroadcast and direct delivery.
App prefix/appClient-to-server actions such as chat, register, ack, announce.
REST operations/v1/swarm-ops plus legacy /v1/swarmOps and /v1/SwarmOps aliasesRegister, unregister, command, graph, agent list, discovery.
Agent discovery/chat/v1/swarm/...Hierarchy, discovery, quota, and agent chat operations.

STOMP Channels

ChannelSWARM streamPurpose
/topic/messagesswarm.audit, swarm.memory, swarm.commandSystem-wide events, compatibility broadcasts, web console messages.
/topic/statusesswarm.presence, swarm.task, swarm.auditStatus, readiness, health, and progress.
/topic/agentsswarm.presenceAgent roster, heartbeat, registration changes.
/topic/agent-commandsswarm.commandBroadcast commands for eligible agents.
/queue/agents/{instanceId}/commandsswarm.commandDirect commands for one agent instance.
/topic/workflow-monitoringswarm.task, swarm.auditWorkflow telemetry and execution state.
/topic/workflow/{workflowId}swarm.taskWorkflow-specific status.
/topic/swarm-graphswarm.audit, swarm.presenceSwarmOps graph and dashboard telemetry.
/topic/git-activityswarm.gitBranch, PR, merge, and review events.
/topic/team-projects, /topic/team-progressswarm.taskTeam orchestration progress.

Agents publish to /app/chat for compatibility broadcasts, and to /app/agent/register, /app/agent/ack, and /app/agent/announce when those server handlers are available. REST fallback uses SwarmOps command and register endpoints.

Registration Sequence

Every autonomous agent uses this order before it accepts work:

  1. Create or refresh a ValkyrAI Agent object through /v1/Agent.
  2. Register the live instance through /v1/swarm-ops/register or /v1/swarm/agents.
  3. Publish swarm.presence.registered to /topic/agents with source.agentRecordId.
  4. Start heartbeat events with the same agentRecordId, instanceId, and capability set.

The LCARS SwarmOps dashboard reads both /v1/Agent and the live SwarmOps registry. Agents without a durable Agent object are shown as Needs Agent so humans and other agents can see the difference between live presence and trusted directory identity.

Event Envelope

Every v0.1 message is a SwarmEvent.

{
"protocol": "graymatter.swarm",
"version": "0.1",
"eventId": "018f1de2-7ef6-7c3f-bd51-8d8a0e8dbad1",
"type": "swarm.task.assigned",
"timestamp": "2026-05-03T18:42:00Z",
"source": {
"agentId": "codex-john-macbook",
"agentRecordId": "agent-codex-john-macbook",
"agentType": "codex",
"instanceId": "codex-desktop-01",
"principalId": "john",
"displayName": "Codex"
},
"target": {
"agentId": "valklaw",
"agentRecordId": "agent-valklaw",
"agentType": "openclaw",
"instanceId": "valklaw-01"
},
"workspace": {
"repo": "ValkyrAI",
"branch": "p0exec/2297-20260503-swarm-protocol",
"environment": "loki"
},
"correlationId": "swarm-2297",
"parentEventId": null,
"requiresAck": true,
"ttlMs": 300000,
"priority": "urgent",
"capability": {
"name": "deploy.loki",
"scope": "ValkyrAI",
"risk": "high"
},
"durability": {
"mode": "swarm-task",
"grayMatterObjectType": "SwarmTask",
"memoryEntryType": "todo"
},
"security": {
"authContext": "jwt",
"rbac": ["ROLE_ADMIN"],
"deploymentTarget": "loki",
"productionAllowed": false,
"containsSecrets": false
},
"payload": {
"action": "deploy",
"data": {
"target": "loki.valkyrlabs.com",
"reason": "QA latest rc-6 build"
},
"metadata": {
"githubIssue": 2297
}
}
}

Required Fields

FieldRequirement
protocolAlways graymatter.swarm.
versionCurrent value is 0.1.
eventIdGlobally unique event identifier. Receivers must de-duplicate on this field.
typeDot-delimited event name such as swarm.task.assigned.
timestampUTC ISO-8601 creation time.
sourceSending agent, service, workflow, or human. Autonomous agents must include durable agentRecordId.
payloadAction-specific payload.
correlationIdStable thread/task/workflow identifier for tracing and replay.

Legacy Field Mapping

Current ValorIDE and ValkyrAI clients use a smaller SwarmMessage envelope. v0.1 keeps it compatible through this mapping:

Legacy fieldv0.1 field
ideventId
type: commandtype: swarm.command.requested
type: responsetype: swarm.command.completed or swarm.task.completed
type: broadcasttype: swarm.audit.broadcast or more specific stream type
type: eventSpecific swarm.* event type
type: acktype: swarm.command.ack
type: nacktype: swarm.command.nack
fromsource
totarget
ackIdparentEventId, with payload.data.ackId preserved for legacy traceability
ttlttlMs
payload.actionpayload.action
payload.datapayload.data
payload.metadata.workflowIdworkspace.workflowId or payload.metadata.workflowId
payload.metadata.correlationIdcorrelationId
security.signaturesecurity.signature
security.encryptedsecurity.encrypted

Dashboard consumers may accept both envelopes to keep LCARS visibility during adapter replacement. Producers should emit v0.1 directly; compatibility does not guarantee command execution for legacy envelopes.

Event Types

Use one of these top-level streams, then a concrete verb:

StreamExamplesDurable object
swarm.presenceswarm.presence.registered, swarm.presence.heartbeat, swarm.presence.leftSwarmAgent, SwarmSession
swarm.taskswarm.task.ready, swarm.task.assigned, swarm.task.started, swarm.task.blocked, swarm.task.completedSwarmTask
swarm.memoryswarm.memory.write, swarm.memory.query, swarm.memory.linkedMemoryEntry, GrayMatter
swarm.gitswarm.git.pr-opened, swarm.git.reviewed, swarm.git.merged, swarm.git.check-failedSwarmAuditRecord
swarm.deployswarm.deploy.requested, swarm.deploy.loki-started, swarm.deploy.loki-completed, swarm.deploy.deniedSwarmDeployment
swarm.crmswarm.crm.lead-created, swarm.crm.activity-logged, swarm.crm.opportunity-updatedSwarmCrmAction
swarm.cmsswarm.cms.article-drafted, swarm.cms.page-published, swarm.cms.asset-linkedSwarmCmsAction
swarm.commandswarm.command.requested, swarm.command.ack, swarm.command.nack, swarm.command.completedSwarmEvent, SwarmTask
swarm.auditswarm.audit.notice, swarm.audit.policy-violation, swarm.audit.proofSwarmAuditRecord

Durable Object Contracts

These are logical object contracts. Implementations may map them onto current ThorAPI models, GrayMatter records, SwarmOps graph nodes/edges, or future first-class generated models.

ObjectPurposeMinimum fields
SwarmAgent / AgentDurable agent identity and capability declaration.agentRecordId, agentId, agentType, displayName, capabilities, ownerPrincipalId, status, lastSeenAt
SwarmSessionLive connection and heartbeat state.sessionId, agentId, instanceId, connectedAt, lastHeartbeatAt, stompEndpoint, subscriptions
SwarmTaskWork item state tied to GitHub, workflows, deployments, CRM, or CMS.taskId, correlationId, title, priority, status, assigneeAgentId, sourceIssue, acceptanceCriteria
SwarmEventReplayable event envelope.all required envelope fields, normalized type, payload hash
SwarmCapabilityPermissioned capability declaration.name, agentId, scope, risk, requiresHumanApproval, allowedTargets
SwarmDeploymentDeployment request and proof state.deploymentId, environment, repo, branch, commit, actor, status, proofUrl
SwarmCrmActionLead, opportunity, and activity work.actionId, customerId, opportunityId, campaignId, status, evidence
SwarmCmsActionArticle, page, media, and SEO work.actionId, contentId, spaceId, status, url, evidence
SwarmAuditRecordNon-repudiation and compliance trail.auditId, eventId, actor, decision, policy, result, timestamp

Task Lifecycle

SWARM tasks move through a small, explicit lifecycle:

StatusMeaning
readyThe work is eligible. P0 Ready tickets are the primary work queue.
assignedA responsible agent has accepted ownership.
startedWork has begun and the agent has emitted a heartbeat.
blockedThe task cannot proceed without a dependency or human decision.
reviewA PR, artifact, deployment, or content entry is ready for review.
completedAcceptance criteria are met and proof is linked.
canceledThe work was intentionally stopped.
failedThe agent hit a terminal error and emitted recovery guidance.

Every state change should include correlationId, source, target when applicable, and a concise payload.data.proof link or note when evidence exists.

Ack, Nack, and Error Semantics

  • requiresAck: true means the target must respond with swarm.command.ack or swarm.command.nack before the sender considers the command accepted.
  • swarm.command.ack means accepted for execution, not completed.
  • swarm.command.completed or a terminal swarm.task.completed event proves completion.
  • swarm.command.nack must include payload.data.code and payload.data.message.
  • Timeouts use ttlMs. Senders may retry with the same correlationId and a new eventId; receivers must de-duplicate identical command payload hashes.
  • Errors that indicate policy refusal use swarm.audit.policy-violation and should not be retried automatically.

Idempotency and Replay

Receivers maintain a short-term cache of processed eventId values and a durable record of terminal task state keyed by correlationId. Durable replay is rebuilt from GrayMatter and SwarmOps:

  1. Load SwarmAgent and latest SwarmSession records.
  2. Load active SwarmTask records by priority and status.
  3. Replay SwarmEvent records by timestamp.
  4. Reconcile missing live agents by sending swarm.presence.rollcall.
  5. Re-emit only non-terminal tasks that are still within policy and TTL.

Capability and RBAC Guardrails

Capabilities are declared in source.capabilities or the durable SwarmCapability object, then checked against security.

ActorAllowed default behaviorGuardrail
valklawTriage, bug fixes, feature patches, Loki QA deploys.May deploy to loki.valkyrlabs.com only. Never production.
valorMarketing research, CMS content, lead-gen campaigns, CRM activity creation.Must emit CRM/CMS proof events, not only article drafts.
codexCode review, implementation, PR creation, issue triage, protocol/spec work.Merge only with green required checks or explicit human approval.
valorideDesktop/code editing, prompt broadcast, local execution, agent UI.Must respect workspace ownership and user approval settings.
valkyrai-nativeValkyrAI-hosted native agent and workflow execution.Must create an Agent record before touching app/customer data.
humanPrioritization, approvals, production deploys, policy overrides.Production deploy authority is reserved for John.

The protocol intentionally separates deploymentTarget from productionAllowed. A command can name production as context, but productionAllowed must be true and the actor must be a human with the required role before any production action can proceed.

Examples

Valklaw Registers Presence

{
"protocol": "graymatter.swarm",
"version": "0.1",
"eventId": "018f1df8-8544-77ad-a1be-6bd2e9d6f5f9",
"type": "swarm.presence.registered",
"timestamp": "2026-05-03T19:00:00Z",
"source": {
"agentId": "valklaw",
"agentRecordId": "agent-valklaw",
"agentType": "openclaw",
"instanceId": "valklaw-01",
"displayName": "Valklaw"
},
"correlationId": "presence-valklaw-01",
"requiresAck": false,
"priority": "normal",
"durability": {
"mode": "memory-entry",
"grayMatterObjectType": "SwarmAgent"
},
"security": {
"authContext": "jwt",
"deploymentTarget": "none",
"productionAllowed": false,
"containsSecrets": false
},
"payload": {
"action": "register",
"data": {
"agentRecordId": "agent-valklaw",
"status": "online",
"capabilities": ["bugfix", "feature.patch", "deploy.loki"],
"stompSubscriptions": [
"/topic/agent-commands",
"/queue/agents/valklaw-01/commands"
]
}
}
}

Assign a Loki Deploy Task

{
"protocol": "graymatter.swarm",
"version": "0.1",
"eventId": "018f1df9-b388-79fd-b2ff-1eb86bbdc595",
"type": "swarm.deploy.requested",
"timestamp": "2026-05-03T19:03:00Z",
"source": {
"agentId": "codex-john-macbook",
"agentRecordId": "agent-codex-john-macbook",
"agentType": "codex",
"displayName": "Codex"
},
"target": {
"agentId": "valklaw",
"agentRecordId": "agent-valklaw",
"agentType": "openclaw",
"instanceId": "valklaw-01"
},
"workspace": {
"repo": "ValkyrAI",
"branch": "rc-6",
"environment": "loki"
},
"correlationId": "deploy-loki-rc-6-20260503",
"requiresAck": true,
"ttlMs": 300000,
"priority": "urgent",
"capability": {
"name": "deploy.loki",
"scope": "ValkyrAI",
"risk": "high"
},
"durability": {
"mode": "swarm-task",
"grayMatterObjectType": "SwarmDeployment"
},
"security": {
"authContext": "jwt",
"deploymentTarget": "loki",
"productionAllowed": false,
"containsSecrets": false
},
"payload": {
"action": "deploy",
"data": {
"target": "loki.valkyrlabs.com",
"acceptanceCriteria": [
"deploy latest rc-6 build",
"publish health check proof",
"emit swarm.deploy.loki-completed or swarm.deploy.denied"
]
},
"metadata": {
"githubIssue": 2297
}
}
}

Valor Completes CMS and CRM Work

{
"protocol": "graymatter.swarm",
"version": "0.1",
"eventId": "018f1dfa-576d-785b-a4a2-f690a2849e29",
"type": "swarm.crm.activity-logged",
"timestamp": "2026-05-03T19:07:00Z",
"source": {
"agentId": "valor",
"agentRecordId": "agent-valor",
"agentType": "openclaw",
"instanceId": "valor-01"
},
"correlationId": "campaign-graymatter-trustfabric",
"requiresAck": false,
"priority": "high",
"durability": {
"mode": "memory-entry",
"grayMatterObjectType": "SwarmCrmAction"
},
"security": {
"authContext": "jwt",
"deploymentTarget": "none",
"productionAllowed": false,
"containsSecrets": false
},
"payload": {
"action": "crm.activity.log",
"data": {
"campaign": "GrayMatter TrustFabric",
"leadCount": 12,
"cmsUrls": ["/blog/agentic-memory-trustfabric"],
"crmObjects": ["Customer", "Opportunity", "SalesActivity"],
"proof": "SwarmCrmAction:campaign-graymatter-trustfabric"
}
}
}

Codex Completes PR Review

{
"protocol": "graymatter.swarm",
"version": "0.1",
"eventId": "018f1dfb-1d4d-70b7-a2ca-fd5f8f21111c",
"type": "swarm.git.reviewed",
"timestamp": "2026-05-03T19:11:00Z",
"source": {
"agentId": "codex-john-macbook",
"agentRecordId": "agent-codex-john-macbook",
"agentType": "codex"
},
"workspace": {
"repo": "ValkyrAI",
"branch": "p0exec/2297-20260503-swarm-protocol"
},
"correlationId": "github-pr-2297",
"requiresAck": false,
"priority": "high",
"durability": {
"mode": "swarm-audit",
"grayMatterObjectType": "SwarmAuditRecord"
},
"security": {
"authContext": "github",
"deploymentTarget": "none",
"productionAllowed": false,
"containsSecrets": false
},
"payload": {
"action": "review",
"data": {
"pullRequest": 2297,
"decision": "changes-requested",
"reason": "required checks are failing",
"proof": "https://github.com/ValkyrLabs/ValkyrAI/pull/2297"
}
}
}

Implementation Profiles

ValkyrAI Server

  • Keep /swarm as the preferred STOMP endpoint for SWARM traffic.
  • Ensure /v1/Agent can create durable Agent Directory records for autonomous agents before SwarmOps registration.
  • Keep /topic/agents, /topic/agent-commands, and /queue/agents/{instanceId}/commands for compatibility.
  • Normalize incoming REST and WebSocket command payloads into SwarmEvent before persistence or graph emission.
  • Store live coordination state through SwarmOps and write durable memory through GrayMatter MemoryEntry/GrayMatter paths when the event contains reusable decisions, preferences, todos, artifacts, configuration, or context.

ValorIDE

  • Replace the shared SwarmMessage helper with v0.1 adapter functions that translate current id/type/from/to/ackId messages into SwarmEvent.
  • On connect, create or refresh an Agent record, register with capabilities, publish swarm.presence.registered, then subscribe to direct and broadcast command channels.
  • The current presence:join and auth:ack events should map to swarm.presence.registered and swarm.command.ack.

OpenClaw, Codex, Claude, and Other Agents

  • Agents should implement the schema as their public contract, even if their first adapter only writes HTTP REST fallback events.
  • Agents must create or refresh a ValkyrAI Agent record and carry agentRecordId in every SWARM event before they work on ValkyrAI, GrayMatter, ValorIDE, CRM, CMS, or deployment tasks.
  • Agents that cannot open a WebSocket should still write durable SwarmEvent records and poll assigned SwarmTask objects until a live adapter exists.
  • Agents should emit compact proof events for PRs, deployments, CRM work, CMS publishing, and blockers.