OpenHands / OpenHands/benchmarks
Portable result export: to_openeval()/from_openeval() for EvalInstance/EvalOutput?
Nobody has claimed this yet.
- Dominant language
- Python
- Stars
- 124
- Forks
- 90
- Avg merge
- 1d 6h
- Merged PRs (30d)
- 1
Description
Summary
Would to_openeval() / from_openeval() helpers for this repo's EvalInstance / EvalOutput models be useful, so runs from any of the ~20 benchmark harnesses here (SWE-Bench, GAIA, Harbor/TerminalBench, Commit0, etc.) could be exported into a portable, framework-agnostic result format?
Context
I looked through benchmarks/utils/models.py and CONTRIBUTING.md — this repo already has a clean, shared shape across every benchmark folder:
EvalInstance(id: str, data: dict[str, Any])— the per-task input, produced by every benchmark'sprepare_instances().EvalOutput(instance_id, attempt, test_result: dict[str, Any], instruction, metadata: EvalMetadata, history: list[Event], metrics: Metrics, error, instance, runtime_runs)— the per-task result, produced byevaluate_instance()and written out by everyeval_infer.py.EvalMetadata(llm, dataset, dataset_split, max_iterations, eval_output_dir, critic, workspace_type, ...)— the run-level config.
That's a real, shared, installable schema (not per-benchmark ad hoc JSON), which is exactly the situation EvalPort (spec: https://github.com/adhabnr-ux/evalport/blob/main/spec/SPEC.md) is meant for: a small JSON-Schema-defined format for portable eval test cases and result sets, with a Python SDK (evalport-sdk on PyPI, openeval.validate.validate_suite() / validate_result_set()) and 35+ community adapter packages (example: autogen-openeval-adapter).
What I'm proposing
Not a change to the harness itself — just two small, optional conversion functions (could live in benchmarks/utils/ or as a separate benchmarks-openeval-adapter package, whichever this repo prefers):
# sketch — field names taken from benchmarks/utils/models.py
from benchmarks.utils.models import EvalInstance, EvalOutput
def to_openeval_case(instance: EvalInstance, suite_id: str) -> dict:
"""EvalInstance -> an EvalPort testcase.json-shaped record."""
return {
"case_id": instance.id,
"suite_id": suite_id,
"input": instance.data,
}
def to_openeval_result(output: EvalOutput, suite_id: str) -> dict:
"""EvalOutput -> an EvalPort resultset.json-shaped record."""
return {
"suite_id": suite_id,
"case_id": output.instance_id,
"attempt": output.attempt,
"raw_result": output.test_result,
"error": output.error,
"cost_usd": getattr(output.metrics, "accumulated_cost", None)
if output.metrics
else None,
}
with the reverse direction (from_openeval_case → EvalInstance) letting an external OpenEval-format suite be dropped straight into prepare_instances().
Why this might be worth it for this repo specifically: with 20+ benchmark integrations already normalized to EvalInstance/EvalOutput, this would be the cheapest path to (a) comparing results across benchmarks and external tools in one place, and (b) letting other eval tooling consume benchmarks/ output without hand-writing a parser per benchmark.
Happy to put together a draft PR (either inside this repo under benchmarks/utils/, or as a standalone adapter package under evalport's adapters/) if this is a direction the maintainers are interested in — or to hear that it isn't a good fit given where the harness is headed.
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start by reading benchmarks/utils/models.py and CONTRIBUTING.md, then review the linked EvalPort specification and the existing benchmark output paths. Confirm with maintainers whether an in-repo utility or separate adapter is wanted before defining conversions in both directions. Done means an agreed scope and format mapping, followed by validation and tests for the accepted interface.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- python
- Domain
- tooling
- Issue type
- Feature
- Difficulty
- 5/5
- Estimated time
- Over a week
- Activity status
- Active
- Clarity
- Needs clarification
- Newbie friendliness
- 35/100