Skip to content

Rectify: CmdSpec Argument Ordering Structural Immunity#3341

Merged
Trecek merged 8 commits into
developfrom
autoskillit-order-session-sits-idle-tools-variadic-flag-cons/3285
May 30, 2026
Merged

Rectify: CmdSpec Argument Ordering Structural Immunity#3341
Trecek merged 8 commits into
developfrom
autoskillit-order-session-sits-idle-tools-variadic-flag-cons/3285

Conversation

@Trecek
Copy link
Copy Markdown
Collaborator

@Trecek Trecek commented May 30, 2026

Summary

ClaudeCodeBackend.build_interactive_cmd() appended initial_prompt (a positional argument) after variadic CLI flags (--tools, --add-dir). The CLI parser greedily consumed the prompt string as a flag value, causing sessions to sit idle with a blank prompt. The fix (PR #3302) reordered arguments and added VARIADIC_CLAUDE_FLAGS metadata plus ordering tests.

The architectural weakness is that CmdSpec is a flat, opaque tuple[str, ...] with no semantic encoding of argument roles (positional vs flag-value vs variadic). Ordering correctness is enforced only by test coverage — not by construction. This plan introduces a typed CmdBuilder that makes argument-ordering bugs impossible by construction, plus a runtime assert_cmd_ordering gate that catches any bypass of the builder.

Requirements

Conflict Resolution Table

Implementation Plan

Plan file: /home/talon/projects/autoskillit-runs/remediation-20260530-130320-729652/.autoskillit/temp/rectify/rectify_cmd_ordering_immunity_2026-05-30_130320.md

🤖 Generated with Claude Code via AutoSkillit

Token Usage Summary

Step Model count uncached output cache_read peak_ctx turns cache_write time
rectify* opus[1m] 1 3.0k 26.3k 5.5M 160.9k 325 277.1k 21m 29s
review_approach* sonnet 1 52 7.0k 202.8k 50.4k 98 38.4k 5m 7s
dry_walkthrough* opus 1 45 16.8k 398.4k 65.8k 93 49.6k 9m 45s
implement* sonnet 1 2.1k 64.8k 11.7M 175.1k 305 160.3k 23m 13s
audit_impl* sonnet 1 78 14.7k 276.7k 47.9k 26 45.4k 7m 8s
prepare_pr* sonnet 1 79.0k 4.8k 182.6k 30.9k 17 15.8k 1m 15s
compose_pr* sonnet 1 58.7k 1.3k 182.6k 30.9k 15 15.5k 36s
review_pr* sonnet 3 4.6k 125.5k 4.6M 131.7k 279 289.5k 34m 56s
resolve_review* opus 3 172 44.3k 4.9M 99.6k 201 258.6k 32m 22s
resolve_pre_review_conflicts* opus 1 35 3.8k 727.5k 53.4k 30 37.2k 1m 26s
Total 147.9k 309.3k 28.7M 175.1k 1.2M 2h 17m

* Step used a non-Anthropic provider; caching behavior may differ.

Token Efficiency

Step LoC Changed cache_read/LoC cache_write/LoC output/LoC
rectify 0
review_approach 0
dry_walkthrough 0
implement 582 20145.8 275.5 111.3
audit_impl 0
prepare_pr 0
compose_pr 0
review_pr 0
resolve_review 56 88236.7 4618.4 791.4
resolve_pre_review_conflicts 198 3674.1 187.8 19.2
Total 836 34380.4 1420.4 369.9

Model Usage Breakdown

Model steps uncached output cache_read cache_write time
opus[1m] 1 3.0k 26.3k 5.5M 277.1k 21m 29s
sonnet 6 144.6k 218.0k 17.1M 564.9k 1h 12m
opus 3 252 64.9k 6.1M 345.4k 43m 35s

@Trecek Trecek force-pushed the autoskillit-order-session-sits-idle-tools-variadic-flag-cons/3285 branch 2 times, most recently from 19801a9 to 579bae0 Compare May 30, 2026 22:16
Copy link
Copy Markdown
Collaborator Author

@Trecek Trecek left a comment

Choose a reason for hiding this comment

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

AutoSkillit PR Review — Verdict: approved_with_comments

Comment thread src/autoskillit/execution/backends/codex.py
claude_code_project_dir,
get_logger,
)
from autoskillit.execution.backends.codex import CodexFlags
Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

[warning] arch: _headless_helpers.py imports CodexFlags directly from execution/backends/codex.py to construct _CODEX_VALUE_BEARING_FLAGS. This couples the headless/ module to a concrete backend implementation. The CodexFlags value-bearing flag constants should be co-located with CodexFlags and imported as a ready-made constant.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

Valid observation — flagged for design decision. The CodexFlags import couples headless/ to a concrete backend. Options: (a) co-locate value-bearing flag constants with each backend, (b) create a backend-agnostic registry in core/types, (c) accept the coupling as pragmatic for the ordering gate.

