Patch Topology
patch_topologyUpdate work and annotations or record a completion. Describe before composing unfamiliar operations.
Input Schema
| Name | Required | Description | Default |
|---|---|---|---|
| op | No | Required when action='patch' or 'validate'. Ignored when action='describe'. work_patch: partial merge on an existing item by `what` across all groups — update goal/state/next/assigned_to, append refs — without resending the item (fields per topology 3.0). The primary keep-it-current op: `state` is the thread's current standing (renamed from detail), `next` its own next move — keep both current, they replace the retired session summary. work_upsert: create an item, or fully reshape one (match on `what`) in work.{active|paused|blocked|done}. Items carry goal/state/next/refs[]/annotations[] and assigned_to — advisory deck-handle label naming the owning deck. This is the reshape op the over_shape boot flag points at. work_transition: move an existing item by `what` to a different group. work_remove: remove an item by `what` from any group. work_annotate: append a typed annotation to a work item's annotations[] (renamed from note_append, topology 3.1.0). did_append: record a completion into the did trail (its own table since topology 3.0); append-only, attribution on every entry, optional work_ref to the closed item, nudges if that item is still open. Retired (topology 3.0): summary_set + session_mode_set (slots dissolved) and client op_append (audit is worker-stamped at source). Work items are pointers plus current standing, never documents (topology 3.2): goal/state/next are capped at 250/600/250 chars and refs[] at 8 typed pointers; all three write ops reject over-cap rather than truncating, and check only what you send. | |
| action | Yes | Required. describe: returns the contract envelope (op catalogue, per-op payloads, server-side caps, parallel-safe property) — use as a pre-flight before composing a patch. validate: pre-send check — runs required-field + char-cap validation on a candidate op + payload WITHOUT writing; returns { valid, missing_required[], over_cap: [{field, len, cap}], not_checked? } so a long compose is checked in one cheap call instead of paying a rejected write to learn a length. State-dependent checks (item existence, group capacity) still run at write time. patch: applies one op against state. Pre-flight pattern: describe → choose op → (validate when composing long) → patch. | |
| payload | No | Required when action='patch' or 'validate' (validate takes the same candidate payload the patch would send). Ignored when action='describe'. Op-specific payload. work_patch: {what, patch: {goal?, state?, next?, assigned_to?, refs_append?: [...]}} — partial merge on the item matched by `what` (any group); provided fields update, untouched fields survive; refs_append appends to refs[] (exact duplicates skipped with a warning); empty or unknown-field patches are rejected with the patchable field list (`detail` rejects — renamed to `state`). `state` REPLACES — write the new standing from scratch, never the old text plus a layer; goal/state/next reject over 250/600/250 chars. Each appended ref is {kind, label?, locator}: kinds are knowledge | skill | signal | connection | url | file, the locator is the one its kind needs, and nothing else is accepted; the merged refs[] caps at 8. Stamps item.updated (the freshness clock behind the boot hygiene flags). assigned_to soft-validates like work_upsert. work_upsert: {group: 'active'|'paused'|'blocked'|'done', item: {what, goal?, state?, next?, refs?: [{kind, label?, <locator>}], annotations?, assigned_to?, ...}} — `detail` is rejected (renamed to `state`, topology 3.0); blocked requires `blocker`; done auto-stamps `closed` if missing; item.updated stamps on every upsert. Caps: active/paused 5, blocked 3, done 5 — over-cap on active/paused/blocked is REJECTED with a make-room hint (work items are never silently evicted); done alone trims oldest-by-closed. assigned_to is an advisory deck handle: soft-validated against the container's decks, mismatch warns in the envelope, never rejects. The sent item is checked against the work-item caps and ref shape; knowledge/skill/signal refs must resolve in this container, and a connection ref naming nothing the container declared warns and lands. work_transition: {what, to: 'active'|'paused'|'blocked'|'done', patch?: {...}} — transitioning to blocked requires `blocker` in patch; moving into a full active/paused/blocked group is REJECTED (make room first — the source item stays put), done trims oldest-by-closed. Only the patch you send is checked against the caps and ref shape — the stored item's other fields are left alone, so a bare transition of a legacy over-shape item passes. work_remove: {what}. work_annotate: {what, type, text: string|string[], actor?} — `what` matches the work item's `what` field (the same item key as work_patch/work_transition/work_remove); `type` is open vocabulary (gotchas, choice, observation, shipped, attempt, risk, …); `text` is the annotation content, aligned with did_append. Char caps (150 chars/bullet, 900 total) are REJECTED over-cap with a field+limit message (never truncated) — tighten and resend; the 6-bullet cap drops oldest. Per-item cap 10: an over-cap append succeeds and RETURNS the evicted annotation in evicted_annotations (annotations are memory, never silently destroyed) — graduate it to knowledge or fold it into the item if it still matters. did_append: {text, work_ref?, by?} — record a COMPLETION into the did trail (topology 3.0): `text` ≤250 chars (rejected over-cap); optional `work_ref` (a work item's `what` this completion closes) and `by` (your deck handle). Append-only, retention keep-everything; boot ships a tail of 8, read_topology pages deeper (trail='did'). A work_ref still in active/paused returns a nudge. Use for finished things — in-flight standing stays on the work item's `state` via work_patch. | |
| contract | No | Help mode — return the complete contract with no operation performed. | |
| container_id | Yes | Container ID — required. Per-container Durable Object isolate serialises writes — parallel patch_topology calls for the same container queue inside the DO; calls for different containers run in independent isolates. |