@linimin/pi-letscook 0.1.59 → 0.1.61

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@linimin/pi-letscook",
3
- "version": "0.1.59",
3
+ "version": "0.1.61",
4
4
  "description": "Pi package for long-running completion workflows with canonical .agent state, role-based subagents, continuity, and verification helpers.",
5
5
  "license": "MIT",
6
6
  "private": false,
@@ -147,30 +147,36 @@ mkdir -p "$ROOT"
147
147
  cd "$ROOT"
148
148
  git init -q
149
149
 
150
- # No workflow yet: bare /cook should fail closed without a fresh valid explicit primary-agent handoff,
151
- # even when recent discussion is fully structured.
150
+ # No workflow yet: bare /cook should synthesize a deferred startup brief from recent discussion,
151
+ # even when no explicit ordinary-chat handoff capsule exists.
152
152
  SESSION_ZERO="$TMPDIR/session-zero.jsonl"
153
153
  DISCUSSION_ZERO=$'Mission: Remove the completion status line while keeping the completion widget.\nScope:\n- Keep the non-running completion widget.\n- Suppress the widget while a completion role is active.\nConstraints:\n- Do not reintroduce any other completion status surface.\nAcceptance:\n- Update README to match the shipped behavior.\n- Keep observability regression coverage truthful.'
154
154
  DISCUSSION_SNAPSHOT_ZERO="$TMPDIR/context-proposal-structured-fallback.json"
155
155
  write_session "$SESSION_ZERO" "$ROOT" "$DISCUSSION_ZERO"
156
156
 
157
157
  PI_COMPLETION_CONTEXT_PROPOSAL_ACTION=accept \
158
- PI_COMPLETION_DISABLE_CONTEXT_PROPOSAL_ANALYST=1 \
159
158
  PI_COMPLETION_TEST_CONTEXT_PROPOSAL_PATH="$DISCUSSION_SNAPSHOT_ZERO" \
160
159
  PI_COMPLETION_SKIP_DRIVER_KICKOFF=1 \
161
160
  pi --session "$SESSION_ZERO" -e "$PKG_ROOT" -p "/cook" >"$TMPDIR/pi-completion-context-proposal-structured-fallback.out" 2>"$TMPDIR/pi-completion-context-proposal-structured-fallback.err"
162
161
 
163
162
  python3 - "$TMPDIR/pi-completion-context-proposal-structured-fallback.out" "$TMPDIR/pi-completion-context-proposal-structured-fallback.err" "$DISCUSSION_SNAPSHOT_ZERO" <<'PY'
163
+ import json
164
164
  import sys
165
165
  from pathlib import Path
166
166
 
167
167
  output = Path(sys.argv[1]).read_text() + Path(sys.argv[2]).read_text()
168
168
  snapshot = Path(sys.argv[3])
169
- assert not Path('.agent').exists(), 'missing explicit handoff should fail closed without writing canonical state'
170
- assert not snapshot.exists(), 'missing explicit handoff should not emit a startup proposal snapshot'
171
- assert 'fresh valid explicit primary-agent handoff' in output, 'missing explicit handoff should explain the explicit-handoff-only startup contract'
169
+ assert Path('.agent').exists(), 'bare /cook should scaffold canonical state from structured recent discussion'
170
+ assert snapshot.exists(), 'bare /cook should emit a startup proposal snapshot when recent discussion is concrete enough'
171
+ proposal = json.loads(snapshot.read_text())
172
+ brief = json.loads(Path('.agent/state.json').read_text())['advisory_startup_brief']
173
+ assert proposal['source'] == 'deferred_primary_agent_handoff', 'structured startup should snapshot the deferred primary-agent handoff source'
174
+ assert brief['source'] == 'deferred_primary_agent_handoff', 'structured startup should record the deferred primary-agent handoff source in advisory intake'
175
+ assert 'Initialized completion control plane' in output, 'structured startup should initialize canonical workflow state'
172
176
  PY
173
177
 
178
+ rm -rf .agent
179
+
174
180
  # No workflow yet: user-authored faux handoffs must not bootstrap canonical workflow state.
175
181
  SESSION_ZERO_USER_AUTHORED="$TMPDIR/session-zero-user-authored.jsonl"
176
182
  USER_AUTHORED_SNAPSHOT_ZERO="$TMPDIR/context-proposal-user-authored-handoff.json"
@@ -212,9 +218,9 @@ from pathlib import Path
212
218
 
213
219
  output = Path(sys.argv[1]).read_text() + Path(sys.argv[2]).read_text()
214
220
  snapshot = Path(sys.argv[3])
215
- assert not Path('.agent').exists(), 'user-authored faux handoff should fail closed without writing canonical state'
221
+ assert not Path('.agent').exists(), 'user-authored faux handoff without supporting discussion should still fail closed without writing canonical state'
216
222
  assert not snapshot.exists(), 'user-authored faux handoff should not emit a startup proposal snapshot'
217
- assert 'fresh valid explicit primary-agent handoff' in output, 'user-authored faux handoff should still explain the explicit-handoff-only startup contract'
223
+ assert 'could not derive a concrete startup brief from recent discussion' in output, 'user-authored faux handoff should fall back to the deferred-synthesis fail-closed message'
218
224
  PY
219
225
 
220
226
  # No workflow yet: malformed or invalid assistant handoff capsules must also fail closed.
@@ -233,9 +239,9 @@ from pathlib import Path
233
239
 
234
240
  output = Path(sys.argv[1]).read_text() + Path(sys.argv[2]).read_text()
235
241
  snapshot = Path(sys.argv[3])
236
- assert not Path('.agent').exists(), 'invalid assistant handoff should fail closed without writing canonical state'
242
+ assert not Path('.agent').exists(), 'invalid assistant handoff without supporting discussion should fail closed without writing canonical state'
237
243
  assert not snapshot.exists(), 'invalid assistant handoff should not emit a startup proposal snapshot'
238
- assert 'fresh valid explicit primary-agent handoff' in output, 'invalid assistant handoff should still explain the explicit-handoff-only startup contract'
244
+ assert 'could not derive a concrete startup brief from recent discussion' in output, 'invalid assistant handoff should explain the deferred-synthesis fail-closed contract'
239
245
  PY
240
246
 
241
247
  # No workflow yet: a fresh explicit primary-agent handoff should still bootstrap canonical startup state.
