Skip to content

Bound coordinator artifact reads without reducing agent autonomy - #86

Merged
fazpu merged 1 commit into
mainfrom
fix/bounded-read-file
Jul 17, 2026
Merged

Bound coordinator artifact reads without reducing agent autonomy#86
fazpu merged 1 commit into
mainfrom
fix/bounded-read-file

Conversation

@fazpu

@fazpu fazpu commented Jul 17, 2026

Copy link
Copy Markdown
Member

Why

Loopy supplied an eval-runner coordinator with only the absolute path to a canonical 1.9 MiB evaluation report. The coordinator then reasonably called Team Harness read_file. The old core tool returned the complete report as one tool result, so the immediately following model request exceeded the coordinator context window. All five evaluation checks had already passed, but the coordinator failed before it could publish the receipt and goal-check output.

Path-only prompting is therefore insufficient if the path-reading tool itself is unbounded. Review also found the same transport risk in read_new_file_content: a fresh incremental cursor starts at byte zero and the old implementation read from there to EOF.

What changes

  • Make read_file an explicit, recoverable page interface.

    • Zero-based offset_chars and optional limit_chars arguments.
    • Hard maximum of 32,768 decoded file-content characters and 32 KiB after UTF-8 encoding per result, plus short metadata.
    • Exact returned character range, EOF state, and continuation offset.
    • Exact historical result for small and empty files.
    • Unicode code points are never split, including giant one-line JSON reports.
  • Bound read_new_file_content without changing its path-only schema.

    • FIFO pages from an isolated per-run raw-byte cursor.
    • Unread backlog is preserved; the result tells the coordinator to call again with the same path.
    • The cursor advances only over raw bytes fully represented in returned text.
    • Valid UTF-8 crossing a raw page boundary is held for the next page.
    • Invalid UTF-8 retains replacement-character behavior without expanding the returned content past 32 KiB.
    • Module-level and per-run bindings share one implementation, while per-run state remains isolated.
  • Preserve the state/trace boundary.

    • Caller envelopes and prompts remain path-only.
    • The harness does not select evidence fields, summarize semantic content, or infer an evaluation verdict.
    • The complete canonical artifact stays untouched at its absolute path.
    • Only the bounded page actually returned to the coordinator is placed in the next model request and run.json.
  • Record the contract in TH-D9 and a binding design document, update the CLI and website documentation, document consumer impact, repair missing changelog comparison links, and prepare version 0.5.3.

Compatibility

Small reads are unchanged. The read_file schema change is additive because its two new arguments are optional; read_new_file_content retains its existing schema. Consumers that relied on receiving a large file or append backlog in one call must follow the continuation offset, call the incremental reader again, or choose a focused projection such as jq.

Verification

  • 552 tests passed with NO_COLOR unset and TERM=xterm-256color
  • Ruff lint and formatting passed
  • Pyright: 0 errors, 0 warnings
  • Coordinator-loop regressions prove both tools place only the bounded page in the next model request and run.json
  • Boundary coverage includes empty files, exact limits, multi-megabyte one-line content, Unicode boundary splits, invalid UTF-8 expansion, FIFO backlog, and isolated per-run cursors
  • Claude Opus and Antigravity both approved the final amended diff
  • Claude additionally fuzzed adversarial and random byte streams, verifying strict cursor progress, bounded output, and lossless/replay-free reconstruction

Non-goals

This PR does not add semantic report digestion, credential scanning, preventive policy, generic all-tool truncation, or source-artifact rewriting. Those would be separate contracts.

@fazpu
fazpu merged commit dec83ce into main Jul 17, 2026
8 checks passed
@fazpu
fazpu deleted the fix/bounded-read-file branch July 17, 2026 09:24
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