Comment thread tests/arch/test_variadic_ordering.py
Comment thread tests/arch/test_interactive_ordering_gate.py
from autoskillit.execution.backends.codex import CodexFlags
from autoskillit.execution.headless._headless_git import _compute_loc_changed

_CLAUDE_VALUE_BEARING_FLAGS: frozenset[str] = frozenset(
Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

[warning] cohesion: _CLAUDE_VALUE_BEARING_FLAGS, _CODEX_VALUE_BEARING_FLAGS, and _ALL_VALUE_BEARING_FLAGS are defined in _headless_helpers.py but belong logically to the command-building layer. They are orphaned from the flag registries they classify and inaccessible to other consumers. Move to backends/_cmd_builder.py or core/types/_type_enums.py.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

Valid observation — flagged for design decision. The value-bearing flag constants are consumed only by assert_interactive_ordering in this file. Moving them to _cmd_builder.py or core/types/_type_enums.py requires evaluating import-layer constraints (IL-0 vs IL-1).


VARIADIC_CLAUDE_FLAGS: frozenset[str] = frozenset({ClaudeFlags.ADD_DIR, ClaudeFlags.TOOLS})

NON_VARIADIC_CLAUDE_FLAGS: frozenset[str] = frozenset(
Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

[warning] cohesion: NON_VARIADIC_CLAUDE_FLAGS (core/types/_type_enums.py) and _CLAUDE_VALUE_BEARING_FLAGS (_headless_helpers.py) both classify ClaudeFlags members by argument-taking behavior but are defined separately with overlapping intent and inconsistent membership. The flag-classification vocabulary is split across two layers with neither referencing the other.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

Valid observation — flagged for design decision. NON_VARIADIC_CLAUDE_FLAGS and _CLAUDE_VALUE_BEARING_FLAGS overlap in intent but serve different validation gates. Unification requires deciding on a single taxonomy for flag properties.

Copy link
Copy Markdown
Collaborator Author

@Trecek Trecek left a comment

Choose a reason for hiding this comment

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

AutoSkillit review: warning-only findings detected. See inline comments — no blocking changes required.

Copy link
Copy Markdown
Collaborator Author

@Trecek Trecek left a comment

Choose a reason for hiding this comment

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

Observations accumulated from 1 local review round.

Trecek and others added 8 commits May 30, 2026 15:38
Adds test coverage that will fail until the structural guards are in place:
- test_flag_metadata_coverage: closed categorization of ClaudeFlags members
- test_cmd_builder: CmdBuilder ordering invariants and CmdSpec origin
- test_assert_interactive_ordering: runtime gate for positional/variadic ordering
- test_interactive_ordering_gate: AST guard that launch sites call the gate
- Extended test_variadic_ordering: cross-backend parametrized coverage

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Introduces typed CmdBuilder, NON_VARIADIC_CLAUDE_FLAGS closed categorization,
CmdOrigin provenance metadata, and assert_interactive_ordering runtime gate.

- core/types: CmdOrigin dataclass, origin field on CmdSpec, NON_VARIADIC_CLAUDE_FLAGS
- execution/backends/_cmd_builder.py: CmdBuilder enforces positional-before-variadic
  by raising CmdOrderingError immediately if positional() called after variadic_pair()
- ClaudeCodeBackend and CodexBackend build_interactive_cmd refactored to use CmdBuilder
- _headless_helpers.py: assert_interactive_ordering scans raw cmd tuple, refuses
  to trust CmdOrigin alone
- _session_launch.py and _cook.py: gate wired in before subprocess invocation

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
… test assertions

- Re-export assert_interactive_ordering via execution.headless and execution __init__
- Update imports in _cook.py and _session_launch.py to use public API
- Fix error message casing for consistent test matching
- Update test_backend_dataclasses to expect origin field and CmdOrigin export
- Update headless helpers size budget for new assert_interactive_ordering function
- Sort NON_VARIADIC_CLAUDE_FLAGS re-export alphabetically in core/__init__.pyi

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…nd remove redundant comment

NamedResume session_id is a positional value, not a flag — mode_flag(sid)
incorrectly placed it in CmdOrigin.mode_flags. Also removes the slop comment
describing absence of plugin_source handling.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Prevents CmdSpec with empty binary that would fail at subprocess invocation
with no diagnostic context.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…n ordering test

Uses CodexFlags.ADD_DIR when testing CodexBackend. Adds explicit assertion
that the variadic flag is present before checking ordering, converting
silent skips into visible failures.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…f cmd index

The NamedResume session_id is now tracked in origin.positional (not
mode_flags), so tests verify presence and semantic correctness rather
than position-dependent indexing.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…T import-collection logic

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@Trecek Trecek force-pushed the autoskillit-order-session-sits-idle-tools-variadic-flag-cons/3285 branch from 579bae0 to 81ab78e Compare May 30, 2026 22:38
@Trecek Trecek added this pull request to the merge queue May 30, 2026
Merged via the queue into develop with commit 546a980 May 30, 2026
3 checks passed
@Trecek Trecek deleted the autoskillit-order-session-sits-idle-tools-variadic-flag-cons/3285 branch May 30, 2026 22:49
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