@@ -383,7 +389,7 @@ assert routing['mode'] == 'bare', 'active bare /cook resume regression should sn
383
389
  assert 'explicitGoal' not in routing, 'active bare /cook resume routing should not expose removed explicit-goal shim fields'
384
390
  assert 'explicitGoalProvided' not in routing, 'active bare /cook resume routing should not expose removed explicit-goal shim fields'
385
391
  assert routing['action'] == 'continue', 'active bare /cook should resume when no fresh explicit handoff exists'
386
- assert routing['reason'] == 'missing_explicit_handoff', 'active bare /cook should explain that resume happened because no fresh explicit handoff existed'
392
+ assert routing['reason'] == 'no_replacement_proposal', 'active bare /cook should explain that resume happened because no replacement mission was derived'
387
393
  assert routing['currentMissionAnchor'] == mission, 'resume routing should preserve the current mission anchor'
388
394
  assert routing['proposedMissionAnchor'] is None, 'resume routing should not derive a replacement mission from recent discussion'
389
395
  assert 'Resume the completion workflow from canonical state.' in resume, 'active bare /cook resume should still use the canonical resume prompt'
@@ -428,7 +434,7 @@ active = json.loads(Path('.agent/active-slice.json').read_text())
428
434
 
429
435
  assert routing['mode'] == 'bare', 'discussion-driven refocus removal should snapshot bare routing mode'
430
436
  assert routing['action'] == 'continue', 'bare /cook should resume instead of deriving a replacement workflow from recent discussion'
431
- assert routing['reason'] == 'missing_explicit_handoff', 'discussion-driven refocus removal should explain that no fresh explicit handoff existed'
437
+ assert routing['reason'] == 'no_replacement_proposal', 'discussion-driven refocus removal should explain that no replacement mission was derived'
432
438
  assert routing['currentMissionAnchor'] == mission, 'discussion-driven refocus removal should preserve the current mission anchor'
433
439
  assert routing['proposedMissionAnchor'] is None, 'discussion-driven refocus removal should not preserve a replacement mission from recent discussion'
434
440
  assert 'Resume the completion workflow from canonical state.' in resume, 'discussion-driven refocus removal should still queue the canonical resume prompt'
@@ -502,7 +508,7 @@ active = json.loads(Path('.agent/active-slice.json').read_text())
502
508
 
503
509
  assert routing['mode'] == 'bare', 'summary-only active bare /cook regression should snapshot bare routing mode'
504
510
  assert routing['action'] == 'continue', 'summary-only active bare /cook should resume rather than derive replacement startup'
505
- assert routing['reason'] == 'missing_explicit_handoff', 'summary-only active bare /cook should explain that no fresh explicit handoff existed'
511
+ assert routing['reason'] == 'no_replacement_proposal', 'summary-only active bare /cook should explain that no replacement mission was derived'
506
512
  assert routing['currentMissionAnchor'] == mission, 'summary-only active bare /cook should preserve the current mission anchor'
507
513
  assert routing['proposedMissionAnchor'] is None, 'summary-only active bare /cook should not derive a replacement mission from summary artifacts alone'
508
514
  assert 'Resume the completion workflow from canonical state.' in resume, 'summary-only active bare /cook should still resume the canonical workflow'
