Skip to content

Commit bc73334

Browse files
Your Nameclaude
andcommitted
feat(server): truth-kernel hardening Wave 11 -- source() pagination + unified continuation state field
Wave 11 (items 1 and 3 of the kept roadmap; item 4 -- a multi-agent dogfood benchmark -- is a measurement exercise, not a code change, and is deliberately not attempted here; item 2 was already dropped as unnecessary since native-Edit + diff_impact already covers it): - item 1 (response budget): opt-in max_lines/resume_from_line params on source(), truncated/omitted_lines/next_cursor on the response -- directly closes the cited overflow case (a single source() call with no way to ask for less). etag/line_start/line_end always cover the FULL range regardless of pagination -- range-identity, not tied to how much was rendered. Also fixes a real bug found while wiring this up: with_line_gutters always numbered from the symbol's start line even under pagination, which would have mislabeled every paginated response's line numbers. - item 3 (unified continuation state): every ToolOutcome/ResolvedOutcome response now carries state: "ready" | "needs_context" | "needs_human_review" | "needs_verification" | "blocked", added once in the two shared wrapper constructors (classify_error_state in outcome.rs) rather than at any of the ~150 individual error_detail() call sites. All 74 error codes the codebase currently emits get an explicit classification -- not derived from `recoverable` alone, which turned out to be an unreliable proxy (most INVALID_*/*_REQUIRED codes are recoverable: false yet are exactly "fix your params and retry"). 2 new regression tests prove actual truncation + resume-from-cursor + unbounded-is-unaffected, and prove state distinguishes ready vs needs_context on a real response. All 40 __toolsnaps__ schema snapshots regenerated (state is now a required property on every tool's output). 1745 tests green, clippy/fmt clean. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
1 parent c44c0c1 commit bc73334

43 files changed

Lines changed: 900 additions & 94 deletions

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

crates/calm-server/src/__toolsnaps__/batch_status.snap

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -82,7 +82,15 @@
8282
]
8383
}
8484
},
85+
"required": [
86+
"state"
87+
],
88+
"type": "object",
8589
"properties": {
90+
"state": {
91+
"description": "Wave 11 (item 3, \"unified continuation state machine\"): present on\nevery response regardless of success/error -- `\"ready\"` on success,\nor one of `needs_context`/`needs_human_review`/`needs_verification`/\n`blocked` on error (see `classify_error_state`'s own doc comment).\nLets an agent dispatch on ONE top-level field instead of\nmaintaining its own per-`code` remediation table across ~70\ndistinct codes.",
92+
"type": "string"
93+
},
8694
"error": {
8795
"anyOf": [
8896
{
@@ -134,8 +142,7 @@
134142
}
135143
]
136144
}
137-
},
138-
"type": "object"
145+
}
139146
},
140147
"annotations": {
141148
"readOnlyHint": true,

crates/calm-server/src/__toolsnaps__/callees.snap

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -272,7 +272,15 @@
272272
]
273273
}
274274
},
275+
"required": [
276+
"state"
277+
],
278+
"type": "object",
275279
"properties": {
280+
"state": {
281+
"description": "See `ToolOutcome::state`'s own doc comment -- same contract, plus\n`ambiguous`/`not_found` both map onto `needs_context` (the caller\nneeds one more piece of information: which candidate, or a\ndifferent query).",
282+
"type": "string"
283+
},
276284
"error": {
277285
"anyOf": [
278286
{
@@ -401,8 +409,7 @@
401409
}
402410
]
403411
}
404-
},
405-
"type": "object"
412+
}
406413
},
407414
"annotations": {
408415
"readOnlyHint": true,

crates/calm-server/src/__toolsnaps__/callers.snap

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -269,7 +269,15 @@
269269
]
270270
}
271271
},
272+
"required": [
273+
"state"
274+
],
275+
"type": "object",
272276
"properties": {
277+
"state": {
278+
"description": "See `ToolOutcome::state`'s own doc comment -- same contract, plus\n`ambiguous`/`not_found` both map onto `needs_context` (the caller\nneeds one more piece of information: which candidate, or a\ndifferent query).",
279+
"type": "string"
280+
},
273281
"error": {
274282
"anyOf": [
275283
{
@@ -405,8 +413,7 @@
405413
}
406414
]
407415
}
408-
},
409-
"type": "object"
416+
}
410417
},
411418
"annotations": {
412419
"readOnlyHint": true,

crates/calm-server/src/__toolsnaps__/dependencies.snap

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -86,7 +86,15 @@
8686
]
8787
}
8888
},
89+
"required": [
90+
"state"
91+
],
92+
"type": "object",
8993
"properties": {
94+
"state": {
95+
"description": "Wave 11 (item 3, \"unified continuation state machine\"): present on\nevery response regardless of success/error -- `\"ready\"` on success,\nor one of `needs_context`/`needs_human_review`/`needs_verification`/\n`blocked` on error (see `classify_error_state`'s own doc comment).\nLets an agent dispatch on ONE top-level field instead of\nmaintaining its own per-`code` remediation table across ~70\ndistinct codes.",
96+
"type": "string"
97+
},
9098
"error": {
9199
"anyOf": [
92100
{
@@ -142,8 +150,7 @@
142150
}
143151
]
144152
}
145-
},
146-
"type": "object"
153+
}
147154
},
148155
"annotations": {
149156
"readOnlyHint": true,

crates/calm-server/src/__toolsnaps__/diff_impact.snap

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -160,7 +160,15 @@
160160
]
161161
}
162162
},
163+
"required": [
164+
"state"
165+
],
166+
"type": "object",
163167
"properties": {
168+
"state": {
169+
"description": "Wave 11 (item 3, \"unified continuation state machine\"): present on\nevery response regardless of success/error -- `\"ready\"` on success,\nor one of `needs_context`/`needs_human_review`/`needs_verification`/\n`blocked` on error (see `classify_error_state`'s own doc comment).\nLets an agent dispatch on ONE top-level field instead of\nmaintaining its own per-`code` remediation table across ~70\ndistinct codes.",
170+
"type": "string"
171+
},
164172
"error": {
165173
"anyOf": [
166174
{
@@ -214,8 +222,7 @@
214222
}
215223
]
216224
}
217-
},
218-
"type": "object"
225+
}
219226
},
220227
"annotations": {
221228
"readOnlyHint": true,

crates/calm-server/src/__toolsnaps__/edit_context.snap

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -415,7 +415,15 @@
415415
]
416416
}
417417
},
418+
"required": [
419+
"state"
420+
],
421+
"type": "object",
418422
"properties": {
423+
"state": {
424+
"description": "See `ToolOutcome::state`'s own doc comment -- same contract, plus\n`ambiguous`/`not_found` both map onto `needs_context` (the caller\nneeds one more piece of information: which candidate, or a\ndifferent query).",
425+
"type": "string"
426+
},
419427
"error": {
420428
"anyOf": [
421429
{
@@ -590,8 +598,7 @@
590598
}
591599
]
592600
}
593-
},
594-
"type": "object"
601+
}
595602
},
596603
"annotations": {
597604
"readOnlyHint": false,

crates/calm-server/src/__toolsnaps__/edit_lines.snap

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -215,7 +215,15 @@
215215
]
216216
}
217217
},
218+
"required": [
219+
"state"
220+
],
221+
"type": "object",
218222
"properties": {
223+
"state": {
224+
"description": "Wave 11 (item 3, \"unified continuation state machine\"): present on\nevery response regardless of success/error -- `\"ready\"` on success,\nor one of `needs_context`/`needs_human_review`/`needs_verification`/\n`blocked` on error (see `classify_error_state`'s own doc comment).\nLets an agent dispatch on ONE top-level field instead of\nmaintaining its own per-`code` remediation table across ~70\ndistinct codes.",
225+
"type": "string"
226+
},
219227
"error": {
220228
"anyOf": [
221229
{
@@ -288,8 +296,7 @@
288296
}
289297
]
290298
}
291-
},
292-
"type": "object"
299+
}
293300
},
294301
"annotations": {
295302
"readOnlyHint": false,

crates/calm-server/src/__toolsnaps__/edit_symbol.snap

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -293,7 +293,15 @@
293293
]
294294
}
295295
},
296+
"required": [
297+
"state"
298+
],
299+
"type": "object",
296300
"properties": {
301+
"state": {
302+
"description": "See `ToolOutcome::state`'s own doc comment -- same contract, plus\n`ambiguous`/`not_found` both map onto `needs_context` (the caller\nneeds one more piece of information: which candidate, or a\ndifferent query).",
303+
"type": "string"
304+
},
297305
"error": {
298306
"anyOf": [
299307
{
@@ -395,8 +403,7 @@
395403
}
396404
]
397405
}
398-
},
399-
"type": "object"
406+
}
400407
},
401408
"annotations": {
402409
"readOnlyHint": false,

crates/calm-server/src/__toolsnaps__/edit_transaction_status.snap

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -60,7 +60,14 @@
6060
]
6161
}
6262
},
63+
"required": [
64+
"state"
65+
],
66+
"type": "object",
6367
"properties": {
68+
"state": {
69+
"type": "string"
70+
},
6471
"error": {
6572
"anyOf": [
6673
{
@@ -77,9 +84,6 @@
7784
"path": {
7885
"type": "string"
7986
},
80-
"state": {
81-
"type": "string"
82-
},
8387
"replay_state": {
8488
"type": [
8589
"string",
@@ -102,8 +106,7 @@
102106
}
103107
]
104108
}
105-
},
106-
"type": "object"
109+
}
107110
},
108111
"annotations": {
109112
"readOnlyHint": true,

crates/calm-server/src/__toolsnaps__/file_overview.snap

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -102,7 +102,15 @@
102102
]
103103
}
104104
},
105+
"required": [
106+
"state"
107+
],
108+
"type": "object",
105109
"properties": {
110+
"state": {
111+
"description": "Wave 11 (item 3, \"unified continuation state machine\"): present on\nevery response regardless of success/error -- `\"ready\"` on success,\nor one of `needs_context`/`needs_human_review`/`needs_verification`/\n`blocked` on error (see `classify_error_state`'s own doc comment).\nLets an agent dispatch on ONE top-level field instead of\nmaintaining its own per-`code` remediation table across ~70\ndistinct codes.",
112+
"type": "string"
113+
},
106114
"error": {
107115
"anyOf": [
108116
{
@@ -147,8 +155,7 @@
147155
}
148156
]
149157
}
150-
},
151-
"type": "object"
158+
}
152159
},
153160
"annotations": {
154161
"readOnlyHint": true,

0 commit comments

Comments
 (0)