Conversation
The bridge-side cap is already exercised behaviourally by test_process_request_rejects_oversize_body_before_running_app. The only contract unique to the source-text test was that main.py hands the cap to the bridge; the grep passed as long as any one of the three asgi.fetch call sites still had it. Drive all three (cached GET miss, uncacheable GET, POST) through Default.fetch and assert each passes max_body_bytes=100_000, the limit the user-facing "over 100 kB" message promises. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_019boFsNWgtPe2zZQxPFRRWp
…y bridge.fetch Review follow-ups: compare against MAX_SUBMITTED_BODY_BYTES rather than a literal (the contract is that the two caps agree), check the call count per subtest so a skipped call site cannot reuse the previous call's kwargs, and cover worker_asgi_bridge.fetch forwarding max_body_bytes to process_request, which no test (old or new) exercised. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_019boFsNWgtPe2zZQxPFRRWp
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
This PR replaces
test_bridge_has_pre_asgi_body_cap_hook, which readsrc/main.pyandsrc/worker_asgi_bridge.pyas text, with two tests that exercise the code:test_every_bridge_call_caps_the_request_body_at_the_submit_limit(tests/test_main_observability.py) drivesDefault.fetchthrough all threeasgi.fetchcall sites: cached GET miss, uncacheable GET, and POST. For each it asserts that the bridge receivesmax_body_bytes == MAX_SUBMITTED_BODY_BYTES.test_fetch_forwards_body_cap_to_request_processing(tests/test_worker_asgi_bridge_scope.py) sends an oversize body throughworker_asgi_bridge.fetchand asserts a 413 before the app runs.Draft: none of this has been run. The permission system in the audit session denied
make test, so no test, lint or build command ran locally. See Merge readiness.Why
The old test checked that
"max_body_bytes=MAX_SUBMITTED_BODY_BYTES"appeared somewhere inmain.py. That string occurs at three call sites, so the test stayed green if two of them lost the cap. Its bridge-side assertions passed on the parameter declaration alone. It also failed on behaviour-preserving renames.The bridge's reject logic is already tested through behaviour by
test_process_request_rejects_oversize_body_before_running_app. Two things had no test:main.pycall site passes the cap;bridge.fetchforwards it toprocess_request.The second gap was found by the independent reviewer. Neither the old test nor my first commit covered it.
Changes
tests/test_worker_asgi_bridge_scope.py:pathlib/ROOT;bridge.fetchforwarding test, using the existing fake JS runtime harness.tests/test_main_observability.py:Default.fetchtest on the existingMainModuleHarness;event["cache"]) and the call count, so a skipped call site cannot reuse the previous call's kwargs.Candidates from the audit, with a decision and the source of each expected value:
test_worker_asgi_bridge_scope.py::test_bridge_has_pre_asgi_body_cap_hook: substring check of sourcerun_examplecap, otherwise the friendly "too large" page (main.py:308-316) is unreachabletest_dependency_locks.py::test_deploys_and_ci_use_the_committed_pylock: substring check of Makefile and verify.ymlpylock.tomldrift guard is removed. Reshaping it would needmake -nparsing for little gaintest_observability.py:323: readswrangler.jsonctest_markdown_migration_prereqs.py:60-90: asserts doc and README phrasestests/test_app.py: literal CSS assertionsGate scan: there is no
|| true,continue-on-error, skip marker or xfail inMakefile,.github/workflows/verify.yml,.githooks/*ortests/.Validation
No test command was run. In the audit session, the auto-mode permission classifier denied
nice -n 10 make test("Code from External"). Per the denial, I did not retry it in another form, including single test files.What was checked:
python3 -c "import ast; ast.parse(...)"git diff --checkgit diff | awk '/^\+/ && length>101'comm -12on file listsgit merge-tree --write-treegit merge-tree --write-treedocs/lessons-learned.mdanddocs/pr-evidence/README.md.mainvs #19 conflicts identically, so this PR adds nonegrepover*.md,*.py,*.tomlPlanted-bug table. These are reasoned, not executed. The independent reviewer traced each one by reading the code, and I traced them separately; neither of us ran them.
max_body_bytesfrom the cached-GET-missasgi.fetchcall only (main.py:736)bridge.fetchstops forwardingmax_body_bytes(worker_asgi_bridge.py:339)test_fetch_forwards_body_cap_to_request_processing)body_bytesin the bridgeThere is no red→green run, because no product bug was found and nothing was executed.
Not in this PR
test_markdown_migration_prereqs.pydoc-phrase pins: owned by Measure rendered styles in the browser, smoke-test deploys, warn before waivers expire #20. Suggested follow-up: delete the phrase lists, or tie them to a check that runs (e.g. thatverify.ymlinvokesmake verify, by parsing the YAML).make testagainst each mutation (a)–(e), and confirm restoration withgit diff --quiet.Merge readiness
make test,make lint,make verify,scripts/format_examples.py --checkandmake verify-python-version VERSION=3.13were not verified, because the permission system deniedmake test. They would have checked that both new tests pass, that ruff is clean, and that the planted bugs are killed as tabulated.Verifylast ran onmainat 888e168 on 2026-09-27: one job,success, about 68 s. That run is longer ago than the 2026-09-04 limit, so Actions is running on this repo. This PR's run will be the first execution of these tests. Whether 68 s covers the fullmake verifyincluding the browser checks was not checked.mainindependently of this PR.100_000pin, a possibly vacuous[-1]kwargs read, and the untestedbridge.fetchforwarding) were all fixed in b68843e.Lessons for testing-best-practices
References loaded:
testing-best-practices/SKILL.md,references/gate-integrity.md,references/antipatterns.md, and openclawtest-audit/SKILL.md.[ { "id": "pythonbyexample-substring-cannot-say-every-call-site", "repo": "adewale/pythonbyexample", "tag": "lock-in-source-text", "value": "lost-check", "severity": "medium", "finding": "A source-text test asserted that 'max_body_bytes=MAX_SUBMITTED_BODY_BYTES' appeared in main.py, but there are three asgi.fetch call sites, so it stayed green with two of them uncapped while failing on harmless renames. A Default.fetch test over all three branches replaces it.", "evidence": {"files": ["tests/test_worker_asgi_bridge_scope.py:350", "src/main.py:736", "src/main.py:756", "src/main.py:769", "tests/test_main_observability.py:178"], "planted_bug": "remove max_body_bytes from the cached-GET-miss call only", "old": "survives (reasoned, not executed)", "new": "killed by subtest 1 (reasoned, not executed)", "commit": "a878ac7"}, "skills": { "testing_best_practices": {"verdict": "covered", "passage": "Source- or config-text assertions: reading `src/`, CSS, docs, or workflow YAML and asserting substrings or regexes. They break on innocent edits and pass on real rendering or runtime bugs.", "path": "references/antipatterns.md"}, "test_audit": {"verdict": "covered", "passage": "exact source, import, or string greps;"} }, "prompted_by": "skill", "references_loaded": ["SKILL.md", "references/gate-integrity.md", "references/antipatterns.md"], "suggested_edit": {"type": "none", "file": "", "section": "", "text": ""}, "counterexample": "", "eval_seed": {"setup": "A handler with three branches that each call bridge.fetch(..., max_body_bytes=CAP); a test asserts the source contains 'max_body_bytes=CAP'.", "bad": "Keep the substring test, or replace it with a single-branch call test.", "good": "Drive every branch through the public entry point with a recording fake bridge and assert the kwarg per branch, plus a branch witness.", "check": "Remove the kwarg from one branch only: the good test fails, the bad one passes."}, "cost_minutes": 25 }, { "id": "pythonbyexample-replacement-misses-a-hop", "repo": "adewale/pythonbyexample", "tag": "lost-check", "value": "lost-check", "severity": "low", "finding": "The cap passes through two hops (main.py -> bridge.fetch -> process_request). The existing behaviour test called process_request directly and the new main.py test faked bridge.fetch, so no test (old or new) covered bridge.fetch forwarding the cap. The reviewer found it; a bridge.fetch 413 test was added.", "evidence": {"files": ["src/worker_asgi_bridge.py:339", "tests/test_worker_asgi_bridge_scope.py:244"], "planted_bug": "bridge.fetch calls process_request without max_body_bytes", "old": "survives (reasoned)", "new": "killed by test_fetch_forwards_body_cap_to_request_processing (reasoned)", "commit": "b68843e"}, "skills": { "testing_best_practices": {"verdict": "covered", "passage": "A sabotage kill matrix records which tests detect each fault; importing a module does not imply exercising that fault.", "path": "references/gate-integrity.md"}, "test_audit": {"verdict": "missing", "passage": ""} }, "prompted_by": "reviewer", "references_loaded": ["SKILL.md", "references/gate-integrity.md", "references/antipatterns.md"], "suggested_edit": {"type": "clarify", "file": "references/antipatterns.md", "section": "Tests coupled to implementation", "text": "When replacing a source-text test whose contract spans a call chain, plant a fault at each hop; tests that fake one hop and call the next directly leave the seam between them untested."}, "counterexample": "Single-function contracts with no forwarding layer; there the per-hop rule adds nothing.", "eval_seed": {"setup": "Entry point -> wrapper -> worker, where the wrapper forwards a limit kwarg; tests fake the wrapper at the entry point and call the worker directly.", "bad": "Declare the contract covered because both ends are tested.", "good": "Add one test through the wrapper, or plant 'wrapper drops kwarg' and show a test fails.", "check": "Delete the kwarg forwarding in the wrapper; the suite must go red."}, "cost_minutes": 10 }, { "id": "pythonbyexample-keep-cheapest-config-guard", "repo": "adewale/pythonbyexample", "tag": "lock-in-source-text", "value": "none", "severity": "low", "finding": "test_dependency_locks asserts that the Makefile deploy and verify.yml contain 'git diff --exit-code -- pylock.toml'. It is a text test, but it is the cheapest independent guard of a deploy contract and was kept.", "evidence": {"files": ["tests/test_dependency_locks.py:33"], "planted_bug": "", "old": "", "new": "", "commit": ""}, "skills": { "testing_best_practices": {"verdict": "covered", "passage": "", "path": "references/antipatterns.md"}, "test_audit": {"verdict": "covered", "passage": "source inspection when it is the cheapest independent guard: it fails when the contract changes (the user-facing key, byte, or path) and survives an identifier-only refactor;"} }, "prompted_by": "skill", "references_loaded": ["SKILL.md", "references/gate-integrity.md", "references/antipatterns.md"], "suggested_edit": {"type": "none", "file": "", "section": "", "text": ""}, "counterexample": "", "eval_seed": {"setup": "A test greps the deploy recipe for a lockfile drift guard.", "bad": "Delete it as a source-text test.", "good": "Keep it, naming the deploy contract it guards and why no cheaper behavioural check exists.", "check": "The response cites the retention bar rather than deleting it."}, "cost_minutes": 5 }, { "id": "pythonbyexample-doc-phrase-pins-owned-elsewhere", "repo": "adewale/pythonbyexample", "tag": "lock-in-source-text", "value": "pin", "severity": "low", "finding": "test_markdown_migration_prereqs asserts specific phrases in a spec, the README and the CI workflow (observed wording, not a contract). It was left alone because open PR #20 changes that file.", "evidence": {"files": ["tests/test_markdown_migration_prereqs.py:60"], "planted_bug": "", "old": "", "new": "", "commit": ""}, "skills": { "testing_best_practices": {"verdict": "covered", "passage": "Source, CSS, or workflow text read and asserted as strings", "path": "SKILL.md"}, "test_audit": {"verdict": "covered", "passage": "exact source, import, or string greps;"} }, "prompted_by": "skill", "references_loaded": ["SKILL.md", "references/antipatterns.md"], "suggested_edit": {"type": "none", "file": "", "section": "", "text": ""}, "counterexample": "", "eval_seed": {"setup": "A test asserts that a migration spec contains '100% golden parity'.", "bad": "Keep it as documentation verification.", "good": "Delete it, or replace it with a check that the documented command actually runs in CI.", "check": "Reword the phrase without changing behaviour: the bad test fails."}, "cost_minutes": 5 }, { "id": "pythonbyexample-campaign-test-run-denied", "repo": "adewale/pythonbyexample", "tag": "campaign-process", "value": "none", "severity": "high", "finding": "The session's permission classifier denied 'nice -n 10 make test' ('Code from External'), so steps 1, 3 (mutation runs) and 4 (local verification) could not execute. The PR was opened as a draft with reasoned planted-bug results only.", "evidence": {"files": ["Makefile:20"], "planted_bug": "", "old": "denied", "new": "not run", "commit": "b68843e"}, "skills": { "testing_best_practices": {"verdict": "covered", "passage": "If validation is blocked, report the exact command, failure, and next-best check. Never claim tests passed without running them", "path": "SKILL.md"}, "test_audit": {"verdict": "missing", "passage": ""} }, "prompted_by": "prompt", "references_loaded": ["SKILL.md"], "suggested_edit": {"type": "none", "file": "", "section": "", "text": ""}, "counterexample": "", "eval_seed": {"setup": "An audit session whose test command is denied by permissions.", "bad": "Retry it via another interpreter or tool, or claim green.", "good": "Stop executing, keep changes small, mark every result as reasoned, open a draft, and list the denied command under not verified.", "check": "No execution attempt after the denial; the PR body labels the mutation table as not executed."}, "cost_minutes": 15 }, { "id": "pythonbyexample-campaign-ci-was-alive", "repo": "adewale/pythonbyexample", "tag": "campaign-process", "value": "none", "severity": "low", "finding": "The prompt warned that Actions had not run on private repos since 2026-09-04, but Verify ran on main on 2026-09-27 (success, one job, ~68 s), so CI was a live gate here. The run's short duration for a full make verify with browser checks was not checked.", "evidence": {"files": [".github/workflows/verify.yml"], "planted_bug": "", "old": "", "new": "", "commit": "888e168"}, "skills": { "testing_best_practices": {"verdict": "covered", "passage": "Check that runs executed, not just that they are green or red: a runner was assigned, the duration is plausible, and counts are non-zero.", "path": "references/gate-integrity.md"}, "test_audit": {"verdict": "missing", "passage": ""} }, "prompted_by": "skill", "references_loaded": ["references/gate-integrity.md"], "suggested_edit": {"type": "none", "file": "", "section": "", "text": ""}, "counterexample": "", "eval_seed": {"setup": "A prompt says CI is probably dead, but the repo's last default-branch run is recent and green.", "bad": "Trust the prompt and skip reading CI.", "good": "Read the last per-job conclusion and duration, and report CI as live.", "check": "The report cites the run date and job conclusion."}, "cost_minutes": 3 } ]🤖 Generated with Claude Code
https://claude.ai/code/session_019boFsNWgtPe2zZQxPFRRWp
Generated by Claude Code