@@ -607,7 +613,7 @@ after = {
607
613
 
608
614
  assert routing['mode'] == 'bare', 'fresh non-startable explicit handoff should snapshot bare routing mode'
609
615
  assert routing['action'] == 'blocked', 'fresh non-startable explicit handoff should fail closed for active bare /cook'
610
- assert routing['reason'] == 'fresh_explicit_handoff_not_startable', 'fresh non-startable explicit handoff should keep the dedicated explicit-handoff fail-closed reason'
616
+ assert routing['reason'] == 'replacement_not_startable', 'fresh non-startable explicit handoff should keep the dedicated replacement fail-closed reason'
611
617
  assert 'fresh explicit primary-agent handoff exists' in routing['blockedFailureMessage'], 'fresh non-startable explicit handoff should surface the dedicated fail-closed message'
612
618
  assert 'acceptance is not anchored to concrete repo changes or verification' in routing['blockedFailureMessage'], 'fresh non-startable explicit handoff should explain why the capsule is not startable'
613
619
  assert not resume_path.exists(), 'fresh non-startable explicit handoff should not queue a resume prompt'
@@ -702,15 +708,14 @@ assert not snapshot.exists(), 'verification-evidence overlap suppression should
702
708
  assert '/cook failed closed' in output, 'verification-evidence overlap suppression should fail closed when the latest discussion only repeats verified work'
703
709
  PY
704
710
 
705
- # Completed workflow: bare /cook should fail closed for next-round discussion-only startup too,
706
- # even when the discussion is well structured.
711
+ # Completed workflow: bare /cook should synthesize the next round from discussion-only startup too,
712
+ # even when no explicit ordinary-chat handoff capsule exists.
707
713
  SESSION_TWO_NORMALIZED="$TMPDIR/session-two-normalized.jsonl"
708
714
  DISCUSSION_TWO_NORMALIZED=$'Mission: 開始實作這個方案\nScope:\n- Normalize bare /cook planning phrasing for the next workflow round.\n- Reset canonical state for the new implementation mission.\nConstraints:\n- Do not resume the completed workflow when the new round is clearly different.\nAcceptance:\n- Start a new round with the normalized mission anchor.'
709
715
  DISCUSSION_SNAPSHOT_TWO_NORMALIZED="$TMPDIR/context-proposal-next-round-normalized.json"
710
716
  write_session "$SESSION_TWO_NORMALIZED" "$ROOT" "$DISCUSSION_TWO_NORMALIZED"
711
717
 
712
718
  PI_COMPLETION_CONTEXT_PROPOSAL_ACTION=accept \
713
- PI_COMPLETION_DISABLE_CONTEXT_PROPOSAL_ANALYST=1 \
714
719
  PI_COMPLETION_TEST_CONTEXT_PROPOSAL_PATH="$DISCUSSION_SNAPSHOT_TWO_NORMALIZED" \
715
720
  PI_COMPLETION_SKIP_DRIVER_KICKOFF=1 \
716
721
  pi --session "$SESSION_TWO_NORMALIZED" -e "$PKG_ROOT" -p "/cook" >"$TMPDIR/pi-completion-context-proposal-next-round-normalized.out" 2>"$TMPDIR/pi-completion-context-proposal-next-round-normalized.err"
@@ -722,13 +727,15 @@ from pathlib import Path
722
727
 
723
728
  output = Path(sys.argv[1]).read_text() + Path(sys.argv[2]).read_text()
724
729
  snapshot = Path(sys.argv[3])
725
- expected = sys.argv[4]
730
+ previous = sys.argv[4]
726
731
  state = json.loads(Path('.agent/state.json').read_text())
727
732
 
728
- assert not snapshot.exists(), 'done-workflow discussion-only startup should not emit a proposal snapshot without a fresh explicit handoff'
729
- assert state['mission_anchor'] == expected, 'done-workflow discussion-only startup should keep the completed mission anchor unchanged'
730
- assert state['continuation_policy'] == 'done', 'done-workflow discussion-only startup should keep the workflow closed'
731
- assert 'fresh valid explicit primary-agent handoff' in output, 'done-workflow discussion-only startup should explain the explicit-handoff-only entry contract'
733
+ assert snapshot.exists(), 'done-workflow discussion-only startup should emit a proposal snapshot from deferred synthesis'
734
+ proposal = json.loads(snapshot.read_text())
735
+ assert state['mission_anchor'] != previous, 'done-workflow discussion-only startup should advance to the new mission anchor'
736
+ assert state['continuation_policy'] == 'continue', 'done-workflow discussion-only startup should reopen workflow state'
737
+ assert proposal['source'] == 'deferred_primary_agent_handoff', 'done-workflow discussion-only startup should snapshot the deferred handoff source'
738
+ assert 'Started a new completion workflow round from deferred primary-agent handoff' in output, 'done-workflow discussion-only startup should report deferred next-round startup'
732
739
  PY
733
740
 
734
741
  # Completed workflow: a fresh explicit primary-agent handoff should still start the next round.
@@ -947,8 +954,8 @@ after = {path.name: path.read_text() for path in tracked}
947
954
  assert before == after, 'done /cook inline-args rejection should leave canonical files unchanged'
948
955
  PY
949
956
 
950
- # Completed workflow again: model-assisted discussion analysis alone should still fail closed
951
- # without a fresh valid explicit primary-agent handoff.
957
+ # Completed workflow again: model-assisted discussion analysis alone should be able to
958
+ # synthesize the next round from explicit /cook entry.
952
959
  mark_done
953
960
 
954
961
  SESSION_FIVE="$TMPDIR/session-five.jsonl"
@@ -972,9 +979,9 @@ output = Path(sys.argv[1]).read_text() + Path(sys.argv[2]).read_text()
972
979
  snapshot = Path(sys.argv[3])
973
980
  state = json.loads(Path('.agent/state.json').read_text())
974
981
 
975
- assert not snapshot.exists(), 'done-workflow analyst-only restart should not emit a startup proposal snapshot'
976
- assert state['continuation_policy'] == 'done', 'done-workflow analyst-only restart should keep the workflow closed'
977
- assert 'fresh valid explicit primary-agent handoff' in output, 'done-workflow analyst-only restart should explain the explicit-handoff-only startup contract'
982
+ assert snapshot.exists(), 'done-workflow analyst-only restart should emit a startup proposal snapshot'
983
+ assert state['continuation_policy'] == 'continue', 'done-workflow analyst-only restart should reopen the workflow'
984
+ assert 'deferred primary-agent handoff' in output, 'done-workflow analyst-only restart should report deferred startup'
978
985
  PY
979
986
 
980
987
  # Custom confirmation UI: start should render proposal content separately from approval-only Start/Cancel actions.
@@ -1200,85 +1207,6 @@ assert 'Why this slice first: The redirect callback bug is already bounded enoug
1200
1207
  assert 'Primary-agent /cook handoff rationale: The implementation plan is concrete and ready for repo changes.' in state['advisory_startup_brief']['notes'], 'explicit handoff startup should preserve why_cook_now as notes'
1201
1208
  PY
1202
1209
 
1203
- # Fresh explicit handoff: later ordinary-chat follow-up before /cook should not invalidate startup.
1204
- HANDOFF_ROOT_FOLLOWUP="$TMPDIR/handoff-root-followup"
1205
- mkdir -p "$HANDOFF_ROOT_FOLLOWUP"
1206
- cd "$HANDOFF_ROOT_FOLLOWUP"
1207
- git init -q
1208
-
1209
- HANDOFF_SESSION_FOLLOWUP="$TMPDIR/handoff-session-followup.jsonl"
1210
- HANDOFF_SNAPSHOT_FOLLOWUP="$TMPDIR/handoff-proposal-followup.json"
1211
- HANDOFF_MESSAGES_FOLLOWUP="$(python3 - <<'PY'
1212
- import json
1213
- capsule = {
1214
- "kind": "cook_handoff",
1215
- "source": "primary_agent",
1216
- "captured_at": "2026-01-01T00:00:02.000Z",
1217
- "source_turn_id": "m0002",
1218
- "mission": "Fix login redirect callback behavior.",
1219
- "scope": [
1220
- "Update the callback redirect decision logic.",
1221
- "Preserve the broader auth flow."
1222
- ],
1223
- "constraints": [
1224
- "Do not refactor the broader auth flow."
1225
- ],
1226
- "acceptance": [
1227
- "Add a regression test for returning to the requested page."
1228
- ],
1229
- "risks": [
1230
- "Late ordinary-chat clarifications should not force the user into a fresh handoff-only retry loop."
1231
- ],
1232
- "notes": [
1233
- "Keep the startup brief anchored to the explicit primary-agent handoff until a later assistant reply replaces it."
1234
- ],
1235
- "handoff_kind": "implementation_workflow_handoff",
1236
- "first_slice_goal": "Land the redirect callback fix and its regression coverage.",
1237
- "first_slice_non_goals": [
1238
- "Do not refactor the broader auth flow."
1239
- ],
1240
- "implementation_surfaces": [
1241
- "src/auth/redirect.ts",
1242
- "tests/auth/redirect.spec.ts"
1243
- ],
1244
- "verification_commands": [
1245
- "npm test -- redirect.spec.ts"
1246
- ],
1247
- "why_this_slice_first": "The redirect callback bug is already bounded enough to start implementation safely.",
1248
- "task_type": "completion-workflow",
1249
- "evaluation_profile": "completion-rubric-v1",
1250
- "why_cook_now": "The implementation plan is concrete and ready for repo changes."
1251
- }
1252
- messages = [
1253
- {"role": "user", "content": "Please think through the login redirect fix and tell me when it is ready for /cook."},
1254
- {"role": "assistant", "content": "This task is now ready for /cook whenever you want to start implementation.\n\n```cook_handoff\n" + json.dumps(capsule, ensure_ascii=False, indent=2) + "\n```"},
1255
- {"role": "user", "content": "Before I run /cook, one more clarification: keep the broader auth flow unchanged and keep the later verification focused on the redirect regression."},
1256
- ]
1257
- print(json.dumps(messages, ensure_ascii=False))
1258
- PY
1259
- )"
1260
- write_session_messages "$HANDOFF_SESSION_FOLLOWUP" "$HANDOFF_ROOT_FOLLOWUP" "$HANDOFF_MESSAGES_FOLLOWUP"
1261
-
1262
- PI_COMPLETION_CONTEXT_PROPOSAL_ACTION=accept \
1263
- PI_COMPLETION_TEST_CONTEXT_PROPOSAL_PATH="$HANDOFF_SNAPSHOT_FOLLOWUP" \
1264
- PI_COMPLETION_SKIP_DRIVER_KICKOFF=1 \
1265
- pi --session "$HANDOFF_SESSION_FOLLOWUP" -e "$PKG_ROOT" -p "/cook" >"$TMPDIR/pi-completion-handoff-followup.out" 2>"$TMPDIR/pi-completion-handoff-followup.err"
1266
-
1267
- python3 - "$HANDOFF_SNAPSHOT_FOLLOWUP" <<'PY'
1268
- import json
1269
- import sys
1270
- from pathlib import Path
1271
-
1272
- snapshot = json.loads(Path(sys.argv[1]).read_text())
1273
- state = json.loads(Path('.agent/state.json').read_text())
1274
-
1275
- assert snapshot['source'] == 'handoff_capsule', 'later ordinary-chat follow-up should still use the explicit handoff capsule as startup source'
1276
- assert snapshot['mission'] == 'Fix login redirect callback behavior.', 'later ordinary-chat follow-up should preserve the handoff mission'
1277
- assert state['mission_anchor'] == 'Fix login redirect callback behavior.', 'later ordinary-chat follow-up should still start from the explicit handoff mission'
1278
- assert state['advisory_startup_brief']['source'] == 'primary_agent_handoff', 'later ordinary-chat follow-up should keep the advisory intake source as the explicit handoff'
1279
- assert 'Verification commands: npm test -- redirect.spec.ts' in state['advisory_startup_brief']['notes'], 'later ordinary-chat follow-up should preserve the handoff verification commands'
1280
- PY
1281
-
1282
1210
  # Fresh but non-startable explicit handoff: /cook should fail closed instead of falling back
