RunResult. They may inspect the normalized answer, trajectory, metrics, status, error, and artifacts, then return an AnalysisResult. They must not rerun the agent, change Benchmark correctness, or replace scoring logic that belongs in BaseBenchmark.evaluate().
Implement a Public Analyzer
The following example is scoped to the publicexample_exact_match Benchmark from the Harness-driven Benchmark tutorial and flags empty or unusually long final answers. It does not depend on any Environment provider implementation:
BaseAnalyzer Contract
The base class also provides
matches_dataset(), check_requirements(), should_skip(), and is_threshold_badcase(). The shared should_skip() recognizes conf.only_incorrect; custom configuration remains the Analyzer’s responsibility.
Use exact registered Benchmark IDs in datasets. Use JSONPath only for data genuinely required before calling analysis(); optional fields should be handled inside the method so their absence does not silently remove the Analyzer output.
Register and Export
Place the implementation undersrc/agentcompass/analyzers/, commonly in analyzers/basic/ for deterministic rules. Decorate the concrete class with @ANALYZERS.register() and import its module through package __init__.py files so importing agentcompass.analyzers executes the decorator.
The registry rejects duplicate IDs. A top-level re-export is optional for Python name convenience, but transitive module import is required for registration. Confirm discovery with:
execution.analysis_params; agentcompass config docs currently documents only Benchmark, Harness, and Environment config dataclasses, not Analyzer conf dictionaries. Document every supported Analyzer key and default explicitly.
Selection and Family Resolution
For each attempt, the runtime follows this sequence when analysis is enabled:- Apply the
analyzerswhitelist when present; otherwise applyexclude_analyzers. - Construct each remaining registered Analyzer and overlay its per-ID configuration object.
- Check
datasets,data_requirements, andonly_incorrecteligibility. - Group eligible implementations by
base_analyzeror, when absent, their ownid. - Select the strictly highest-
priorityimplementation in each family and call itsanalysis()method.
base_analyzer = "<generic-id>", a higher priority, and a narrower datasets list. Unrelated Analyzers should keep base_analyzer = None so they can run independently.
This priority behavior is specific to Analyzers. Recipe priority does not currently affect Recipe application order.
Return AnalysisResult
analysis() returns:
The runtime persists the selected family’s payload at:
is_badcase and details for a returned result, and includes score, error, and extra only when populated. AnalysisResult.task_id is not duplicated inside that family payload. If analysis() raises, the runtime records an indeterminate family error and continues; it does not alter the Benchmark’s existing result.
Declare only supported aggregation methods:
analysis_summary.json and analysis_summary.md. A detector that explicitly returns is_badcase but produces zero bad cases and zero analysis errors remains in per-attempt details but is omitted from the run-level summary. See Summary and Analysis Results for the persisted format.
Validate on One Public Task
After addingexample_exact_match and example_answer from the Benchmark and Harness implementation tutorials, run their deterministic task with the example Analyzer. This path needs no model endpoint or credentials:
- exactly the requested family appears under the attempt’s
analysis_result; details.answer_charactersmatches the savedfinal_answer;- the configured limit overrides the class default without mutating later Analyzer instances, and the five-character answer is marked as a bad case by the four-character limit;
- a different Benchmark is skipped because of
datasets; - missing required data skips the Analyzer, while an exception inside
analysis()produces a family error; analysis_summary.jsonandanalysis_summary.mdcontain the declared numeric distribution when output is aggregatable.
agentcompass analysis to verify compatibility with persisted RunResult reconstruction. Follow Testing and Validation for complete repository checks and pull request evidence.
Completion Checklist
- The new logic diagnoses an existing result and does not replace Benchmark scoring.
- The ID, description, category, dataset scope, required fields, and configuration defaults are explicit.
- Registration is reachable from
agentcompass.analyzers, andagentcompass list analyzershows the ID. - Family and priority settings cannot suppress an unrelated Analyzer.
AnalysisResultanddetailsare JSON-serializable, and declared distributions use supported value types.- Inline analysis, copied-result re-analysis, skips, errors, and aggregate output have been checked on public data.
- User-facing configuration and output fields are documented in both languages.
