Private agent messages #
Purpose #
Private agent messages let one explicitly admitted agent address a thought stream agent without impersonating a human, forging a channel update, or editing trusted identity/memory documents. The first route is Co → Stream. It is a local operator-authorized capability over Jazz, not a public protocol, generic RPC endpoint, or Telegram bot-to-bot workaround.
Event contracts #
stream.thought.source.agent.message@1 is the canonical inbound message.
sourceKindisagent.- The source is exactly
agent-message:<senderAgentId>and is owned by that sender/producer. - The actor is exactly
agent:<senderAgentId>. - Privacy is
sensitive. - The strict payload contains
messageId,threadId,senderAgentId,recipientAgentId, and boundedtext. - Envelope
externalIdequalsmessageId;correlationIdequalsthreadId; idempotency binds sender, recipient, thread, and message id. - The sender and recipient ids are lowercase stable agent ids, not display names.
stream.thought.derived.agent.message@1 is the canonical response.
- It is emitted only by the declaration named as the source message recipient.
- It preserves source root, parent input event, correlation/thread id, sensitive privacy, completed run/execution identity, input source sequence, exact sender/recipient reversal, output-contract identity, validated structured output, model evidence, and declaration fingerprint.
- It has no Telegram delivery eligibility. Its durable event is the response receipt.
- A failed/blocked/abandoned run remains terminal execution evidence; no response event is synthesized.
Stream endpoint #
The first endpoint declaration is stream-agent-conversation.
- It subscribes only to
stream.thought.source.agent.message@1fromagent-message:cowithreplay: now. - It accepts only messages whose
recipientAgentIdequals its declaration id and whose sender/source/actor tuple is exact. - It shares Stream's operator-selected
identity.mdandmemory.mddocuments, model, and sandbox boundary, but has its own declaration, prompt, inference budget, progress, and output events. - It has no tools, proposals, external actions, Telegram dispatcher route, or learned adapter.
- The prompt states that the current correspondent is Co rather than Cameron. Inter-agent history cannot become operator policy.
Conversation reconstruction #
agent-conversation context is thread-local and evidence-backed.
- Select source messages with the same exact source, sender, recipient, and thread at or before the current event.
- Admit a prior assistant turn only when one completed run of the current endpoint declaration names exactly one valid
stream.thought.derived.agent.message@1output rooted in that source message. - Preserve chronological user/assistant roles. The current source message is the final prompt and appears once.
- Exclude other senders, recipients, threads, declaration ids, failed outputs, malformed routes, and later events.
- Apply declaration event/character limits after reconstruction. The manifest records bounded provenance, route, thread, omitted event ids, and exact declaration/output authority; ids do not enter model-visible text.
- A retry reuses the immutable context snapshot.
Inter-agent history is separate from Cameron's Telegram history and from Telegram compaction. Neither surface contaminates the other.
Local send/wait/read capability #
agent-send is the narrow operator-local producer and receipt reader.
- It requires explicit
--from,--to,--thread,--message-id, and--filearguments. - Message text is read from an owner-controlled file, never a shell argument, and is bounded before append.
- V1 admits only the exact route
co→stream-agent-conversation; broader routing requires a new reviewed policy. - Repeating the same identity is idempotent only when the exact route/thread/text match; divergent reuse fails closed.
- Without wait flags, output is content-dark ids/status.
--wait-secondspolls only the exact trigger execution.--show-responserequires--acknowledge-sensitive-private; only a contract-valid completed response body is printed.- The command reads no channel or provider credential, contacts no external service, and does not run inference itself. The independent consumer owns execution.
Authority and security #
- There is no generic event injection endpoint.
- The CLI cannot claim another sender, target arbitrary declarations, publish, send Telegram, edit memory, grant tools, or mutate prior events.
- Model output cannot create another source message or continue recursively by itself.
- Source and response text remain sensitive in Jazz/context snapshots and are forbidden from public projections, logs, incident alerts, training export, and Telegram delivery absent a later explicit reviewed policy.
- The Letta
messaging-agentscapability and Telegram Bot API are not part of this route.
Proof #
Credential-dark tests must prove event schema/route rejection, idempotent and divergent message identity, exact thread reconstruction, completed-output admission, failed/foreign/thread-crossing exclusion, context bounds, retry-stable snapshots, response lineage, no Telegram eligibility, CLI privacy gates, and send/wait/read behavior against temporary Jazz databases and deterministic runners.
Live activation requires installing the endpoint declaration/prompt, restarting the exact consumer process, verifying declaration/progress readback, then sending one real Co-authored message with the bounded CLI. Completion means source event, run, typed response event, and CLI readback receipts all exist. It does not require or permit a Telegram message.