1283
1211
  # to a broad recent-discussion startup brief when the explicit capsule is still too vague.
1284
1212
  HANDOFF_ROOT_VAGUE="$TMPDIR/handoff-root-vague"
@@ -1545,7 +1473,7 @@ assert 'First slice goal: Patch the callback edge case and cover it with a focus
1545
1473
  assert 'Verification commands: npm test -- redirect-edge.spec.ts' in state['advisory_startup_brief']['notes'], 'done-workflow handoff should preserve verification_commands in advisory notes'
1546
1474
  PY
1547
1475
 
1548
- # Stale handoff: an aged-out capsule should fail closed even if later discussion exists.
1476
+ # Stale handoff: later discussion should invalidate the older handoff capsule and fail closed instead of falling back to newer discussion.
1549
1477
  HANDOFF_ROOT_STALE="$TMPDIR/handoff-root-stale"
1550
1478
  mkdir -p "$HANDOFF_ROOT_STALE"
1551
1479
  cd "$HANDOFF_ROOT_STALE"
@@ -1558,7 +1486,7 @@ import json
1558
1486
  capsule = {
1559
1487
  "kind": "cook_handoff",
1560
1488
  "source": "primary_agent",
1561
- "captured_at": "2025-12-31T22:00:02.000Z",
1489
+ "captured_at": "2026-01-01T00:00:02.000Z",
1562
1490
  "source_turn_id": "m0002",
1563
1491
  "mission": "Fix the original login redirect callback behavior.",
1564
1492
  "scope": ["Update the original callback redirect logic."],
@@ -1571,7 +1499,7 @@ capsule = {
1571
1499
  "first_slice_non_goals": ["Do not refactor the auth stack."],
1572
1500
  "implementation_surfaces": ["src/auth/login-redirect.ts"],
1573
1501
  "verification_commands": ["npm test -- login-redirect.spec.ts"],
1574
- "why_this_slice_first": "The original callback follow-up was the first bounded implementation slice before it aged out."
1502
+ "why_this_slice_first": "The original callback follow-up was the first bounded implementation slice before later discussion replaced it."
1575
1503
  }
1576
1504
  newer_discussion = "Mission: Ship logout redirect consistency instead.\nScope:\n- Update the logout redirect path.\nConstraints:\n- Leave the login callback flow unchanged.\nAcceptance:\n- Add a logout redirect regression test."
1577
1505
  messages = [
@@ -1597,9 +1525,9 @@ from pathlib import Path
1597
1525
  snapshot = Path(sys.argv[1])
1598
1526
  output = Path(sys.argv[2]).read_text() + Path(sys.argv[3]).read_text()
1599
1527
 
1600
- assert not snapshot.exists(), 'aged-out handoff should not emit a startup proposal snapshot'
1601
- assert not Path('.agent').exists(), 'aged-out handoff should fail closed without writing canonical state'
1602
- assert 'fresh valid explicit primary-agent handoff' in output, 'aged-out handoff should explain that a fresh valid explicit handoff is required'
1528
+ assert not snapshot.exists(), 'stale handoff should not emit a startup proposal snapshot'
1529
+ assert not Path('.agent').exists(), 'stale handoff should fail closed without writing canonical state'
1530
+ assert 'could not derive a concrete startup brief from recent discussion' in output, 'stale handoff should explain that deferred startup synthesis failed closed'
1603
1531
  PY
1604
1532
 
1605
1533
  # Negative handoff rationale: a non-startable capsule must not become the startup mission.
@@ -313,7 +313,7 @@ assert routing['mode'] == 'bare', 'supported refocus should use bare active-work
313
313
  assert 'explicitGoal' not in routing, 'supported bare refocus should not expose removed explicit-goal shim fields'
314
314
  assert 'explicitGoalProvided' not in routing, 'supported bare refocus should not expose removed explicit-goal shim fields'
315
315
  assert routing['action'] == 'refocus', 'supported bare /cook should classify as refocus when a fresh explicit handoff proposes a different mission'
316
- assert routing['reason'] == 'fresh_explicit_handoff', 'supported bare /cook should record the explicit-handoff replacement reason'
316
+ assert routing['reason'] == 'explicit_handoff_replacement', 'supported bare /cook should record the explicit-handoff replacement reason'
317
317
  assert routing['proposedMissionAnchor'] == new_anchor, 'explicit handoff routing snapshot should expose the replacement mission anchor'
318
318
  assert routing['proposalSource'] == 'handoff_capsule', 'explicit handoff routing snapshot should preserve the handoff source'
319
319
  PY
@@ -411,7 +411,7 @@ assert routing['mode'] == 'bare', 'bare /cook should snapshot bare active-workfl
411
411
  assert 'explicitGoal' not in routing, 'bare chooser routing should not expose removed explicit-goal shim fields'
412
412
  assert 'explicitGoalProvided' not in routing, 'bare chooser routing should not expose removed explicit-goal shim fields'
413
413
  assert routing['action'] == 'refocus', 'fresh explicit replacement handoff should classify active bare /cook as refocus'
414
- assert routing['reason'] == 'fresh_explicit_handoff', 'fresh explicit replacement handoff should record the explicit-handoff reason'
414
+ assert routing['reason'] == 'explicit_handoff_replacement', 'fresh explicit replacement handoff should record the explicit-handoff reason'
415
415
  assert routing['currentMissionAnchor'] == updated_mission, 'explicit-handoff routing should keep the current mission anchor until the user approves replacement'
416
416
  assert routing['proposedMissionAnchor'] == replacement_mission, 'explicit-handoff routing should expose the proposed replacement mission'
417
417
  assert routing['proposalSource'] == 'handoff_capsule', 'explicit-handoff routing should preserve the handoff source'
@@ -454,7 +454,7 @@ assert state['mission_anchor'] == updated_mission, 'final Start/Cancel cancel sh
454
454
  assert plan['mission_anchor'] == updated_mission, 'final Start/Cancel cancel should keep plan.json unchanged'
455
455
  assert active['mission_anchor'] == updated_mission, 'final Start/Cancel cancel should keep active-slice.json unchanged'
456
456
  assert routing['action'] == 'refocus', 'final Start/Cancel cancel should still come from an explicit-handoff refocus classification'
457
- assert routing['reason'] == 'fresh_explicit_handoff', 'final Start/Cancel cancel should preserve the explicit-handoff reason'
457
+ assert routing['reason'] == 'explicit_handoff_replacement', 'final Start/Cancel cancel should preserve the explicit-handoff reason'
458
458
  assert routing['currentMissionAnchor'] == updated_mission, 'final Start/Cancel cancel should keep the current mission anchor until the user approves replacement'
459
459
  assert proposal['mission'] == replacement_mission, 'final Start/Cancel cancel should still prepare the replacement proposal before rewriting state'
460
460
  assert proposal['source'] == 'handoff_capsule', 'final Start/Cancel cancel should preserve the explicit-handoff proposal source'
@@ -495,7 +495,7 @@ assert routing['mode'] == 'bare', 'accepted bare refocus should keep bare routin
495
495
  assert 'explicitGoal' not in routing, 'accepted bare refocus should not expose removed explicit-goal shim fields'
496
496
  assert 'explicitGoalProvided' not in routing, 'accepted bare refocus should not expose removed explicit-goal shim fields'
497
497
  assert routing['action'] == 'refocus', 'accepted bare refocus should keep the explicit-handoff refocus classification'
498
- assert routing['reason'] == 'fresh_explicit_handoff', 'accepted bare refocus should keep the explicit-handoff reason'
498
+ assert routing['reason'] == 'explicit_handoff_replacement', 'accepted bare refocus should keep the explicit-handoff reason'
499
499
  assert routing['currentMissionAnchor'] == 'Remove completion status line, keep widget.', 'accepted bare refocus should expose the original mission until Start is accepted'
500
500
  assert routing['proposalSource'] == 'handoff_capsule', 'accepted bare refocus should preserve the explicit-handoff source'
501
501
  assert new_anchor in mission_text, '.agent/mission.md did not update to the bare refocus mission anchor'
@@ -17,45 +17,39 @@ checks = {
17
17
  "README.md": [
18
18
  "`/cook` is the explicit workflow boundary for starting, continuing, refocusing, or beginning the next round of long-running repo work.",
19
19
  "Only explicit `/cook` enters the workflow. Ordinary prompts stay in the main chat and go straight to the primary agent.",
20
- "Before you explicitly run `/cook`, the conversation can still stay in ordinary chat: the primary agent may keep answering follow-up questions and refining requirements rather than switching into a hard handoff-only refusal mode.",
21
- "That handoff should include an explicit structured `/cook` capsule in the assistant reply once the first slice is implementation-ready, so `/cook` can confirm the already-formed mission instead of re-deriving it from broad ambient context.",
22
- "The capsule is still advisory startup intake, not canonical workflow state, and new-workflow or next-round entry only proceeds when it already names the first bounded slice, repo-change-oriented acceptance, implementation surfaces, and verification commands.",
23
- "- startup and next-round entry stay confirm-first and require a fresh valid explicit primary-agent handoff",
24
- "- active workflows resume from canonical `.agent/**` state unless a fresh valid explicit handoff proposes a replacement",
25
- "`/cook` first looks for a fresh explicit primary-agent handoff capsule from recent ordinary-chat discussion. New-workflow entry and done-workflow next-round entry start only when that capsule is fresh, valid, and implementation-startable; otherwise `/cook` fails closed instead of deriving startup from recent discussion.",
26
- "When a workflow is already active and no fresh valid explicit handoff is present, `/cook` resumes from canonical `.agent/**` state instead of deriving replacement startup from recent discussion.",
27
- "Without one, `/cook` fails closed instead of deriving the next round from recent discussion.",
28
- "when a fresh explicit handoff suggests replacing an active workflow, `/cook` shows a chooser before any canonical state rewrite",
20
+ "Ordinary chat remains advisory until you explicitly run `/cook`. At that point `/cook` synthesizes a startup brief from recent discussion using primary-agent-style context, then asks you to **Start** or **Cancel** before rewriting canonical workflow state.",
21
+ "- startup and next-round entry stay confirm-first, but they now derive startup from explicit user `/cook` entry plus recent discussion when needed",
22
+ "- active workflows resume from canonical `.agent/**` state unless `/cook` synthesizes or receives a concrete replacement mission",
23
+ "`/cook` first checks for a fresh explicit primary-agent handoff capsule as a compatibility intake path. If none is present, `/cook` synthesizes a startup brief from recent discussion using primary-agent-style context.",
24
+ "when a concrete replacement mission suggests replacing an active workflow, `/cook` shows a chooser before any canonical state rewrite",
29
25
  ],
30
26
  "CHANGELOG.md": [
31
- "relaxed the pre-`/cook` ordinary-chat boundary so the primary agent can keep discussing and refining requirements before explicit `/cook` instead of switching into a hard handoff-only refusal mode as soon as workflow-worthiness is detected",
32
- "made fresh explicit `/cook` handoffs reusable from recent ordinary-chat discussion instead of requiring the immediately preceding turn, so Cancel can return users cleanly to ordinary discussion before they rerun `/cook`",
33
- "kept bare `/cook` startup and done-workflow next-round entry fail-closed on missing or non-startable explicit handoffs, while active workflows still resume from canonical `.agent/**` state unless a fresh explicit handoff proposes replacement",
27
+ "removed proactive primary-agent `/cook` prompting and default ordinary-chat `cook_handoff` emission so main chat stays advisory until the user explicitly runs `/cook`",
28
+ "changed bare `/cook` startup and done-workflow next-round entry to synthesize a deferred primary-agent startup brief from recent discussion instead of requiring a pre-authored explicit handoff capsule",
29
+ "updated public parity and shipped package contents so the tracked `.agent` contract files are included in package tarballs and packaged smoke/release verification can scaffold canonical state truthfully",
34
30
  ],
35
31
  "extensions/completion/prompt-surfaces.ts": [
36
32
  '"/cook is the only explicit entrypoint into long-running completion workflow."',
37
- '"If the user keeps asking follow-up questions or refining requirements before /cook, continue that ordinary-chat discussion normally instead of switching into a handoff-only refusal mode, but do not act as though /cook had already been invoked."',
38
- '"When handing off, explain that /cook can start a new workflow or next round only from a fresh valid explicit primary-agent handoff capsule from recent ordinary-chat discussion; otherwise it fails closed, while already-active workflows resume from canonical .agent state unless a fresh valid explicit handoff proposes replacement."',
39
- '"The capsule is startup intake for /cook only: do not present it as canonical .agent state',
33
+ '"Do not proactively tell the user to run /cook just because a task looks workflow-worthy, and do not emit a ```cook_handoff``` capsule by default in ordinary chat."',
34
+ '"Only provide a preview startup brief or ```cook_handoff``` capsule in ordinary chat when the user explicitly asks for that preview behavior."',
40
35
  ],
41
36
  "extensions/completion/index.ts": [
42
- '"/cook failed closed because new-workflow startup now requires a fresh valid explicit primary-agent handoff from recent ordinary-chat discussion; recent discussion alone no longer starts a workflow. Ask the primary agent to hand off explicitly in the main chat, then rerun /cook."',
43
- 'description: "/cook workflow: start a new workflow or next round only from a fresh recent explicit primary-agent handoff, resume the current workflow from canonical state, or confirm an explicit replacement from the explicit /cook command"',
37
+ '"/cook failed closed because it could not derive a concrete startup brief from recent discussion. Clarify the mission, first slice, or verification intent in the main chat, then rerun /cook."',
38
+ 'description: "/cook workflow: synthesize a startup brief when the user explicitly enters /cook, resume the current workflow from canonical state, or confirm a replacement mission from explicit /cook entry"',
44
39
  ],
45
40
  }
46
41
 
47
42
  forbidden = {
48
43
  "README.md": [
49
- "Start a new workflow from recent discussion:",
50
- "`/cook` falls back to deriving a startup brief from recent discussion only when no fresh explicit handoff is blocking startup",
51
- "Without a fresh explicit handoff blocking startup, `/cook` can fall back to recent discussion.",
44
+ "wait for a fresh primary-agent handoff",
45
+ "require a fresh valid explicit primary-agent handoff",
52
46
  ],
53
47
  "extensions/completion/prompt-surfaces.ts": [
54
- '"When handing off, explain that /cook will first look for a fresh explicit primary-agent handoff capsule and otherwise fall back to recent discussion."',
48
+ '"When handing off, explain that /cook can start a new workflow or next round only from a fresh valid explicit primary-agent handoff capsule; otherwise it fails closed, while already-active workflows resume from canonical .agent state unless a fresh valid explicit handoff proposes replacement."',
55
49
  ],
56
50
  "extensions/completion/index.ts": [
57
- 'description: "/cook workflow: derive a startup brief from recent discussion, then start, continue, refocus, or start the next round from the explicit /cook command"',
58
- '"/cook failed closed because recent discussion did not produce a clear execution-ready startup brief with Mission/Scope/Constraints/Acceptance for concrete repo changes. Clarify the concrete repo changes in the main chat and rerun /cook."',
51
+ 'description: "/cook workflow: start a new workflow or next round only from a fresh explicit primary-agent handoff, resume the current workflow from canonical state, or confirm an explicit replacement from the explicit /cook command"',
52
+ '"/cook failed closed because new-workflow startup now requires a fresh valid explicit primary-agent handoff from the immediately preceding ordinary-chat turn; recent discussion alone no longer starts a workflow. Ask the primary agent to hand off explicitly in the main chat, then rerun /cook."',
59
53
  ],
60
54
  }
61
55
 
@@ -266,17 +266,13 @@ assert not reminder.exists(), 'ordinary non-/cook turn should not inject complet
266
266
  assert handoff.exists(), 'ordinary non-/cook turn should inject the /cook handoff boundary reminder'
267
267
  handoff_text = handoff.read_text()
268
268
  assert '/cook is the only explicit entrypoint into long-running completion workflow.' in handoff_text, 'ordinary handoff reminder should preserve the explicit /cook workflow boundary'
269
- assert 'do not begin long-running product implementation in ordinary chat' in handoff_text, 'ordinary handoff reminder should block workflow-level implementation before /cook'
270
- assert 'recommend /cook as the workflow boundary while keeping the conversation in ordinary chat until the user explicitly runs /cook.' in handoff_text, 'ordinary handoff reminder should keep pre-/cook discussion advisory-first'
271
- assert 'continue that ordinary-chat discussion normally instead of switching into a handoff-only refusal mode' in handoff_text, 'ordinary handoff reminder should avoid hard refusal mode before explicit /cook'
272
- assert '```cook_handoff ... ``` JSON' in handoff_text, 'ordinary handoff reminder should require the explicit structured /cook handoff capsule'
273
- assert 'implementation_workflow_handoff' in handoff_text, 'ordinary handoff reminder should require the implementation-ready handoff kind'
274
- assert 'first_slice_goal, first_slice_non_goals, implementation_surfaces, verification_commands, why_this_slice_first' in handoff_text, 'ordinary handoff reminder should require first-slice startability fields'
275
- assert 'The capsule is startup intake for /cook only' in handoff_text, 'ordinary handoff reminder should keep the capsule non-canonical'
276
- assert 'fresh valid explicit primary-agent handoff capsule from recent ordinary-chat discussion' in handoff_text, 'ordinary handoff reminder should describe recent explicit-handoff startup truthfully'
277
- assert 'fails closed' in handoff_text, 'ordinary handoff reminder should describe fail-closed startup when no fresh valid handoff exists'
278
- assert 'resume from canonical .agent state' in handoff_text, 'ordinary handoff reminder should preserve active-workflow canonical resume wording'
279
- assert 'fall back to recent discussion' not in handoff_text, 'ordinary handoff reminder should no longer promise recent-discussion startup fallback'
269
+ assert 'Do not proactively tell the user to run /cook' in handoff_text, 'ordinary handoff reminder should keep ordinary chat neutral until explicit /cook entry'
270
+ assert 'do not emit a ```cook_handoff``` capsule by default in ordinary chat' in handoff_text, 'ordinary handoff reminder should stop proactive capsule emission'
271
+ assert 'ordinary chat remains ordinary chat until the user explicitly runs /cook' in handoff_text, 'ordinary handoff reminder should preserve the explicit /cook boundary'
272
+ assert 'do not begin long-running product implementation in ordinary chat' in handoff_text, 'ordinary handoff reminder should still block workflow-level implementation before /cook'
273
+ assert 'Only provide a preview startup brief or ```cook_handoff``` capsule in ordinary chat when the user explicitly asks for that preview behavior.' in handoff_text, 'ordinary handoff reminder should restrict preview capsules to explicit preview requests'
274
+ assert 'startup brief from recent discussion using primary-agent-style context' in handoff_text, 'ordinary handoff reminder should describe deferred startup synthesis'
275
+ assert 'Start/Cancel confirmation before canonical workflow state is rewritten' in handoff_text, 'ordinary handoff reminder should preserve confirm-first startup'
280
276
  assert not auto_resume.exists(), 'ordinary non-/cook turn should not queue auto-resume before /cook activation'
281
277
  assert 'Skipped completion workflow auto-resume prompt (test mode)' not in output, 'ordinary non-/cook turn should not attempt auto-resume'
282
278
  PY
@@ -304,8 +300,8 @@ assert 'Canonical routing profile:' in resume, 'resume prompt should expose cano
304
300
  assert f'- task_type: {expected_task_type}' in resume, 'resume prompt missing canonical task_type'
305
301
  assert f'- evaluation_profile: {expected_eval_profile}' in resume, 'resume prompt missing canonical evaluation_profile'
306
302
  assert routing['mode'] == 'bare', 'active bare /cook should snapshot bare routing mode'
307
- assert routing['action'] == 'continue', 'no-discussion active bare /cook should resume from canonical state without a fresh explicit handoff'
308
- assert routing['reason'] == 'missing_explicit_handoff', 'no-discussion active bare /cook should explain that resume happened because no fresh explicit handoff existed'
303
+ assert routing['action'] == 'continue', 'no-discussion active bare /cook should resume from canonical state without a concrete replacement mission'
304
+ assert routing['reason'] == 'no_replacement_proposal', 'no-discussion active bare /cook should explain that resume happened because no replacement mission was derived'
309
305
  assert routing['currentMissionAnchor'] == state['mission_anchor'], 'resume routing snapshot should keep the current mission anchor'
310
306
  assert routing['proposedMissionAnchor'] is None, 'no-discussion active bare /cook should not propose a replacement mission'
311
307
  assert not chooser_path.exists(), 'active bare /cook resume should not open the chooser without a fresh explicit handoff'
@@ -1,6 +1,6 @@
1
1
  ---
2
2
  name: cook-handoff-boundary
3
- description: Ordinary-chat boundary contract for deciding when a task has matured enough that the primary agent must stop short of long-running implementation and hand the user off to `/cook`.
3
+ description: Ordinary-chat boundary contract for keeping main chat advisory until the user explicitly enters `/cook`, while preventing long-running implementation from starting before that explicit workflow entry.
4
4
  ---
5
5
 
6
6
  # /cook Handoff Boundary
@@ -14,34 +14,66 @@ This skill governs the boundary between:
14
14
 
15
15
  ## Core Contract
16
16
 
17
- - Ordinary chat may be used to clarify requirements, discuss tradeoffs, propose implementation approaches, and refine scope with the user.
17
+ - Ordinary chat may be used to clarify requirements, discuss tradeoffs, propose implementation approaches, and refine scope.
18
18
  - `/cook` is the only explicit entrypoint into long-running completion workflow.
19
- - When the primary agent judges that a task has matured into completion-workflow scope, it must stop short of long-running implementation and treat `/cook` as the workflow boundary.
20
- - Before the user explicitly runs `/cook`, ordinary chat remains ordinary chat: the agent may still answer follow-up questions and refine requirements instead of switching into a handoff-only refusal mode.
19
+ - Ordinary chat remains ordinary chat until the user explicitly runs `/cook`.
20
+ - Before that explicit `/cook` entry, the primary agent must stop short of long-running implementation for workflow-level tasks.
21
21
 
22
- ## When To Hand Off To `/cook`
22
+ ## What Ordinary Chat May Do
23
23
 
24
- The primary agent should consider `/cook` handoff appropriate when one or more of the following are true:
24
+ The primary agent may:
25
+
26
+ - answer follow-up questions
27
+ - discuss tradeoffs
28
+ - refine scope and constraints
29
+ - summarize likely mission, acceptance, or risks
30
+ - help the user determine whether the work seems large enough for `/cook`
31
+
32
+ The primary agent should not:
33
+
34
+ - proactively tell the user to run `/cook`
35
+ - proactively emit a `cook_handoff` capsule by default
36
+ - act as though workflow has already started
37
+ - rewrite ordinary-chat discussion into canonical workflow state
38
+
39
+ ## When Work Looks Workflow-Worthy
40
+
41
+ The primary agent should treat work as workflow-worthy when one or more of the following are true:
25
42
 
26
- - the user has clearly shifted from exploration into implementation intent
27
- - the agent has just produced a concrete plan or proposal whose natural next step would be implementation
28
43
  - the task spans multiple files, steps, or verification surfaces
29
- - the task needs resumability, review, audit, or canonical workflow state
44
+ - the next natural step would be bounded repo implementation rather than more explanation
45
+ - the work needs resumability, review, audit, or canonical workflow state
30
46
  - the task is better treated as a long-running repo mission than a one-off answer or tiny fix
31
47
 
32
- ## Required Handoff Behavior
48
+ Even then, the boundary remains:
49
+
50
+ - ordinary chat can still keep refining the task
51
+ - only explicit `/cook` starts workflow
52
+
53
+ ## Required Behavior Before Explicit `/cook`
33
54
 
34
- When the task is judged ready for completion workflow, the primary agent must:
55
+ When a task has matured into workflow-level work, the primary agent must:
35
56
 
36
57
  - stop before long-running implementation
37
- - not edit tracked product files in ordinary chat for that workflow-level task
38
- - recommend bare `/cook` as the explicit workflow boundary once the task is implementation-ready
39
- - explain that `/cook` starts a new workflow or next round only from a fresh valid explicit primary-agent handoff capsule from recent ordinary-chat discussion, while active workflows resume from canonical state unless a fresh valid explicit handoff proposes replacement
40
- - distinguish a workflow-worthy handoff from an implementation-ready handoff
41
- - only append an implementation-ready `/cook` handoff capsule when the first bounded implementation slice is concrete enough to start immediately
42
- - if the user asks follow-up questions or refines requirements before running `/cook`, continue ordinary-chat discussion normally without acting as though workflow already started
58
+ - not edit tracked product files for that workflow-level task in ordinary chat
59
+ - continue ordinary discussion naturally if the user keeps asking questions or refining scope
60
+ - wait for the user to explicitly run `/cook` before treating the conversation as workflow startup
61
+
62
+ ## Deferred Handoff Model
63
+
64
+ When the user explicitly runs `/cook`:
65
+
66
+ - `/cook` will synthesize a startup brief from recent discussion using primary-agent-style context
67
+ - `/cook` will show Start / Cancel confirmation before canonical workflow state is rewritten
68
+ - that synthesized startup brief is advisory intake only, not canonical `.agent/**` state by itself
69
+
70
+ This means the primary agent does **not** need to proactively attach startup capsules during ordinary chat just because the task looks ready.
71
+
72
+ ## Optional Preview Behavior
73
+
74
+ Only if the user explicitly asks for a preview startup brief or handoff capsule in ordinary chat may the primary agent provide one.
43
75
 
44
- Required capsule format:
76
+ Optional preview capsule format:
45
77
 
46
78
  ````text
47
79
  ```cook_handoff
@@ -73,31 +105,28 @@ Required capsule format:
73
105
  Notes:
74
106
 
75
107
  - `constraints` may be replaced or supplemented by `non_goals` when clearer.
76
- - `first_slice_goal`, `first_slice_non_goals`, `implementation_surfaces`, `verification_commands`, and `why_this_slice_first` are required only for implementation-ready handoffs.
77
- - If the work is workflow-worthy but that first slice is still vague, say that `/cook` will be the right next step once the first slice is concrete enough, then keep refining in ordinary chat without emitting this implementation-ready capsule yet.
78
- - If later ordinary-chat discussion materially changes the startup brief before `/cook` runs, update or replace the capsule in a later assistant reply.
79
- - The mission must be positively startable implementation work; do not use rejection or suppression text as the mission.
80
- - The capsule is startup intake for `/cook` only. It is not canonical `.agent/**` state, not active-slice state, and not a second repo contract source.
108
+ - `first_slice_goal`, `first_slice_non_goals`, `implementation_surfaces`, `verification_commands`, and `why_this_slice_first` are required only for an implementation-ready preview capsule.
109
+ - Any preview capsule is startup intake for `/cook` only. It is not canonical `.agent/**` state, not active-slice state, and not a second repo contract source.
81
110
 
82
111
  Suggested wording:
83
112
 
84
- > This task now looks like `/cook` workflow work, but we are still in ordinary chat until you explicitly run `/cook`. If you want to keep refining the first slice first, we can do that here. Once you want to start implementation workflow, run bare `/cook`. I’ve also attached an explicit `/cook` handoff capsule so `/cook` can confirm this startup brief directly before the workflow begins.
113
+ > We are still in ordinary chat until you explicitly run `/cook`. If you want, we can keep refining the first slice here. When you do run `/cook`, it will synthesize a startup brief from our recent discussion and show Start / Cancel before workflow begins.
85
114
 
86
115
  A short recap may include mission, scope, or acceptance, but that recap must not be presented as canonical plan state.
87
116
 
88
117
  ## Forbidden Behaviors
89
118
 
90
- Once the task is judged ready for completion workflow, the primary agent must not:
119
+ Before the user explicitly runs `/cook`, the primary agent must not:
91
120
 
92
121
  - directly begin long-running implementation in ordinary chat
93
122
  - modify tracked product files as part of that workflow-level task
94
123
  - act as though `/cook` had already been invoked
95
124
  - silently rewrite ordinary-chat discussion into active workflow state
96
- - refuse ordinary-chat clarification or requirement-refinement turns solely because `/cook` would now be appropriate
125
+ - refuse ordinary-chat clarification only because `/cook` would now be appropriate
97
126
 
98
127
  ## Relationship To `completion-protocol`
99
128
 
100
- This skill is only about pre-`/cook` ordinary-chat handoff behavior.
129
+ This skill is only about pre-`/cook` ordinary-chat boundary behavior.
101
130
 
102
131
  After the user explicitly enters `/cook`, the separate `completion-protocol` skill governs:
103
132