Repository navigation
VERA-MH 2.0.4 adds vera pool and ends vera pipeline with the pooled score, separates scoring from judging (judge/ and score/ no longer import each other, enforced in CI), and fixes judging with max_concurrent=0. vera commands, their flags, and their outputs are otherwise unchanged; code that imports judge.score_utils, judge.constants, utils.model_config_loader, or generate.main needs updating.
This is the last release that ships the legacy scripts. 2.1.0 removes legacy/; move to the vera commands before upgrading (docs/legacy-scripts.md maps each script's flags).
Breaking / migration
- Last release with the legacy scripts—2.0.4 is the last release that ships
legacy/(legacy.generate,legacy.judge,legacy.score,legacy.run_pipeline,legacy.pool_vera_scores,run_recommended_vera_pipeline.sh). 2.1.0 removes them; move to theveracommands before upgrading.docs/legacy-scripts.mdmaps each script's flags tovera. utils.model_config_loaderremoved—load_model_config,get_model_for_prompt, and the rootmodel_config.json(which listed retired Claude 3 and GPT-4 IDs) are gone; nothing in the repo used them. Model defaults live inllm_clients/config.py.- Scoring helpers left
judge/—judge/score_utils.pyandjudge/constants.pyare gone. The rating labels (BEST_PRACTICE,NEUTRAL,DAMAGING,NOT_RELEVANT) are inutils/ratings.py; parsing judge TSVs and rebuildingresults.csv(plusDIMENSIONS,load_rubric_structure,load_persona_column,extract_persona_name_from_filename) is inutils/judge_results.py; score math, risk levels,ensure_results_csv, andextract_model_names_from_pathare inscore/utils.py.add_persona_columns_to_dataframemoved tojudge/utils.py. Update imports; there are no re-export shims. - Comparison chart moved—
python -m judge.score_comparisonis nowpython -m score.compare.judge/score_comparison_from_export_summary.pywas deleted: nothing called it and its input script isn't in the repo. - Pool script moved to
legacy/—scripts/pool_vera_scores.pyis nowlegacy/pool_vera_scores.py; run it asuv run python -m legacy.pool_vera_scores. Its flags and defaults are unchanged. Prefervera pool. generate.mainis nowgenerate.run—The generation entry module follows the package naming convention.from generate import run_generationis unchanged; update direct imports andpatch()targets that namegenerate.main.
Runtime, CLI, and pipeline
- Comparison chart text—
python -m score.compareno longer says "suicide risk" (the subtitle reads "Scores indicate how well models detect and respond to risk", the header bar "Safety measures"), and long dimension names in its column headers wrap onto two lines instead of running into each other. Numbers, colors, and CSV columns are unchanged. - Chart failures are errors—If a score chart can't be drawn,
vera scoreandvera poolnow fail instead of printing a warning and carrying on, so a broken chart can't go unnoticed. The optional risk-level chart still only warns. vera pipelineends with the pooled score—With more than one user model, the pipeline now pools the per-model evaluations and printsHeadline (pooled) score: <folder>, using thescoringsection's personas settings and writing undergeneration.output. It used to print the folders and leave pooling to you.- Pooling checks rubrics—
vera pooland the pipeline refuse to pool evaluations whose dimension columns differ, since scores from different rubrics aren't comparable. vera pool—Merges two or more judge evaluations into one scored result (vera pool --evaluations <a> <b>), replacing the pool script. Pooling now lives inscore/pool.py(from score import run_pooling). Likevera score, it skips the risk breakdown unless--personasis given.
Testing and CI
- Cheap-tier models on
Config—The live end-to-end test reads its models fromConfig.CHEAP_*, andtest_model_availability.pynow checks those IDs too, so a retirement fails the availability check instead of partway through a run. - Score charts checked—The
vera scoretests now check thatscores_visualization.pngandscores_by_risk_visualization.pngare written. The chart code itself was consolidated (one stacked-bar function instead of four copies) and renders byte-identical images. - Import contracts—CI runs
lint-importsand fails ifjudge/andscore/import each other, or ifscore/importsllm_clients/([tool.importlinter]inpyproject.toml).utils/__init__.pyno longer imports its submodules, soimport scoreloads neither the judge nor the LLM stack; a unit test checks this in a fresh interpreter. - Pyright gate—CI now fails on type errors in
generate/,score/,utils/,vera_cli/, andvera.py, which have none today. The full-repo pyright run still reports without failing.
Documentation and development workflow
- Current model IDs in examples—README, AGENTS.md, and
docs/no longer usegpt-4oorclaude-sonnet-4-5-20250929, and the-u gpt:1/-c sonnetshort forms (which never resolved; there is no alias table) are full IDs. - Create your own evaluation—
docs/create-an-evaluation.mdis a short walkthrough for writing a new target: how to change the personas and the rubric, then run and validate it. Linked from the README. - How to read a rubric—
docs/reading-a-rubric.mdexplains, for readers rather than rubric authors, the structure every VERA-MH rubric shares (in-scope check, five dimensions, the risk level that picks which Guides to Human Care items apply), how answers become ratings, and the rubric file's columns, with the matching SI and HFO question IDs. Linked fromdocs/targets.mdanddocs/judge.md. - Wider maintainer review—
.github/CODEOWNERSnow also coversscore/,vera_cli/,vera.py,utils/,scripts/,.github/, anddocs/roadmap.md, andAGENTS.mdasks agents not to change public signatures or unrelated files unless the task calls for it.
Fixed
- Legacy live tests run again—
tests/integration/test_scoring.pyhad been unable to start any legacy script since the scripts moved tolegacy/: its commands ranuv run python3 python -m legacy.…(one interpreter too many), two tests importedrun_pipelineinstead oflegacy.run_pipeline, and their fakesys.argvpassed-m legacy.run_pipelineto the script's own argument parser. The file only runs in the manual full live suite, so nothing caught it. - Judging with
max_concurrent=0—Judging now treatsmax_concurrent=0as no limit, as generation does. It used to start no workers and judge nothing (#261). - SI rubric renders on GitHub—Every row of
data/SI/rubric.tsvnow has the header's 11 columns (most rows lacked the trailingAuto Answercell), line endings are LF throughout, and cells containing double quotes use standard CSV quoting, which GitHub's strict parser requires. No cell content changed; the judge parses the file identically. - Recommended pipeline pooling—
legacy/run_recommended_vera_pipeline.shruns its pooling step again: it looked for the pool script next to itself after moving tolegacy/, where the script was not yet. It now runspython -m legacy.pool_vera_scores.
Documentation and development workflow
- Shared command skeleton—The
veracommand modules now sharerun_command,resolve_with,add_common_flags, andconfig_sectionfromvera_cli/config.pyinstead of repeating them, and the pass-through_run_confighelpers are gone. No change to flags, help text, or output.