@canonmsg/coding-agent-host
v0.10.1
Published
Shared host utilities for Canon coding-agent integrations
Readme
@canonmsg/coding-agent-host
The pieces two Canon coding-agent hosts must implement identically, factored out so they cannot drift.
Canon runs coding agents through two hosts — canon-claude (@canonmsg/claude-code-plugin) and canon-codex (@canonmsg/codex-plugin). Their runtimes are genuinely different, so most host code stays per-host. What lives here is the narrow set of behaviors that are user-visible and therefore must match: how a plan renders, how long an idle session survives, what a host says when it cannot deliver its answer.
This package exists for those hosts. It is published so they can depend on a version rather than a path; there is no reason to install it on its own.
Install
npm install @canonmsg/coding-agent-hostNode.js 18+, no runtime dependencies.
What it owns
Undeliverable finals. Both hosts hit the path where the work finished but Canon would not take the answer — a final over Canon's message byte limit, a rejected payload, an outage outlasting the retries. buildUndeliverableFinalNotice composes that sentence from per-host wording plus shared punctuation, and bounds the quoted error at FAILURE_DETAIL_MAX_CHARS (280) so the notice about an undeliverable message is not itself undeliverable. Pass partiallyDelivered: true for a chunked final whose earlier parts already landed — the reader can see text and has to be told it stops short. The chunked send itself is sendMessageWithRetryChunked in @canonmsg/core.
Plan grammar. Clients read a plan out of the block's text; there is no structured plan payload, so the text is a wire format: **Plan** over numbered steps marked [x] done, [~] in progress, [ ] still to do. renderPlanSteps is the single writer of that grammar. Each host keeps its own mapping from what its runtime reports into PlanStep[].
Idle timeout. IDLE_TIMEOUT_MS (30 minutes) — when a session loses its warm context and the next message starts cold. User-visible, so both hosts age sessions out on one schedule.
Trail-block bookkeeping. buildTrailBlockId and normalizeTrailKey spell margin block ids the same way in both hosts; boundTrailBlockMap keeps a per-turn map under MAX_TRACKED_TRAIL_BLOCKS (200). The matching rules stay per-host — they are genuinely different and folding them together would hide semantics both hosts' tests pin.
Turn artifacts. Getting a file a turn produced — a chart, a recording, a PDF — into the conversation. captureTurnArtifactSnapshot takes a pre-turn baseline of the workspace and collectTurnArtifacts diffs against it, so a turn's new or changed media is discovered wherever the agent wrote it. Bounded at TURN_ARTIFACT_MAX_FILES_PER_TURN (8) and TURN_ARTIFACT_MAX_FILE_BYTES (10 MB), with an extension allowlist.
Coding-agent reference: Coding agents on Canon
