Repository navigation
feat(eval): add eval redteam to probe grading checks with planted answers - #281
Merged
Merged
Conversation
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
Part of #220.
eval redteam QUESTIONS.jsonchecks that each question'sgradingblock rejects the answers it should. It grades four synthetic answers per question:match,fuzzy,exact,choice,json). It must pass.A
negatecheck does not switch the other attacks off: wrong, empty and hedge grade the block's non-negated checks. A block of only negated checks gets none of the three and is reported asnegated_only.Statuses:
pass,blocked(an attack was accepted or a canary was rejected),inconclusive(a graded question was not measured, or nothing was graded). Thestuffedanswer was dropped as an attack (it could not be a violation for a positive block, and a negated block is unmeasured either way);stuffed_forstays as agrade_checkself-check with unit tests. Exit 0 on pass, 1 on blocked or inconclusive, 2 on an unreadable question set or an unwritable--out.--outwritesredteam.v1. Judge checks are unscored unless--judgeis given, so the default run makes no model call. No score changes.Evidence
match 31,match 1,fuzzy on) no longer blocks a correct grader; negated checks no longer silence the attacks on a positive check; a single negated value builds its self-check; a negated whole-answer check builds none; a check value in the hedge skips the hedge probe; the canary formatchat the end withignore_punctuation: falsehas no full stop; a run that probed nothing is inconclusive; an unwritable--outexits 2; the summary counts unprobed questions.FRESH-REVIEW-A2, diff e2147b1...04f2142; its quoted line numbers match 04f2142, not 71cc8e6) found three blockers, all fixed in 6e16c6b: a wrong answer that contained a check value blocked correct graders; stuffing a negatedexact,jsonorlocation: exactcheck blocked correct graders; a block with one negated value was never probed. In-session review found the negated-check silencing (fixed in 04f2142) and the hedge clash (fixed in 068abc8).make ci-local --offline): ruff, mypy (273 files), deptry, bandit, schema and registry checks, mkdocs and the CLI-surface job (which reports the addedeval redteam) pass. Pytest: 9735 passed, 5 skipped, 1 failed:test_container_agent.py::test_probe_reports_a_writable_docker_socket(AF_UNIX path too long). That test depends on the path length of the worktree: it failed in these/localdisk/napetrov/scratchworktrees and on a clean intel/main checkout (earlier run), and passed in the shorter base worktree.mode: allfix on e881ab5: a negatedmatchwithmode: alland the defaultlocation: endgot the stuffed answerParis Lyon. That answer ends with one value only, so the all-match is false and the negation passes it: the real grader accepted it and a correct grader was blocked. The stuffed probe is now skipped for negatedmode: all, as the positive rule already skipsmode: all. Red then green: the two new cases failed on 6e16c6b (2 failed, 41 passed) and pass on e881ab5 (43 passed).ruff checkandmypypass. A fresh-contextclaude -preview of6e16c6bb..e881ab57plusstuffed_forfound no blocker; it confirmed the grader rejects every stuffed answer that is still built, and its two minor points (the skip is wider than the one failing case; the docstrings overstated) are addressed.tests/test_redteam.py), all passing.Merge Danger
eval redteamand new persisted formatredteam.v1(schema, fixture, registry entry). Both are new in this PR.eval redteamnow fails when a grader accepts a wrong answer, and when a question set has nothing gradeable (for example, judge checks only, without--judge).threshold0 or below used to be blocked by its stuffed probe (the grader passes everything); with the probe gone it isinconclusive, exit 1 either way."AB"): the canaryANSWER: ABis rejected by the grader, so the run blocks. This is a grader issue invalidate_grading, not in the red team.--judge, judge checks call the model. The wrong answer is a fixed sentinel string, not one written for each question.🤖 Generated with Claude Code