FRST beta
BelépésLog in

2026-09-13 · 5 perc olvasás13 Sep 2026 · 5 min read

A hamis zöldFalse green

Ha ugyanaz a csapat írja a kódot és a tesztet, a zöld pipa sokszor csak annyit jelent, hogy a csapat egyetért önmagával. Így építettünk olyan mérést, amelyik ezt észreveszi.

When the same team writes both the code and the tests, a green tick often only means the team agrees with itself. This is how we built a measurement that notices.

A probléma: önmagával konzisztens, de nem helyesThe problem: self-consistent, not correct

Az FRST-ben egy csapat AI-munkás dolgozik egy célon: van, aki a backendet írja, van, aki a teszteket. Kézenfekvőnek tűnik, hogy ha a tesztek zöldek, a munka kész. Csakhogy a tesztíró munkás ugyanazt a tervet és ugyanazt a kódot látja, mint a többiek, ezért a teszt könnyen az implementációhoz igazodik, nem a követelményhez. Az eredmény önmagával konzisztens, de nem feltétlenül helyes.

In FRST a team of AI workers pursues one goal: one writes the backend, another writes the tests. It seems obvious that green tests mean the job is done. But the test writer sees the same plan and the same code as everyone else, so the tests drift towards the implementation rather than the requirement. The result is consistent with itself, but not necessarily correct.

Két mintát láttunk újra és újra. Az egyikben a teszt futásidőben derítette fel az interfészt – végigjárta az app.url_map-et az iter_rules segítségével, és azt tesztelte, amit talált. A másikban egyszerre több mezőnevet küldött el, hogy biztosan „eltaláljon” valamit:

We kept seeing two patterns. In the first, the test discovered the interface at runtime – it walked app.url_map via iter_rules and tested whatever it found. In the second, it sent several field names at once, just to be sure one of them would “hit”:

# szemléltető példa – ilyen tesztet NEM szeretnénk
resp = client.post("/api/notes", json={"body": "szia", "content": "szia"})
assert resp.status_code in (200, 201)
# illustrative example – the kind of test we do NOT want
resp = client.post("/api/notes", json={"body": "hi", "content": "hi"})
assert resp.status_code in (200, 201)

Az ilyen teszt nem tud megbuktatni egy rossz interfészt. Ha a cél body mezőt kér, de a kód content-et vár, a teszt ettől még zöld.

A test like that cannot fail a wrong interface. If the goal asks for a body field but the code expects content, the test stays green anyway.

1. megoldás: független mérés, rejtett tesztekkelFix 1: an independent harness with hidden tests

Építettünk egy mérőrendszert, amely rögzített feladatokon futtatja végig a teljes csapatot. A végén egy független teszt (evals_check/test_contract.py) ellenőrzi az eredményt – ezt a csapat soha nem látja, és a cél szövegében rögzített interfészre ír elő elvárásokat. Minden futás négy ítélet egyikét kapja:

We built an evaluation harness that runs the whole team on fixed tasks. At the end an independent test (evals_check/test_contract.py) checks the result – the team never sees it, and it asserts the interface written into the goal text. Every run gets one of four verdicts:

A hamis zöld a legfontosabb szám: megmutatja, hányszor hazudott a rendszer.
False green is the number that matters most: it counts how many times the system lied.

2. megoldás: a kitérő tesztek tiltásaFix 2: banning evasive tests

A tesztíró munkás promptja kifejezetten tiltja a futásidejű felderítést és a többféle mezőnév egyidejű küldését. A kapuőr – az LLM, amely csak akkor szólal meg, ha minden determinisztikus kapu zöld – az ilyen tesztet értéktelennek minősíti és visszadobja. A teszt dolga, hogy a célban leírt interfészt számon kérje, nem az, hogy megtalálja, ami éppen van.

The test writer’s prompt explicitly forbids runtime discovery and sending multiple field names at once. The gatekeeper – the LLM that only speaks up once every deterministic gate is green – rates such a test as worthless and sends it back. A test’s job is to hold the code to the interface in the goal, not to find whatever happens to be there.

3. megoldás: a nulla teszt nem sikerFix 3: zero tests is not success

Volt olyan futásunk, amely zöldnek látszott, pedig egyetlen teszt sem töltődött be. Ha a pytest nem tudja betölteni a tesztfájlt, akkor nulla teszt fut le – és nulla bukás is. Ezt ma külön jelzésként kezeljük: a „nulla lefutott teszt” nem siker, a betöltési hiba pedig hiba.

We had a run that looked green although not a single test had loaded. If pytest cannot load a test file, zero tests run – and zero fail. We now treat this as its own signal: “zero tests executed” is not success, and a collection error is an error.

A számokThe numbers

2026-09-13-án, a 0.9.2-es változattal 11 feladatot futtattunk (8 új projekt és 3 meglévő bővítése). Ugyanazon a napon a teljes sort háromszor is lefuttattuk.

On 13 September 2026, with version 0.9.2, we ran 11 tasks (8 new projects and 3 extensions of existing ones). On the same day we also ran the full set three times over.

MérésFutásOKHAMIS ZÖLDBUKOTTKöltség
11 feladat × 11111001,06 USD
11 feladat × 33330123,64 USD
Run setRunsOKFALSE GREENFAILEDCost
11 tasks × 1111100USD 1.06
11 tasks × 3333012USD 3.64

A 11/11 szép, de a 33 futás mutatja a teljes képet: a szórás valós. Ugyanaz a feladat változatlan kóddal is adhat más eredményt, mert a modellek nem determinisztikusak. Ezért ismétlünk, és ezért nem hirdetünk egyetlen szerencsés futást eredményként.

11/11 looks nice, but the 33 runs tell the full story: the variance is real. The same task with unchanged code can produce a different outcome, because the models are not deterministic. That is why we repeat runs, and why we never present a single lucky run as a result.

Tanulság. Amit nem egy független teszt mér, arról nem állítjuk, hogy működik.

Takeaway. If an independent test hasn’t measured it, we don’t claim it works.

KapcsolódóRelated