Производительность4 августа 2026 г. · 5 мин чтения

SLO-гейты стали нативными — thresholds в стиле k6, без клеевых скриптов

perfscale v0.8.1 приносит std/thresholds@v1: SLO-гейты уровня прогона, которые вычисляют выражения вида p95<500 по метрикам всего прогона, завершают его ненулевым кодом при нарушении и пишут результат в summary JSON. Бесплатно для всех, в open-source-движке.

Автор: Команда Perfscale

SLO-гейты стали нативными — thresholds в стиле k6, без клеевых скриптов

Нагрузочный тест, который завершился зелёным, но промахнулся мимо SLO по латентности, — это ложная зелень. До сих пор поймать такое можно было только клеем: --summary-export в jq, пара строк awk по перцентилям из stdout или обёртка-скрипт, которую никто не хочет поддерживать. Инлайн-блоки check: намеренно мягкие — они печатают и считают провалы, но прогон всё равно завершается с кодом 0, потому что check — это обратная связь, а не вердикт.

Начиная с v0.8.1, вердикт встроен в движок. std/thresholds@v1 приносит в perfscale threshold-выражения в стиле k6: SLO-гейты уровня прогона, вычисляемые один раз, после остановки всех VU, по метрикам, собранным за весь прогон. И как остальное семейство std/*, это бесплатно для всех — код живёт в OSS-репозитории под двойной лицензией MIT/Apache-2.0.

Гейты живут в after:

after:
  - name: slo gate
    use: std/thresholds@v1
    with:
      http_req_duration: ["p95<500", "avg<300", "max<2000"]
      http_req_failed: ["rate<0.01"]
    severity: fail
    message: "checkout SLO"

Нарушенный fail-гейт печатает http_req_duration p95=612ms ≥ 500ms; checkout SLO, и прогон завершается ненулевым кодом — красная джоба в CI, только без клея. severity: warn и info печатают предупреждение, не роняя прогон, — для бюджетов, которые вы ещё подбираете. Несколько гейтов комбинируются: побеждает худший статус.

Честные цифры по построению

Два свойства делают эти гейты надёжнее обёрток-скриптов:

  • Те же самые гистограммы. Гейты вычисляются по тем же HDR-гистограммам, которые печатает итоговая сводка. p95<500 сравнивается ровно с тем p95, который вы видели в консоли, — никакого расхождения между тем, что вы читали, и тем, что проверял CI.
  • Громкие ошибки. Неизвестная метрика, пустой with:, непарсящееся выражение или агрегат, не подходящий типу метрики, роняют и гейт, и прогон. Зелёный гейт всегда значит: метрика существовала, выражение распарсилось, число удержалось.

Выражения — это <агрегат><оператор><число>: агрегаты — avg, min, max, p50, p90, p95, p99, count, rate. Какие применимы — зависит от метрики: сэмплируемые метрики (http_req_duration, grpc_msg_rtt, ws_msg_rtt, db_query_duration, …) принимают перцентили; счётчики — только count; а каждое семейство длительностей автоматически порождает метрику <family>_failed, так что rate<0.05 работает без лишней инструментации.

Сделано для пайплайнов

Каждый гейт отдаёт структурированный результат — статус, читаемую сводку нарушений и список violations по выражениям, — а summary JSON прогона (perfscale run --summary-export) получает поле thresholds той же формы. Дашборды и аннотации в PR читают результаты гейтов без парсинга stdout; на платформе результаты гейтов показываются в прогоне рядом с метриками, которые они оценивали.

В CI это просто «запустить тест»: GitHub Action или шаблоны GitLab CI выполняют конфиг как есть, а нарушенный fail-гейт красит джобу в красный. Никаких jq, awk и обёрток.

С чего начать

Обновляйтесь через perfscale self-update — и пусть ваш следующий зелёный прогон что-то да значит.

Комментарии

Ответить в Bluesky