Skip to main content
When a Harness owns the agent loop, use BaseBenchmark to prepare tasks and score the RunResult returned by the Harness. This path fits question answering, code editing, browsing, and other Benchmarks that can reuse an existing Harness. The Benchmark neither calls the Model directly nor reimplements the Harness session or tool loop.

Implement a Complete Exact-Match Example

Create example_exact_match.py under src/agentcompass/benchmarks/ with the following content:
This implementation completes the three abstract BaseBenchmark methods: load_tasks(), prepare_task(), and evaluate(). build_plan() keeps the answer on the evaluation side instead of exposing ground_truth to the Harness. evaluate() uses dataclasses.replace() to preserve the status, error, trajectory, artifacts, and other result fields written by the Harness.

Export and Inspect the Registration

Add this import to src/agentcompass/benchmarks/__init__.py:
Inspect registration and the configuration schema:
The first command should list example_exact_match. The second should show case_sensitive and the shared RuntimeBenchmarkConfig fields. If the component is missing, inspect __init__.py, duplicate IDs, and the complete import traceback first.

Run with a Harness

The following command uses example_answer from the Harness implementation tutorial. That Harness returns the configured final_answer directly, so this smoke run does not require a working Model endpoint:
In run_info.json, inspect requestbenchmarkid and resolved_execution_plans, then inspect the single attempt record under details/*.json. With the answer Paris, expect status: "completed" and metrics.correct: true. Change the answer to Lyon; status should remain completed, while metrics.correct becomes false. This demonstrates that execution status and the Benchmark verdict are separate dimensions.

Extend the Pattern for Real Data

  • Put dataset loading, revision validation, and stable task conversion in load_tasks(), not at module-import time.
  • Put per-task evaluator state, timeouts, and paths in a typed BenchmarkPlan; do not pass them between attempts through a shared mutable dictionary.
  • Put prompts, workspaces, and public attachments in PreparedTask; hidden tests, answers, and reference patches must not enter Harness-visible fields.
  • When evaluation needs the task Environment or an isolated verifier, do not keep adding logic to this none example. Use the reuse or fresh patterns from Evaluation Modes and Artifacts.
  • When scoring is not a simple boolean, declare scalar score as the Contract primary and write it under RunResult.metrics; see Results and Aggregation.
For a production Harness-driven Benchmark with controller-side evaluation, inspect browsecomp.py.