diff --git a/README.en.md b/README.en.md index e0696fa..e323ee6 100644 --- a/README.en.md +++ b/README.en.md @@ -2,30 +2,56 @@ [🇷🇺 Русский](README.md) · **🇬🇧 English** -A standalone harness to **run models against askads' MCP tools** (Yandex Direct / VK Ads / -Metrica) and **benchmark them against each other** on our domain (Russian ad analytics + -multi-step tool use) rather than on unrelated coding benchmarks. +A standalone harness to **run models against askads' MCP tools** (Yandex Direct / VK Ads / Metrica) and **benchmark them against each other** on our domain (Russian ad analytics + multi-step tool use) rather than on unrelated coding benchmarks. Two modes: -- **`fixed`** — deterministic fixtures (a frozen fake ad account served as `tool_result`). - Reproducible model comparison; runs in CI without network or account tokens. -- **`live`** — spawns REAL MCP servers over stdio (`mcp-yandex-direct`, etc.) with tokens - from env. Integration tests of the tools themselves against a live account. +- **`fixed`** — deterministic fixtures (a frozen fake ad account served as `tool_result`). Reproducible model comparison; runs in CI without network or account tokens. +- **`live`** — spawns REAL MCP servers over stdio (`mcp-yandex-direct`, etc.) with tokens from env. Integration tests of the tools themselves against a live account. -The engine and MCP client are **decoupled from askads** (extracted into `llmbench/`), so the -repository is self-contained. +The engine and MCP client are **decoupled from askads** (extracted into `llmbench/`), so the repository is self-contained. -> Full review of the harness and the list of fixed issues — see [`REVIEW.md`](REVIEW.md). +## Terms -## What is scored, and by whom +How to read the results table: -| Dimension | By | Where | +| Metric | What | Computed by | |---|---|---| -| **Tool-Use** (right tools succeed / order / call cap) | code | `scoring.score_tooluse` | -| **Numeric-Accuracy** (number correctness + entity anchoring, "don't invent CPA") | code | `scoring.score_numeric` | -| Interpretation / Russian / Edge handling | judge panel | `judges.py` | +| **Accuracy** | number correctness (CTR/CPC/CPA/spend) + right campaign attribution (entity anchoring), nothing invented | Scored by code | +| **Tools Use** | right tools called successfully, in the right order, nothing extra/forbidden | Scored by code | +| **Edge Cases** | behavior in edge cases (empty report, refusing a bid change, clarifying) | Scored by LLM judges | +| **Lang quality** | naturalness and clarity of the Russian | Scored by LLM judges | +| **Score** | a run's overall score = mean of the available components (see "How Score is computed") | — | +| **Cost per Answer** | mean cost of one answer, USD | — | +| **Score per USD** | "quality per dollar" (Score ÷ cost); higher = better value | — | +| **Stability** | `5 − spread of Score between repeats of a case`; higher = more stable | — | +| **⭐** | best quality/price balance: no other variant is both better and cheaper | — | -Key metrics are the backbone of the comparison; judges are strictly secondary. +## How Score is computed + +A run's `Score` is the **mean of the available components** (not all four columns at once): + +- **Tools Use** — always; +- **Accuracy** — if the case has golden facts (numeric cases); +- **Edge Cases** and **Lang quality** — if judges ran. + +The component set depends on the case, so: +- Score is **comparable** across variants (everyone runs the same cases) but is **not equal** to the mean of the four report columns; +- **failed runs** (API errors, token-limit truncation) are excluded from metrics — they show in a separate `Err` column; +- **`Stability = 5 − mean spread (σ) of Score between repeats of the same case`** — it captures model noise, not case difficulty. + +## Latest run results + +**[`results/2026-07-03/`](results/2026-07-03/results.en.md)** (+ Russian `results.ru.md`) — a fresh full grid (16 variants × 9 cases × 3 repeats = 432 runs, 0 errors, ≈ $18) on the fixed scoring. + +Top-3 by quality/price balance (⭐): + +| LLM | Thinking | Score | Cost/answer | Why it wins | +|---|---|--:|--:|---| +| **GLM-4.6** | no | 4.62 | $0.003 | best quality/price, ~27× cheaper than Opus | +| **GPT-4.1** | no | 4.93 | $0.013 | surprisingly strong and cheap | +| **Opus 4.8** | adaptive/high | 4.96 | $0.081 | quality ceiling | + +**Sonnet 4.6 (current production)** drops on edge cases (Edge ~3.3 — invents causes on an empty slice, doesn't clarify an ambiguous question). The `results/2026-06-29/` run is historical, before the scoring fixes. ## Layout @@ -65,67 +91,53 @@ npm install # installs mcp-yandex-direct, etc. RUN_BENCH=1 ANTHROPIC_API_KEY=… YANDEX_DIRECT_TOKEN=… \ python -m llmbench.runner --mode live --variants "GLM-4.6 disabled" --judges off ``` -Account-token env: `YANDEX_DIRECT_TOKEN` (+ optional `YANDEX_DIRECT_LOGIN`), -`YANDEX_METRIKA_TOKEN`, `VK_ADS_TOKEN`. Override a server path with -`MCP_PATH_YANDEX_DIRECT=/path/to/dist/index.js`. Live mode preflights (tokens + server -presence) BEFORE the first paid call. - -Flags: `--variants`, `--cases` (a typo in the filter is an error, not a silent full grid), -`--repeat`, `--judges panel|neutral|off`, `--concurrency N` (parallel runs within a variant), -`--dry-run` (shows the estimate without keys), `--out`, `--report-from `, -`--resume ` (catch up an interrupted run). The variant -list (model x thinking/effort/reasoning) lives in `llmbench/runner.py`; adding a model is one -line (don't forget the rate in `core.MODEL_RATES`, or the runner warns). + +Account-token env (for `--mode live`): + +| Env | Purpose | +|---|---| +| `YANDEX_DIRECT_TOKEN` (+ opt. `YANDEX_DIRECT_LOGIN`) | Yandex Direct token — required for live; LOGIN if the token is an agency token | +| `YANDEX_METRIKA_TOKEN` | Metrica token (for metrika cases) | +| `VK_ADS_TOKEN` | VK Ads token | +| `MCP_PATH_YANDEX_DIRECT` | optional — override the MCP server path (`/path/to/dist/index.js`) | + +Live mode preflights (tokens + server presence) BEFORE the first paid call. + +Runner flags: + +| Flag | What it does | +|---|---| +| `--mode fixed\|live` | fixtures (default) or real MCP servers | +| `--variants ` | which variants to run (a typo in the filter is an error, not a silent full grid) | +| `--cases ` | which cases to run (same typo guard) | +| `--repeat N` | repeats per case (default 2) | +| `--judges panel\|neutral\|off` | judge panel / neutral only / no judges | +| `--concurrency N` | parallel runs within a variant (default 4) | +| `--dry-run` | show the estimate (run/judge counts) without keys or spend | +| `--out ` | report directory (default `results//`) | +| `--report-from ` | rebuild the report (ru+en) from `runs.jsonl` for free | +| `--resume ` | catch up an interrupted run (only missing/failed keys) | + +The variant list (model x thinking/effort/reasoning) lives in `llmbench/runner.py`; adding a model is one line (don't forget the rate in `core.MODEL_RATES`, or the runner warns). ## Artifacts and re-scoring -Every run lands in a dated folder **`results//`**: the raw `runs.jsonl` (one record per -run — answer, tool trace, usage, all scores, errors) and the bilingual generated report -`results.ru.md` + `results.en.md`. `runs.jsonl` is the source of truth: both report versions -are rebuilt from it for free, with no repeat model calls — +Every run lands in a dated folder **`results//`**: the raw `runs.jsonl` (one record per run — answer, tool trace, usage, all scores, errors) and the bilingual generated report `results.ru.md` + `results.en.md`. `runs.jsonl` is the source of truth: both report versions are rebuilt from it for free, with no repeat model calls — ```bash python -m llmbench.runner --report-from results/2026-07-03/runs.jsonl ``` -`runs.jsonl` is **committed for fixed runs** (fake account, no private data; ~230 KB packed). -⚠️ **Live runs contain real account data — don't commit their `runs.jsonl`** (keep local / in a -private S3). The `.md` reports are in VCS. Top-3, prose and takeaways are added by hand on top of -the generated grid in the same dated folder. A second run on the same day doesn't clobber the -first (a time suffix is added on a date collision). - -**Interrupted (out of credits, Ctrl-C)?** Completed runs are already in `runs.jsonl` (written -line-by-line as they finish) — top up and catch up the rest, paying only for what's left: +`runs.jsonl` is **committed for fixed runs** (fake account, no private data; ~230 KB packed). ⚠️ **Live runs contain real account data — don't commit their `runs.jsonl`** (keep local / in a private S3). The `.md` reports are in VCS. Top-3, prose and takeaways are added by hand on top of the generated grid in the same dated folder. A second run on the same day doesn't clobber the first (a time suffix is added on a date collision). + +**Interrupted (out of credits, Ctrl-C)?** Completed runs are already in `runs.jsonl` (written line-by-line as they finish) — top up and catch up the rest, paying only for what's left: ```bash RUN_BENCH=1 …keys… python -m llmbench.runner --resume results/2026-07-03/runs.jsonl ``` -`--resume` skips already-successful `(variant, case, repeat)` keys, runs only the failed/missing -ones, appends to the same file, and rebuilds the report (on duplicates, success wins). You can -also add a key (e.g. `OPENAI_API_KEY`) and backfill variants skipped in the original run. - -## How Score is computed - -A run's `Score` is the mean of the **available** components: Tools Use (always), Accuracy (if -the case has golden facts), Edge Cases and Lang quality (if judges ran). The set depends on -the case, so Score is comparable across variants (everyone runs the same cases) but is NOT -equal to the mean of the four report columns. Failed runs (API errors, token-limit -truncation) are excluded from metrics and shown in a separate `Err` column. -`Stability = 5 − mean spread of Score between repeats of the same case` (not across cases of -differing difficulty). - -## Latest run results - -**[`results/2026-07-03/`](results/2026-07-03/results.en.md)** (+ Russian `results.ru.md`) — a -fresh full grid (16 variants × 9 cases × 3 repeats = 432 runs, 0 errors, ≈ $18) on the fixed -scoring: Top-3 + Pareto frontier + takeaways. In short: **GLM-4.6 without thinking** is the best -quality/price, **GPT-4.1** is surprisingly strong and cheap, **Opus 4.8 (adaptive/high)** is the -quality ceiling; **Sonnet (production)** drops on edge cases. The `results/2026-06-29/` run is -historical, before the scoring fixes. +`--resume` skips already-successful `(variant, case, repeat)` keys, runs only the failed/missing ones, appends to the same file, and rebuilds the report (on duplicates, success wins). You can also add a key (e.g. `OPENAI_API_KEY`) and backfill variants skipped in the original run. ## Known limitations -- **Case ceiling:** top models max out at 5.0 on Tool/Numeric → "parity" here means "both ace - THESE tasks". Harder cases are needed to truly separate quality. -- **Judges are secondary:** without a neutral vendor, the primary soft score is the panel mean - (advisory, self-preference possible). The comparison rests on the key metrics. +- **Case ceiling:** top models max out at 5.0 on Tool/Numeric → "parity" here means "both ace THESE tasks". Harder cases are needed to truly separate quality. +- **Judges are secondary:** without a neutral vendor, the primary soft score is the panel mean (advisory, self-preference possible). The comparison rests on the key metrics. - Model rates and cache multipliers are from price lists; verify against billing. - `glm-5`/`gpt-5`: availability ≠ identity of the expected model — verify. - `--repeat` is a coarse noise flag; "wrong number == missing" in numeric is a simplification. diff --git a/README.md b/README.md index 62000f3..99b0741 100644 --- a/README.md +++ b/README.md @@ -2,29 +2,56 @@ **🇷🇺 Русский** · [🇬🇧 English](README.en.md) -Самостоятельный харнесс, чтобы **гонять модели против MCP-тулз askads** (Яндекс Директ / -VK Ads / Метрика) и **бенчить их между собой** на нашем домене (русская рекламная аналитика -+ многошаговый tool-use), а не на чужих кодинг-бенчах. +Самостоятельный харнесс, чтобы **гонять модели против MCP-тулз askads** (Яндекс Директ / VK Ads / Метрика) и **бенчить их между собой** на нашем домене (русская рекламная аналитика + многошаговый tool-use), а не на чужих кодинг-бенчах. Два режима: -- **`fixed`** — детерминированные фикстуры (замороженный фейк-кабинет как `tool_result`). - Воспроизводимое сравнение моделей, гоняется в CI без сети/ключей кабинета. -- **`live`** — спавн РЕАЛЬНЫХ MCP-серверов по stdio (`mcp-yandex-direct` и т.д.) с токенами - из env. Интеграционные тесты самих тулов на живом кабинете. +- **`fixed`** — детерминированные фикстуры (замороженный фейк-кабинет как `tool_result`). Воспроизводимое сравнение моделей, гоняется в CI без сети/ключей кабинета. +- **`live`** — спавн РЕАЛЬНЫХ MCP-серверов по stdio (`mcp-yandex-direct` и т.д.) с токенами из env. Интеграционные тесты самих тулов на живом кабинете. Движок и MCP-клиент **развязаны от askads** (вынесены в `llmbench/`), репозиторий автономен. -> Полное ревью харнесса и список исправленных проблем — в [`REVIEW.md`](REVIEW.md). +## Термины -## Что и кто считает +Как читать таблицу результатов: -| Измерение | Кто | Где | +| Метрика | Что | Кто считает | |---|---|---| -| **Tool-Use** (нужные тулы успешно/порядок/кап) | код | `scoring.score_tooluse` | -| **Numeric-Accuracy** (точность чисел + entity-анкоринг, «не выдумывать CPA») | код | `scoring.score_numeric` | -| Интерпретация / Русский / Краевое | панель судей | `judges.py` | +| **Accuracy** | точность чисел (CTR/CPC/CPA/расход) + верная привязка к кампании (entity-анкоринг), без выдумок | Оценивается кодом | +| **Tools Use** | нужные тулы вызваны успешно, в нужном порядке, без лишних/запрещённых | Оценивается кодом | +| **Edge Cases** | поведение в краевых случаях (пустой отчёт, отказ менять ставку, уточнение) | Оценивается LLM-судьями | +| **Lang quality** | естественность и ясность русского | Оценивается LLM-судьями | +| **Score** | сводный балл прогона = среднее доступных компонент (см. «Как считается Score») | — | +| **Cost per Answer** | средняя стоимость одного ответа, USD | — | +| **Score per USD** | «качество на доллар» (Score ÷ цена); выше = выгоднее | — | +| **Stability** | `5 − разброс Score между повторами кейса`; выше = стабильнее | — | +| **⭐** | лучший баланс «качество/цена»: нет варианта, который был бы и качественнее, и дешевле одновременно | — | -Ключевые метрики — костяк сравнения; судьи строго вторичны. +## Как считается Score + +`Score` одного прогона — **среднее доступных компонент** (не всех четырёх колонок сразу): + +- **Tools Use** — всегда; +- **Accuracy** — если у кейса есть golden-факты (числовые кейсы); +- **Edge Cases** и **Lang quality** — если работали судьи. + +Состав компонент зависит от кейса, поэтому: +- Score **сравним** между вариантами (кейсы у всех одни), но **не равен** среднему четырёх колонок отчёта; +- **упавшие прогоны** (ошибки API, обрезка лимитом токенов) в метрики не входят — они в отдельной колонке `Err`; +- **`Stability = 5 − средний разброс (σ) Score между повторами одного кейса`** — ловит шум модели, а не разницу сложности кейсов. + +## Результаты последнего прогона + +**[`results/2026-07-03/`](results/2026-07-03/results.ru.md)** (+ англ. `results.en.md`) — свежий полный грид (16 вариантов × 9 кейсов × 3 повтора = 432 прогона, 0 ошибок, ≈ $18) на исправленном скоринге. + +Топ-3 по балансу «качество/цена» (⭐): + +| LLM | Thinking | Score | Cost/ответ | Чем берёт | +|---|---|--:|--:|---| +| **GLM-4.6** | нет | 4.62 | $0.003 | лучший «качество/цена», ~27× дешевле Opus | +| **GPT-4.1** | нет | 4.93 | $0.013 | неожиданно силён и дёшев | +| **Opus 4.8** | adaptive/high | 4.96 | $0.081 | потолок качества | + +**Sonnet 4.6 (текущий прод)** просел на краевых кейсах (Edge ~3.3 — выдумывает причины на пустом срезе, не уточняет неясный вопрос). Прогон `results/2026-06-29/` — исторический, до правок скоринга. ## Структура @@ -64,64 +91,53 @@ npm install # ставит mcp-yandex-direct и др. RUN_BENCH=1 ANTHROPIC_API_KEY=… YANDEX_DIRECT_TOKEN=… \ python -m llmbench.runner --mode live --variants "GLM-4.6 disabled" --judges off ``` -Env токенов кабинета: `YANDEX_DIRECT_TOKEN` (+ опц. `YANDEX_DIRECT_LOGIN`), -`YANDEX_METRIKA_TOKEN`, `VK_ADS_TOKEN`. Путь к серверу можно переопределить -`MCP_PATH_YANDEX_DIRECT=/path/to/dist/index.js`. Live-режим делает префлайт (токены + -наличие серверов) ДО первого платного вызова. - -Флаги: `--variants`, `--cases` (опечатка в фильтре — ошибка, а не молчаливый полный грид), -`--repeat`, `--judges panel|neutral|off`, `--concurrency N` (параллельные прогоны внутри -варианта), `--dry-run` (показывает смету без ключей), `--out`, `--report-from `, -`--resume ` (догнать прерванный прогон). -Список вариантов (модель × thinking/effort/reasoning) — в `llmbench/runner.py`; добавить -модель = одна строка (не забудь тариф в `core.MODEL_RATES`, иначе ранер предупредит). + +Env токенов кабинета (для `--mode live`): + +| Env | Назначение | +|---|---| +| `YANDEX_DIRECT_TOKEN` (+ опц. `YANDEX_DIRECT_LOGIN`) | токен Яндекс Директа — обязателен для live; LOGIN нужен, если токен агентский | +| `YANDEX_METRIKA_TOKEN` | токен Метрики (для metrika-кейсов) | +| `VK_ADS_TOKEN` | токен VK Ads | +| `MCP_PATH_YANDEX_DIRECT` | опц. — переопределить путь к MCP-серверу (`/path/to/dist/index.js`) | + +Live-режим делает префлайт (токены + наличие серверов) ДО первого платного вызова. + +Флаги ранера: + +| Флаг | Что делает | +|---|---| +| `--mode fixed\|live` | фикстуры (дефолт) или реальные MCP-серверы | +| `--variants <подстроки…>` | какие варианты гнать (опечатка в фильтре — ошибка, а не молчаливый полный грид) | +| `--cases ` | какие кейсы гнать (та же защита от опечатки) | +| `--repeat N` | повторов на кейс (дефолт 2) | +| `--judges panel\|neutral\|off` | панель судей / только нейтральные / без судей | +| `--concurrency N` | параллельных прогонов внутри варианта (дефолт 4) | +| `--dry-run` | показать смету (число прогонов/судейских) без ключей и трат | +| `--out ` | каталог отчёта (дефолт `results//`) | +| `--report-from ` | пересобрать отчёт (ru+en) из `runs.jsonl` бесплатно | +| `--resume ` | догнать прерванный прогон (только недостающие/упавшие ключи) | + +Список вариантов (модель × thinking/effort/reasoning) — в `llmbench/runner.py`; добавить модель = одна строка (не забудь тариф в `core.MODEL_RATES`, иначе ранер предупредит). ## Артефакты и пере-скоринг -Каждый прогон складывается в дата-папку **`results//`**: сырой `runs.jsonl` (по записи -на прогон — ответ, tool-трейс, usage, все оценки, ошибки) и двуязычный авто-отчёт -`results.ru.md` + `results.en.md`. `runs.jsonl` — источник правды: отчёт (обе версии) -пересобирается из него бесплатно, без повторных вызовов моделей — +Каждый прогон складывается в дата-папку **`results//`**: сырой `runs.jsonl` (по записи на прогон — ответ, tool-трейс, usage, все оценки, ошибки) и двуязычный авто-отчёт `results.ru.md` + `results.en.md`. `runs.jsonl` — источник правды: отчёт (обе версии) пересобирается из него бесплатно, без повторных вызовов моделей — ```bash python -m llmbench.runner --report-from results/2026-07-03/runs.jsonl ``` -`runs.jsonl` **под VCS для fixed-прогонов** (фейк-кабинет, приватных данных нет; ~230 КБ в паке). -⚠️ **Live-прогоны содержат данные реального кабинета — их `runs.jsonl` не коммить** (локально/приватный -S3). Отчёты `.md` — под VCS. Топ-3, прозу и выводы дописывают руками поверх сгенерированного грида в -той же дата-папке. Второй прогон за день не затирает первый (при коллизии по дате к папке добавляется время). +`runs.jsonl` **под VCS для fixed-прогонов** (фейк-кабинет, приватных данных нет; ~230 КБ в паке). ⚠️ **Live-прогоны содержат данные реального кабинета — их `runs.jsonl` не коммить** (локально/приватный S3). Отчёты `.md` — под VCS. Топ-3, прозу и выводы дописывают руками поверх сгенерированного грида в той же дата-папке. Второй прогон за день не затирает первый (при коллизии по дате к папке добавляется время). -**Прервался (обнулился баланс, Ctrl-C)?** Готовые прогоны уже в `runs.jsonl` (пишется построчно -по мере готовности) — долей баланс и догони остаток, платя только за него: +**Прервался (обнулился баланс, Ctrl-C)?** Готовые прогоны уже в `runs.jsonl` (пишется построчно по мере готовности) — долей баланс и догони остаток, платя только за него: ```bash RUN_BENCH=1 …ключи… python -m llmbench.runner --resume results/2026-07-03/runs.jsonl ``` -`--resume` пропускает уже успешные `(вариант, кейс, повтор)`, гоняет только упавшие/недостающие, -дописывает в тот же файл и пересобирает отчёт (при дублях успех побеждает). Можно и добавить -ключ (напр. `OPENAI_API_KEY`) и догнать варианты, пропущенные в исходном прогоне. - -## Как считается Score - -`Score` прогона = среднее **доступных** компонент: Tools Use (всегда), Accuracy (если у -кейса есть golden-факты), Edge Cases и Lang quality (если работали судьи). Состав зависит от -кейса, поэтому Score сравним между вариантами (кейсы у всех одни), но НЕ равен среднему -четырёх колонок отчёта. Упавшие прогоны (ошибки API, обрезка лимитом токенов) в метрики не -входят и видны отдельной колонкой `Err`. `Stability = 5 − средний разброс Score между -повторами одного кейса` (а не между кейсами разной сложности). - -## Результаты последнего прогона - -**[`results/2026-07-03/`](results/2026-07-03/results.ru.md)** (+ англ. `results.en.md`) — свежий -полный грид (16 вариантов × 9 кейсов × 3 повтора = 432 прогона, 0 ошибок, ≈ $18) на исправленном -скоринге: Топ-3 + Pareto-фронт + выводы. Кратко: **GLM-4.6 без thinking** — лучший «качество/цена», -**GPT-4.1** неожиданно силён и дёшев, **Opus 4.8 (adaptive/high)** — потолок качества; **Sonnet -(прод)** просел на краевых кейсах. Прогон `results/2026-06-29/` — исторический, до правок скоринга. +`--resume` пропускает уже успешные `(вариант, кейс, повтор)`, гоняет только упавшие/недостающие, дописывает в тот же файл и пересобирает отчёт (при дублях успех побеждает). Можно и добавить ключ (напр. `OPENAI_API_KEY`) и догнать варианты, пропущенные в исходном прогоне. ## Известные ограничения -- **Потолок кейсов:** топ-модели упираются в 5.0 по Tool/Numeric → «паритет» здесь = «оба - отлично решают ЭТИ задачи». Для строгого различения качества нужны более трудные кейсы. -- **Судьи вторичны:** без нейтрального вендора первичный мягкий балл = среднее панели - (advisory, возможна self-preference). Вес сравнения — на ключевых метриках. +- **Потолок кейсов:** топ-модели упираются в 5.0 по Tool/Numeric → «паритет» здесь = «оба отлично решают ЭТИ задачи». Для строгого различения качества нужны более трудные кейсы. +- **Судьи вторичны:** без нейтрального вендора первичный мягкий балл = среднее панели (advisory, возможна self-preference). Вес сравнения — на ключевых метриках. - Ставки/кэш-множители моделей — по прайс-листам; сверить с биллингом. - `glm-5`/`gpt-5`: доступность ≠ идентичность ожидаемой модели — сверить. - `--repeat` — грубый флаг шума; «неверное число == пропущенное» в numeric — упрощение. diff --git a/results/2026-07-03/results.en.md b/results/2026-07-03/results.en.md index 69b7b44..cd410df 100644 --- a/results/2026-07-03/results.en.md +++ b/results/2026-07-03/results.en.md @@ -8,32 +8,17 @@ _Run from 2026-07-03 12:39 UTC × **16 variants** (model × thinking/effort) × ## Terms (how to read the table) -- **Accuracy** (0–5) — numeric correctness: are CTR/CPC/CPA/spend computed right, nothing made - up, and are the numbers attributed to the right campaign (entity anchoring). **In code** - (deterministic). -- **Tools Use** (0–5) — tool correctness: called the right tools (successfully) in the right - order, nothing extra/forbidden. **Code**. -- **Edge Cases** (0–5) — behavior in edge cases (empty report, refusing to change a bid, - clarifying). **LLM judges** — they also score runs with tool violations. +- **Accuracy** (0–5) — numeric correctness: are CTR/CPC/CPA/spend computed right, nothing made up, and are the numbers attributed to the right campaign (entity anchoring). **In code** (deterministic). +- **Tools Use** (0–5) — tool correctness: called the right tools (successfully) in the right order, nothing extra/forbidden. **Code**. +- **Edge Cases** (0–5) — behavior in edge cases (empty report, refusing to change a bid, clarifying). **LLM judges** — they also score runs with tool violations. - **Lang quality** (0–5) — naturalness and clarity of the Russian. Judges. -- **Score** (0–5) — a run's overall score = mean of the available components: Tools Use - (always), Accuracy (if the case has golden facts), Edge Cases/Lang quality (if judges ran). - The component set depends on the case, so Score is comparable across variants (everyone runs - the same cases) but is NOT equal to the mean of the four left columns. Failed runs are - excluded from Score — see Err. -- **Cost per Answer** — mean cost of a successful run (USD); **Score per USD (s/m)** — "quality - per dollar" (Score ÷ cost) for single-/multi-step dialogs; higher = better value. -- **Stability** (0–5) — `5 − mean spread (σ) of Score between repeats of the same case`: - higher = more stable. Meaningful at repeat ≥ 2. -- **Err** — `failed/all runs` (API errors, token-limit truncation); suffix `·NR` — N runs - succeeded only after a retry with the same config. Failed runs are excluded from all metrics, - but their cost is included in the total run cost. -- **Thinking** — whether the model thinks before answering: `adaptive` (Claude/GLM), - `reasoning` (GPT-5), `no`. -- **Effort** — the "effort" budget per answer (`low/medium/high/max`); separate from thinking - (weak effect when thinking is off). Not configurable for GLM (`—`). -- **⭐** — **best quality/price balance**: a variant that can't be beaten — no other is both - better and cheaper. _(In optimization — the "Pareto frontier".)_ +- **Score** (0–5) — a run's overall score = mean of the available components: Tools Use (always), Accuracy (if the case has golden facts), Edge Cases/Lang quality (if judges ran). The component set depends on the case, so Score is comparable across variants (everyone runs the same cases) but is NOT equal to the mean of the four left columns. Failed runs are excluded from Score — see Err. +- **Cost per Answer** — mean cost of a successful run (USD); **Score per USD (s/m)** — "quality per dollar" (Score ÷ cost) for single-/multi-step dialogs; higher = better value. +- **Stability** (0–5) — `5 − mean spread (σ) of Score between repeats of the same case`: higher = more stable. Meaningful at repeat ≥ 2. +- **Err** — `failed/all runs` (API errors, token-limit truncation); suffix `·NR` — N runs succeeded only after a retry with the same config. Failed runs are excluded from all metrics, but their cost is included in the total run cost. +- **Thinking** — whether the model thinks before answering: `adaptive` (Claude/GLM), `reasoning` (GPT-5), `no`. +- **Effort** — the "effort" budget per answer (`low/medium/high/max`); separate from thinking (weak effect when thinking is off). Not configurable for GLM (`—`). +- **⭐** — **best quality/price balance**: a variant that can't be beaten — no other is both better and cheaper. _(In optimization — the "Pareto frontier".)_ ## Top-3 (best quality/price balance) @@ -95,4 +80,4 @@ Same caveat as before: these tasks are still easy for the top models (Accuracy/T - **No independent judge**: answers are scored by the same companies whose models are compared — possible self-model inflation; judge scores are auxiliary, weight is on the key metrics Tools Use/Accuracy (computed in code). - Mode `fixed`: models see clean test data (fixtures), not the "messy" real API output (use `--mode live` for that). -_Raw per-run data: `results/2026-07-03/runs.jsonl` — the report is rebuilt from it with `python -m llmbench.runner --report-from `._ \ No newline at end of file +_Raw per-run data: `results/2026-07-03/runs.jsonl` — the report is rebuilt from it with `python -m llmbench.runner --report-from `._ diff --git a/results/2026-07-03/results.ru.md b/results/2026-07-03/results.ru.md index d7809fb..fa16d54 100644 --- a/results/2026-07-03/results.ru.md +++ b/results/2026-07-03/results.ru.md @@ -8,29 +8,17 @@ _Запуск от 2026-07-03 12:39 UTC × **16 вариантов** (модел ## Термины (как читать таблицу) -- **Accuracy** (0–5) — точность чисел: верно ли посчитаны CTR/CPC/CPA/расход, не выдуманы ли - цифры и той ли кампании они приписаны (entity-анкоринг). **В коде** (детерминированно). -- **Tools Use** (0–5) — корректность инструментов: вызвал нужные тулы (успешно) в нужном - порядке, без лишних/запрещённых. **Код**. -- **Edge Cases** (0–5) — поведение в краевых случаях (пустой отчёт, отказ менять ставку, - уточнение). **LLM-судьи** — оценивают и прогоны с нарушениями по тулам. +- **Accuracy** (0–5) — точность чисел: верно ли посчитаны CTR/CPC/CPA/расход, не выдуманы ли цифры и той ли кампании они приписаны (entity-анкоринг). **В коде** (детерминированно). +- **Tools Use** (0–5) — корректность инструментов: вызвал нужные тулы (успешно) в нужном порядке, без лишних/запрещённых. **Код**. +- **Edge Cases** (0–5) — поведение в краевых случаях (пустой отчёт, отказ менять ставку, уточнение). **LLM-судьи** — оценивают и прогоны с нарушениями по тулам. - **Lang quality** (0–5) — естественность и ясность русского. Судьи. -- **Score** (0–5) — сводный балл прогона = среднее доступных компонент: Tools Use (всегда), - Accuracy (если у кейса есть golden-факты), Edge Cases/Lang quality (если судьи работали). - Состав компонент зависит от кейса, поэтому Score сравним между вариантами (кейсы у всех - одни), но НЕ равен среднему четырёх колонок слева. Упавшие прогоны в Score не входят — см. Err. -- **Cost per Answer** — средняя стоимость успешного прогона (USD); **Score per USD (s/m)** — - «качество на доллар» (Score ÷ цена) для одно-/многошаговых диалогов; выше = выгоднее. -- **Stability** (0–5) — `5 − средний разброс (σ) Score между повторами одного кейса`: - выше = стабильнее. Осмысленна при repeat ≥ 2. -- **Err** — `упавшие/все прогоны` (ошибки API, обрезка лимитом токенов); суффикс `·NR` — - N прогонов удались только после повтора тем же конфигом. Упавшие прогоны исключены из - всех метрик, но их стоимость входит в полную стоимость прогона. +- **Score** (0–5) — сводный балл прогона = среднее доступных компонент: Tools Use (всегда), Accuracy (если у кейса есть golden-факты), Edge Cases/Lang quality (если судьи работали). Состав компонент зависит от кейса, поэтому Score сравним между вариантами (кейсы у всех одни), но НЕ равен среднему четырёх колонок слева. Упавшие прогоны в Score не входят — см. Err. +- **Cost per Answer** — средняя стоимость успешного прогона (USD); **Score per USD (s/m)** — «качество на доллар» (Score ÷ цена) для одно-/многошаговых диалогов; выше = выгоднее. +- **Stability** (0–5) — `5 − средний разброс (σ) Score между повторами одного кейса`: выше = стабильнее. Осмысленна при repeat ≥ 2. +- **Err** — `упавшие/все прогоны` (ошибки API, обрезка лимитом токенов); суффикс `·NR` — N прогонов удались только после повтора тем же конфигом. Упавшие прогоны исключены из всех метрик, но их стоимость входит в полную стоимость прогона. - **Thinking** — думает ли модель перед ответом: `adaptive` (Claude/GLM), `reasoning` (GPT-5), `нет`. -- **Effort** — бюджет «усилий» на ответ (`low/medium/high/max`); отдельная от thinking - настройка (при выключенном thinking влияет слабо). У GLM не настраивается (`—`). -- **⭐** — **лучший баланс «качество/цена»**: вариант, который нельзя «побить» — нет другого, - который и качественнее, и дешевле. _(В оптимизации — «Pareto-фронт».)_ +- **Effort** — бюджет «усилий» на ответ (`low/medium/high/max`); отдельная от thinking настройка (при выключенном thinking влияет слабо). У GLM не настраивается (`—`). +- **⭐** — **лучший баланс «качество/цена»**: вариант, который нельзя «побить» — нет другого, который и качественнее, и дешевле. _(В оптимизации — «Pareto-фронт».)_ ## Топ-3 (лучший баланс «качество/цена») @@ -92,4 +80,4 @@ _Для ориентира: текущий прод askads — Sonnet 4.6 (think - **Независимого судьи нет**: ответы оценивают те же компании, чьи модели и сравниваются — возможно завышение «своей» модели; оценки судей вспомогательные, вес на ключевых метриках Tools Use/Accuracy (их считает код). - Режим `fixed`: модели видят аккуратные тестовые данные (фикстуры), а не «грязный» реальный вывод API (для этого `--mode live`). -_Сырые per-run данные: `results/2026-07-03/runs.jsonl` — отчёт пересобирается из них командой `python -m llmbench.runner --report-from <файл>`._ \ No newline at end of file +_Сырые per-run данные: `results/2026-07-03/runs.jsonl` — отчёт пересобирается из них командой `python -m llmbench.runner --report-from <файл>`._