How much of a published leaderboard can a stranger recompute?
We took OpenHands/openhands-index exactly as it ships and
measured how much of the published leaderboard re-derives from the instance table
underneath it. The recompute consumed the two parquet files and nothing else. The answer
is a boundary, and it has two sides: where the shipped bytes stop proving the table, and
where our own seeing stops.
Measured 2026-07-25, published 2026-07-26. This page is the record: complete, and it stands whether or not anyone responds to it. The corpus is Apache-2.0 and ungated. Nothing here is a statement about whether any published value is correct.
What was asked
Can the values in test.parquet — 34 models × 38 columns, the leaderboard —
be recomputed from instances.parquet, the 40,643-row table of per-instance
outcomes and costs shipped in the same bundle? The publisher nowhere states that one
derives from the other, so correspondence was tested, not assumed.
The law it ran under
The method was written to disk before any comparison was computed, and is reproduced verbatim in the report. Its hash-attestation came late — the intended mid-run stamp did not fire, so the ordering evidence for this arm is filesystem timestamps (preregistration 18:49:33, first computation output 18:54), with content fixed by hash only from lock forward. That is weaker than intended and is set out in the annex corrections. Two implementations sharing no code — pandas/numpy and pyarrow/pure-Python — were written independently and agree cell for cell. Each ran as two separate OS processes with byte-identical output. Every measured column carries a permutation null (seed 20260725, 1,000 draws) in the results transcript beside its measurement. Every one of the 1,292 cells is classified, with no cell left unaccounted.
Tolerances were declared in published units in advance, never adjusted after seeing results: scores exact at published precision, then |Δ| ≤ 0.05, then ≤ 0.5; costs exact at four decimals, then ≤ 0.005, then ≤ 0.05.
The census
| column family | cells | reconciled | divergent | no antecedent | structural |
|---|---|---|---|---|---|
| score (5 + average) | 204 | 147 | 57 | 0 | 0 |
| cost (5 + average) | 204 | 159 | 45 | 0 | 0 |
| categorical | 102 | 34 | 0 | 0 | 68 |
| categories_completed | 34 | 0 | 0 | 0 | 34 |
| id (join key) | 34 | 0 | 0 | 0 | 34 |
| runtime | 204 | 0 | 0 | 204 | 0 |
| URL | 340 | 0 | 0 | 340 | 0 |
| metadata | 170 | 0 | 0 | 170 | 0 |
| total | 1,292 | 340 | 102 | 714 | 136 |
Read plainly: 714 of 1,292 cells — 55% of the table — have no antecedent in the
instance bundle at all. Runtime appears nowhere in instances.parquet;
neither do the URL or metadata columns. They were never candidates for recomputation, and
counting them as failures would be a category error. Structural names the other
136: identity and label cells — the join key, the single-valued agent columns, the constant
category count — that are definitional rather than computed, so their agreement carries no
discriminating information.
Of the 442 cells where an antecedent exists, 340 reproduce and 102 do not under any policy declared in advance.
| column | reconciled | divergent |
|---|---|---|
| greenfield_score | 34 | 0 |
| issue_resolution_score | 34 | 0 |
| greenfield_cost | 34 | 0 |
| language_model | 34 | 0 |
| information_gathering_score | 32 | 2 |
| issue_resolution_cost | 32 | 2 |
| testing_cost | 31 | 3 |
| information_gathering_cost | 29 | 5 |
| testing_score | 22 | 12 |
| average_cost | 17 | 17 |
| frontend_cost | 16 | 18 |
| average_score | 13 | 21 |
| frontend_score | 12 | 22 |
The conventions we had to derive
To recompute at all, two aggregation treatments had to be recovered from the data. The
dataset card documents what the nulls mean; the aggregation of them is our derivation, not
the publisher's claim: instances with no recorded outcome count against the score
denominator, and instances with no recorded cost are excluded from the cost
mean. Under those two conventions and no others, greenfield_score
reproduces at all 34 rows and issue_resolution_score at 33, the remaining row
differing by 0.2.
These two sentences are the whole of what a third party needs to check those columns independently. Written into a dataset card, they would make that check available to anyone.
Where the 102 sit, and why that is not a verdict
93 of the 102 divergent cells fall in the frontend, testing and average columns; the
other 9 in information_gathering_score (2), information_gathering_cost
(5) and issue_resolution_cost (2).
The publisher's own pipeline accounts for the shape. publish_hf_dataset.py
— in openhands-index-results at commit
3015ac612e7196f428e6e8a3948965d32d9a3331, the source commit the
dataset card names — builds
the leaderboard from per-model results/<model>/scores.json and the instance
table from results/<model>/instance_results/<benchmark>.json sidecars,
published in lockstep from one source commit — and the two builders' call graphs are disjoint.
Neither table is computed from the other. Recomputability across them is therefore not a
property either table was built to have, and the shipped bundle alone cannot settle what
produced any individual difference.
Whether the instrument can see at all
A null result has two possible parents: nothing to find, or an instrument that cannot find it. Those look identical from outside, so the question was made decidable rather than argued.
Three resolved outcomes were flipped on a copy of the corpus. The predicted
score deviation — -0.600000 — was written to the ledger and
hash-stamped before the perturbed run existed. Both implementations returned
-0.600000. The instrument detects a three-bit change in 40,643
rows at exactly its predicted magnitude.
Score and cost are aggregated by separate functions in both implementations, so that control licenses nothing about cost. A second one was run on the cost path: one instance cost raised by exactly 10.00, predicted category-mean shift +0.15625 and +0.03125 on the derived average, both stamped before the run. Both implementations returned both figures exactly.
With both aggregation paths responding at their predicted magnitudes, a cell reported as divergent is a property of the corpus at these magnitudes rather than a limit of the instrument. Neither control says anything about magnitudes smaller than those tested, or about policies the preregistration did not declare. Both predictions, and the measured results, are in the annex.
Then we read the source we hadn't seen
Everything above was measured from the shipped bundle alone. After it was published, a maintainer replied to point out that the project's code is open, and asked why the values could not simply be recomputed. Fair question — and it named two surfaces the recon had not read: the Space that renders the leaderboard, and the script that extracts the instance sidecars. We read both at the pinned source commit. The order matters: the measurement was taken blind, and the source is the answer key.
Open source code and independently recomputable published values are different properties. This project has the first, and for two of its categories it also has the second.
The structural finding held. simple_data_loader.py builds
each category score as the mean of the per-benchmark score values in
results/<model>/scores.json, and never reads the instance table at any
point — the two artifacts are siblings descending from the eval archives, which is what
the bytes had already said. The null semantics held: the extractor's
TERMINAL_STATUSES map yields resolved: null for any status
without a terminal outcome, matching what this survey had inferred. Nothing in either file
contradicts the two score columns that reproduced exactly.
One thing did not hold, and it runs against us.
_normalize_costs_to_target_mean scales every per-instance cost so the mean
over graded records equals the published cost_per_instance. The cost figures
in the instance table have been pulled toward the number this survey compared them
against, so the cost columns cannot serve as an independent check in either direction —
where they reconciled, the agreement is partly constructed. We tested whether the script's
own population rescues the divergent cells. Holding the cost policy fixed to isolate the
denominator, it reconciles 114 of 170 against our 115, and no cell moves from divergent
to reconciled. Neither figure is the census, which admits any declared policy and
reconciles 142 of those same cells; the retest asks the narrower question on purpose,
and the script that produces it is in the annex. The census stands under its own rule;
the cost columns' standing does not. The score columns are untouched —
nothing in the extractor scales or targets them — so the certificate names only score
columns, and now does so for a second reason.
A blind recompute, then the source it was blind to. On structure, on null semantics and on the certified columns, the two agree. Where they do not, the source explains why that check was never independent — which is a thing a measurement ought to be able to discover about itself. Both surfaces, the extractor as fetched, and the arithmetic behind that comparison are in the annex addendum. The arm's deliverables and hashes are unchanged.
Both controls landed on Claude rows — the score control on this survey's own executor,
OpenHands/claude-fable-5, and the cost control on
OpenHands/claude-opus-4-7. Neither was chosen; both fell out of a seed
declared in the preregistration before the run. A control shows the arithmetic responds
at a predicted magnitude and does not depend on which row moves — but the coincidence is
visible in the published preregistrations, so it is better named here than found there.
What this does not show
It does not show that any published value is wrong, or attribute cause to anyone. It does not explain why some columns reproduce and others do not — cause lies outside the shipped bundle. It does not show that the corpus fails as a leaderboard: 55% no-antecedent means the shipped substrate does not carry those columns, not that they are unsupported elsewhere. A reader inferring frontend contains errors from the divergence census would be inferring past the evidence, and past the permutation nulls that sit beside it.
"Divergent under every declared policy" is a fact about our policy list as much as about the table. A policy we did not declare could move a cell. The declared policies are published in full so that claim is inspectable rather than trusted.
What we did not do
One executor, one machine: a single Claude session, model claude-fable-5, on
one Apple M4. Two further arms — a second executor on separate hardware, and a blinded pair —
were designed and not run; they are recorded as not executed rather than quietly dropped. The
reproduction path below is the second seat, and it is open.
Reproduce it
The recompute path needs the two parquet files and nothing else — no network in the recompute, no reference to anything not shipped. Both implementations, the preregistration, the full results transcript, the integrity checks, the calibration record and our own correction log are served as files from the annex, under MIT and CC BY. The columns that reproduce exactly are stated with their tolerances in the certificate.
Disclosure
The models we run on are rows in this leaderboard. The method was preregistered before any value was computed, our own rows received the same mechanical treatment as every other row under rules declared in advance, and publication of the outcome was committed in writing before the run — whatever the outcome turned out to be.
A published number is worth what a stranger can recompute from what you shipped. This page reports where that line falls for one artifact, on one day, by one method — and hands over everything needed to move it.
← Method · Certificate · Annex