Skip to content

fix: time constraints cap scale and bind the whole /plan chain (#886)#25

Merged
time-attack merged 4 commits into
mainfrom
time-attack/planslow
Jul 23, 2026
Merged

fix: time constraints cap scale and bind the whole /plan chain (#886)#25
time-attack merged 4 commits into
mainfrom
time-attack/planslow

Conversation

@time-attack

@time-attack time-attack commented Jul 23, 2026

Copy link
Copy Markdown
Owner

Problem

A /plan run on a hackathon-demo ask (SwipeMusic) burned 18 AskUserQuestion rounds / 28 questions despite the user stating a tight time budget:

  • The time box was asked in round 2 and never consumed by anything downstream.
  • Scale budgets from overlay GENERAL: Reduce Token Overhead garrytan/gstack#886 are keyed to /plan's Scale: header, which chained eng/design review invocations never see — 13 of the 18 rounds came from that chain running at full pressure.
  • review, plan-design-review, and design-review were not GENERAL: Reduce Token Overhead garrytan/gstack#886 targets at all.
  • Reviews spent rounds on ceremony: re-confirming a target the handoff already named (twice), one round per finding (6 consecutive single-question rounds in the design review), and a round offering to open blog links mid-timebox.
  • The max-vector scale classifier ranks a room demo as audience=public, pushing a throwaway hackathon build toward product-grade treatment.

Evidence: ~/.claude/projects/-Users-sinabina-orca-projects-SwipeMusic/1b922b73-*.jsonl

Fix

  • Time-constraint ceiling: an explicit user time constraint caps scale at session (one sitting) or hobby (day or two) regardless of higher vectors; printed with the scale.
  • Scale binds the chain: every handoff carries scale + time box; the receiving specialist inherits them without re-asking. Overlay GENERAL: Reduce Token Overhead garrytan/gstack#886 now also targets review, plan-design-review, design-review.
  • No ceremony rounds: unambiguous handoff targets are printed, not re-confirmed; obvious in-boundary fixes are applied and reported in a compact list; real decisions are batched (≤4/round); optional extras never get their own round at session/hobby.
  • Shared judgment contract (all six dispatchers): infer-don't-ask + time-budget clauses.

Mechanics

  • EXPECTED_PARITY_CHECKS 5027 → 5033 (+2 per newly targeted module); GENERAL: Reduce Token Overhead garrytan/gstack#886 regression fixture/evaluator extended to pin the ceiling, no-target-confirmation, and apply-not-ask behaviors.
  • Regen commit included (check:gstack2-generated gate).

Testing

  • bun run test:gstack2 — parity green at 5033 checks.
  • bun test — free suite green (exit 0).
  • bun run eval:select — 0/178 E2E, 0/28 LLM-judge tests affected by this diff.

🤖 Generated with Claude Code


Summary by cubic

Caps build scale by user-stated time boxes and binds scale/time across the entire /plan chain, including review modules, to cut wasted rounds. Extends garrytan#886 proportional planning so chained specialists inherit scale and act proportionally; parity now at 5,080 checks.

  • Bug Fixes
    • Bind scale and time box in every handoff; downstream specialists inherit without re-asking.
    • Extend GENERAL: Reduce Token Overhead garrytan/gstack#886 to review, plan-design-review, and design-review.
    • Time ceiling: user-stated limits cap scale at session/hobby; print the constraint with the scale.
    • Remove ceremony rounds: don’t reconfirm named targets, batch decisions, apply obvious in-boundary fixes, and skip optional extras at session/hobby.
    • Shared judgment: add infer-don’t-ask and time-budget clauses across dispatchers.

Written for commit 420793d. Summary will update on new commits.

Review in cubic

Sinabina and others added 2 commits July 23, 2026 11:47
A /plan run on a hackathon-demo ask burned 18 AskUserQuestion rounds:
the Scale budgets never reached the chained eng/design reviews (separate
invocations with no Scale header, and plan-design-review/design-review/
review were not garrytan#886 targets), the collected time box was never used,
and reviews spent rounds on ceremony (re-confirming handoff-named
targets, one round per finding, optional-extras offers).

- Overlay garrytan#886 now targets review, plan-design-review, and design-review;
  the binding scale inherits across chain handoffs; an explicit user
  time constraint caps scale at session/hobby regardless of higher
  vectors; obvious in-boundary fixes are applied and reported, not
  asked; question rounds are batched and never spent on ceremony.
- The /plan Build scale section makes the time-constraint ceiling
  explicit and requires every handoff to carry scale + time box.
- Shared judgment contract gains infer-don't-ask and time-budget
  clauses for all six dispatchers.
- EXPECTED_PARITY_CHECKS 5027 -> 5033 (2 per newly targeted module).

Evidence: ~/.claude/projects/-Users-sinabina-orca-projects-SwipeMusic/1b922b73-*.jsonl

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
…an#886)

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@cursor

cursor Bot commented Jul 23, 2026

Copy link
Copy Markdown

Bugbot is not enabled for your account, so this pull request was not reviewed.

Enable Bugbot in the Cursor dashboard to get automatic reviews on future PRs.

@time-attack

Copy link
Copy Markdown
Owner Author

CI failure attribution (verified, not assumed):

The three failing checks are pre-existing repo-wide breakage, not this branch:

  • windows-free-tests: same six gstack-paths GSTACK_HOME-resolution tests fail identically on every branch for 2+ days, including time-attack/planfixe (merged as fix: /plan empty-target fast path — stop burning ~5k tokens in empty repos #22) — compare this branch vs planfixe.
  • GStack 2 Gate → dev-container + Native windows-latest: failing on every branch since 2026-07-22 (last success 2026-07-17), same two-job signature on merged branches planfixe/questions. Root cause of dev-container: the generated-helper-closure test runs gstack-gbrain-sync.ts --help through Node 20, which cannot execute .ts (ERR_UNKNOWN_FILE_EXTENSION). The same test passes locally on this branch (bun test test/gstack2-runtime-install.test.ts -t 'generated helper closure' → 1 pass).

This diff is judgment-text only (scripts/gstack2/ + regenerated markdown); it touches no path resolution or runtime helper code. The gate jobs that exercise this change (installer-matrix, Installed six-skill first use, Native macos/ubuntu, quality) are all green. The Windows/devcontainer breakage deserves its own fix branch.

@cubic-dev-ai cubic-dev-ai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

5 issues found across 36 files

Prompt for AI agents (unresolved issues)

Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.


<file name="scripts/gstack2/bug-fix-overlays.ts">

<violation number="1" location="scripts/gstack2/bug-fix-overlays.ts:355">
P2: Direct review/design runs may infer a capped scale without printing the scale or time box, so users cannot verify the constraint being enforced. The shared overlay should explicitly print both after resolving them, including for non-`/plan` entry points.</violation>

<violation number="2" location="scripts/gstack2/bug-fix-overlays.ts:677">
P2: An empty or whitespace-only handoff target is treated as unambiguous and skips the target gate. Checking for a non-empty string preserves the no-ceremony behavior only when a target was actually supplied.</violation>

<violation number="3" location="scripts/gstack2/bug-fix-overlays.ts:678">
P2: Session/hobby regressions claim minor findings were applied even when `minor_findings` is zero or absent. Include the finding count in this result so the executable contract describes an action that occurred.</violation>

<violation number="4" location="scripts/gstack2/bug-fix-overlays.ts:678">
P2: The regression marks all findings as safe to apply solely because the scale is session/hobby. That does not test the overlay's required obvious-fix and authorized-mutation conditions, and can hide a workflow that applies unsafe findings without asking. The fixture/evaluator should model those conditions explicitly and only expect automatic application when both are true.</violation>
</file>

<file name="scripts/gstack2/generate-skill-tree.ts">

<violation number="1" location="scripts/gstack2/generate-skill-tree.ts:483">
P2: At product and venture scale, the shared contract now suppresses optional-extra question rounds even though the proportional-planning overlay only removes those rounds at session/hobby and explicitly preserves full question pressure at larger scales. The global rule should keep the no-ceremony restriction scoped to session/hobby (or otherwise defer to the specialist workflow at larger scales).</violation>
</file>

Tip: instead of fixing issues one by one fix them all with cubic

Re-trigger cubic

review_iterations_max: small ? 1 : 3,
step_unit: ['hours', 'days', 'weeks', 'stage-appropriate', 'stage-appropriate'][rank],
target_confirmation_round: input.handoff_target == null,
minor_findings_applied_not_asked: small,

@cubic-dev-ai cubic-dev-ai Bot Jul 23, 2026

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2: Session/hobby regressions claim minor findings were applied even when minor_findings is zero or absent. Include the finding count in this result so the executable contract describes an action that occurred.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At scripts/gstack2/bug-fix-overlays.ts, line 678:

<comment>Session/hobby regressions claim minor findings were applied even when `minor_findings` is zero or absent. Include the finding count in this result so the executable contract describes an action that occurred.</comment>

<file context>
@@ -647,20 +655,27 @@ export function evaluateBugFixRegression(pr: number, rawInput: unknown): Record<
         review_iterations_max: small ? 1 : 3,
         step_unit: ['hours', 'days', 'weeks', 'stage-appropriate', 'stage-appropriate'][rank],
+        target_confirmation_round: input.handoff_target == null,
+        minor_findings_applied_not_asked: small,
       };
     }
</file context>
Suggested change
minor_findings_applied_not_asked: small,
minor_findings_applied_not_asked: small && Number(input.minor_findings ?? 0) > 0,
Fix with cubic

outside_voices: small ? 'on-request' : 'offer',
review_iterations_max: small ? 1 : 3,
step_unit: ['hours', 'days', 'weeks', 'stage-appropriate', 'stage-appropriate'][rank],
target_confirmation_round: input.handoff_target == null,

@cubic-dev-ai cubic-dev-ai Bot Jul 23, 2026

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2: An empty or whitespace-only handoff target is treated as unambiguous and skips the target gate. Checking for a non-empty string preserves the no-ceremony behavior only when a target was actually supplied.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At scripts/gstack2/bug-fix-overlays.ts, line 677:

<comment>An empty or whitespace-only handoff target is treated as unambiguous and skips the target gate. Checking for a non-empty string preserves the no-ceremony behavior only when a target was actually supplied.</comment>

<file context>
@@ -647,20 +655,27 @@ export function evaluateBugFixRegression(pr: number, rawInput: unknown): Record<
         outside_voices: small ? 'on-request' : 'offer',
         review_iterations_max: small ? 1 : 3,
         step_unit: ['hours', 'days', 'weeks', 'stage-appropriate', 'stage-appropriate'][rank],
+        target_confirmation_round: input.handoff_target == null,
+        minor_findings_applied_not_asked: small,
       };
</file context>
Suggested change
target_confirmation_round: input.handoff_target == null,
target_confirmation_round: typeof input.handoff_target !== 'string' || input.handoff_target.trim().length === 0,
Fix with cubic

The /plan dispatcher prints a \`Scale:\` header line classified from fifteen build-scale vectors (its Build scale section). This rule authorizes every planning specialist to size its machinery to that scale while keeping every STOP gate and approval boundary; a polite user answering every question is not evidence the full machinery is wanted, and the user can always ask for the complete treatment.
The /plan dispatcher prints a \`Scale:\` header line classified from fifteen build-scale vectors (its Build scale section). This rule authorizes every planning and review specialist to size its machinery to that scale while keeping every STOP gate and approval boundary; a polite user answering every question is not evidence the full machinery is wanted, and the user can always ask for the complete treatment.

The binding scale comes from the first available source: the printed \`Scale:\` header, a chain handoff that names a scale or time box, or on-the-spot classification from the prompt and cheap repository evidence. An explicit user time constraint is a ceiling, not one vector among fifteen: work that must fit one sitting caps the scale at \`session\`, and a day-or-two deadline caps it at \`hobby\`, regardless of higher vectors. A chained invocation inherits the upstream scale and time box without re-asking, and every handoff it emits carries them forward.

@cubic-dev-ai cubic-dev-ai Bot Jul 23, 2026

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2: Direct review/design runs may infer a capped scale without printing the scale or time box, so users cannot verify the constraint being enforced. The shared overlay should explicitly print both after resolving them, including for non-/plan entry points.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At scripts/gstack2/bug-fix-overlays.ts, line 355:

<comment>Direct review/design runs may infer a capped scale without printing the scale or time box, so users cannot verify the constraint being enforced. The shared overlay should explicitly print both after resolving them, including for non-`/plan` entry points.</comment>

<file context>
@@ -346,21 +346,29 @@ At the Phase 5 approval gate, print the full design-doc body as direct assistant
-The /plan dispatcher prints a \`Scale:\` header line classified from fifteen build-scale vectors (its Build scale section). This rule authorizes every planning specialist to size its machinery to that scale while keeping every STOP gate and approval boundary; a polite user answering every question is not evidence the full machinery is wanted, and the user can always ask for the complete treatment.
+The /plan dispatcher prints a \`Scale:\` header line classified from fifteen build-scale vectors (its Build scale section). This rule authorizes every planning and review specialist to size its machinery to that scale while keeping every STOP gate and approval boundary; a polite user answering every question is not evidence the full machinery is wanted, and the user can always ask for the complete treatment.
+
+The binding scale comes from the first available source: the printed \`Scale:\` header, a chain handoff that names a scale or time box, or on-the-spot classification from the prompt and cheap repository evidence. An explicit user time constraint is a ceiling, not one vector among fifteen: work that must fit one sitting caps the scale at \`session\`, and a day-or-two deadline caps it at \`hobby\`, regardless of higher vectors. A chained invocation inherits the upstream scale and time box without re-asking, and every handoff it emits carries them forward.
 
 - \`session\` and \`hobby\`: batch every question the initial prompt left unanswered into one AskUserQuestion round (two rounds for hobby); skip web or landscape research, outside voices, second opinions, and visual sketches unless the user asks (privacy gates are unchanged whenever they run); cap any adversarial or spec review loop at one iteration; keep the decision artifact near one page with next steps sized in hours (session) or days (hobby), never a phased multi-week roadmap or a distribution plan the user did not ask for.
</file context>
Suggested change
The binding scale comes from the first available source: the printed \`Scale:\` header, a chain handoff that names a scale or time box, or on-the-spot classification from the prompt and cheap repository evidence. An explicit user time constraint is a ceiling, not one vector among fifteen: work that must fit one sitting caps the scale at \`session\`, and a day-or-two deadline caps it at \`hobby\`, regardless of higher vectors. A chained invocation inherits the upstream scale and time box without re-asking, and every handoff it emits carries them forward.
The binding scale comes from the first available source: the printed \`Scale:\` header, a chain handoff that names a scale or time box, or on-the-spot classification from the prompt and cheap repository evidence. An explicit user time constraint is a ceiling, not one vector among fifteen: work that must fit one sitting caps the scale at \`session\`, and a day-or-two deadline caps it at \`hobby\`, regardless of higher vectors. A chained invocation inherits the upstream scale and time box without re-asking, and every handoff it emits carries them forward. After resolving them, print the binding \`Scale:\` and \`Time box:\` before proceeding, including when classification happened on the spot.
Fix with cubic

'8. Match the user language. Empty or contradictory evidence blocks confident success.',
'9. Recommendations remain traceable downstream, including what evidence would change them.',
'10. The user makes the final decision.',
'10. Ask only what cannot be inferred. Question rounds are for decisions that are consequential and still open after the prompt, the repository, and platform convention are consulted; infer the rest, state each inferred default in one line, and batch what remains. Never spend a round confirming what a handoff already names or offering optional extras.',

@cubic-dev-ai cubic-dev-ai Bot Jul 23, 2026

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2: At product and venture scale, the shared contract now suppresses optional-extra question rounds even though the proportional-planning overlay only removes those rounds at session/hobby and explicitly preserves full question pressure at larger scales. The global rule should keep the no-ceremony restriction scoped to session/hobby (or otherwise defer to the specialist workflow at larger scales).

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At scripts/gstack2/generate-skill-tree.ts, line 483:

<comment>At product and venture scale, the shared contract now suppresses optional-extra question rounds even though the proportional-planning overlay only removes those rounds at session/hobby and explicitly preserves full question pressure at larger scales. The global rule should keep the no-ceremony restriction scoped to session/hobby (or otherwise defer to the specialist workflow at larger scales).</comment>

<file context>
@@ -476,7 +480,9 @@ function sharedJudgmentContract(): string {
     '8. Match the user language. Empty or contradictory evidence blocks confident success.',
     '9. Recommendations remain traceable downstream, including what evidence would change them.',
-    '10. The user makes the final decision.',
+    '10. Ask only what cannot be inferred. Question rounds are for decisions that are consequential and still open after the prompt, the repository, and platform convention are consulted; infer the rest, state each inferred default in one line, and batch what remains. Never spend a round confirming what a handoff already names or offering optional extras.',
+    '11. A user-stated time constraint binds every phase and every chained skill. Skip or compress optional phases that do not fit it, noting each skip in one line.',
+    '12. The user makes the final decision.',
</file context>
Fix with cubic

review_iterations_max: small ? 1 : 3,
step_unit: ['hours', 'days', 'weeks', 'stage-appropriate', 'stage-appropriate'][rank],
target_confirmation_round: input.handoff_target == null,
minor_findings_applied_not_asked: small,

@cubic-dev-ai cubic-dev-ai Bot Jul 23, 2026

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2: The regression marks all findings as safe to apply solely because the scale is session/hobby. That does not test the overlay's required obvious-fix and authorized-mutation conditions, and can hide a workflow that applies unsafe findings without asking. The fixture/evaluator should model those conditions explicitly and only expect automatic application when both are true.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At scripts/gstack2/bug-fix-overlays.ts, line 678:

<comment>The regression marks all findings as safe to apply solely because the scale is session/hobby. That does not test the overlay's required obvious-fix and authorized-mutation conditions, and can hide a workflow that applies unsafe findings without asking. The fixture/evaluator should model those conditions explicitly and only expect automatic application when both are true.</comment>

<file context>
@@ -647,20 +655,27 @@ export function evaluateBugFixRegression(pr: number, rawInput: unknown): Record<
         review_iterations_max: small ? 1 : 3,
         step_unit: ['hours', 'days', 'weeks', 'stage-appropriate', 'stage-appropriate'][rank],
+        target_confirmation_round: input.handoff_target == null,
+        minor_findings_applied_not_asked: small,
       };
     }
</file context>
Fix with cubic

Sinabina and others added 2 commits July 23, 2026 12:37
garrytan#538 + code-intelligence contract (parity 5056)

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@time-attack
time-attack merged commit 655e823 into main Jul 23, 2026
7 of 14 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant