Сессионные рецепты и экспорт Go-коллектора
Сессионная экономика bootstrap-once/per-request и экспорт автономного Go-клиента.
Сессионный рецепт фиксирует, в чём экономия API-сессии: какой вызов единожды создаёт сессионный кортеж, как долго этот кортеж остаётся валидным и какие поля нужно пересчитывать при каждой отправке. Когда рецепт совпадает с наблюдаемым трафиком, Traffic Jam транспилирует его — вместе с кодеком декодирования, функциями вывода и обвязкой mTLS — в автономный Go-коллектор, который можно собрать и запустить вне воркспейса. Обе функции находятся в API lab на вкладке Collector → представление Recipes.
Сессионная экономика: bootstrap один раз, вывод на каждый запрос
Рецепт — это упорядоченный список шагов, каждый со своей ролью:
| Роль | Когда выполняется | Назначение |
|---|---|---|
bootstrap | Один раз за сессию, пока его извлечения устарели | Создаёт сессионный кортеж (например, вызов /event, возвращающий сессионные куки/значения CSRF). Его извлечения кэшируются и переиспользуются. |
per-request | При каждом запуске рецепта | Собственно рабочий вызов; производные поля (подписанные куки, метки времени, nonce) пересчитываются при каждой отправке. |
Свежесть bootstrap ограничена двумя регуляторами, оба опциональны (0 = без ограничений):
- max age (секунды) — bootstrap перезапускается, когда последний запуск старше этого значения.
- max uses — bootstrap перезапускается после того, как столько запусков рецепта использовали кортеж.
Пока кортеж свежий, шаги bootstrap пропускаются (отчёт о запуске показывает skipped (fresh)), и срабатывают только шаги per-request. Неудачный bootstrap инвалидирует сессию и немедленно останавливает запуск.
Сборка рецепта из наблюдаемого трафика
- Откройте API lab, переключитесь на вкладку Collector, затем на представление Recipes.
- В разделе New recipe введите Name и границы свежести bootstrap (по умолчанию:
600секунд,25использований). - Выберите запрос Bootstrap и запрос Per-request из загруженных сессий захвата.
- Объявите извлечения bootstrap, по одному на строку, в формате
name=source:expression:
gssc=json:data.cs.gssc
cfids=json:data.cs.cfids
token=header:X-Session-Token
trace=regex:"traceId":"([0-9a-f]+)"
Поддерживаемые источники: json (путь через точки, начальный $. опционален), header, cookie (из Set-Cookie) и regex (первая группа захвата или всё совпадение).
5. Нажмите Store recipe. Рецепт сохраняется в базу проекта (с зеркалом в localStorage под ключом traffic-jam:session-recipes как офлайн-кэш); состояние запуска (время последнего bootstrap, счётчик использований, кэшированные извлечения) хранится в localStorage под traffic-jam:recipe-runtimes.
Запуск рецепта
Нажмите Run на рецепте. Раннер проходит шаги по порядку, проигрывая каждый захваченный запрос через обычный путь replay (так что правила безопасности replay по-прежнему действуют). Извлечённые значения bootstrap сливаются с набором переменных, видимых отправлениям per-request, — тот же механизм {{name}}, описанный в /docs/ru/replay/variables/.
Отчёт Last run показывает бейдж по каждому шагу: HTTP-статус, skipped (fresh) для кэшированного bootstrap или error с сообщением. Шаг, чей захваченный запрос больше не загружен, сообщает step request is not loaded.
[!WARNING] Запуски рецепта проигрывают реальные запросы, включая захваченные учётные данные, и автоматически подтверждают методы, меняющие состояние. Запускайте рецепты только против систем, которые вам разрешено тестировать.
Экспорт автономного Go-коллектора
Нажмите Export Go на рецепте. Генератор поднимает эндпоинты, упорядоченные заголовки и куки из захваченного запроса каждого шага, транспилирует ваши шаблоны вывода в Go и скачивает единый main.go.
Выводы объявляются в поле Derivations for collector export, по одному на строку, в формате target = template (разбиение по первому =). Шаблон использует ту же DSL вычисляемых полей, что и replay:
cookie:fgssca-goldapple = p = randomHex:4; p + sha1(fgsscSecret + cookie:gssca-goldapple + p) | skip:4
Транспайлер поддерживает следующие конструкции:
| DSL | Сгенерированный Go |
|---|---|
sha1(x), md5(x), sha256(x) | tjSha1Hex / tjMd5Hex / tjSha256Hex |
hmac-sha1(key, x), hmac-sha256(key, x) | tjHmacSha1 / tjHmacSha256 |
base64(x), crc32(x) (без аргумента → body) | tjBase64 / tjCrc32 |
nowMs(), nowSec(), uuid4(), randomHex:n | tjNowMs / tjNowSec / tjUUID / tjRandomHex |
cookie:n, header:n, query:n, var:n, body | поиск в картах cookie/header/query/var |
пайпы | skip:n (trunc), | take:n (prefix), | upper, | lower, | urlencode, | base64 | tjSkip / tjTake / strings.To* / tjURLEncode / tjBase64 |
утверждения name = expr; … | локальные переменные, чтобы nonce мог совпадать в двух местах |
Что содержит сгенерированный код
- Заголовок
DO NOT EDIT by hand — regenerate from the session recipe insteadплюс комментарий, описывающий экономику bootstrap max-age/max-uses. sessionState(StartedAt,Uses,Vars) с методомfresh(), кодирующим границы свежести.doRequest— хелпер, который выставляет упорядоченные заголовки, сериализует cookie jar в порядке сортировки имён и ограничивает чтение ответа 4 MiB.- По одной функции
step_<id>на каждый шаг рецепта: захваченные заголовки и куки, JSON-извлечения через обходчик путиdigString, извлечения заголовков черезresponseHeaders.Get. - По одной функции
derive_<target>на каждый вывод, вызываемой вrun()перед отправлениями per-request. - Набор хелперов
tj*и пакетный кодек Group-IB (manglePacket/unmanglePacket, позиционно-зависимый сдвиг символов плюс обёртка CRC32). - Обвязка mTLS:
tls.LoadX509KeyPair,http.Clientс таймаутом 30 с,ForceAttemptHTTP2иMinVersion: tls.VersionTLS12.
Сборка и запуск коллектора
Экспорт скачивает main.go (пакет main). Соберите его как обычный Go-модуль:
mkdir productcard && cd productcard
go mod init productcard
mv ../Downloads/main.go .
go build ./...
Запустите его, указав клиентский сертификат (объединённый PEM с сертификатом и ключом):
CLIENT_CERT=client.pem ./productcard
# or
./productcard -cert client.pem
Флаг -cert по умолчанию берёт $CLIENT_CERT, с фолбэком на client.pem. См. /docs/ru/replay/fingerprints/ о том, как воркспейс управляет клиентскими сертификатами, и /docs/ru/collector/conformance/ о проверке отпечатка коллектора относительно эталонного захвата.
Поведение экспорта и ограничения
| Область | Поведение |
|---|---|
Извлечения regex | Подключены к хелперу regexExtract, который возвращает первую группу захвата или всё совпадение, если групп нет. |
| Цели вывода | Цели cookie:name, header:name, query:name, json:path и body автоматически внедряются в запрос. |
| Нетранспилируемый шаблон | Экспорт отказывается и возвращает ошибку с именем цели вместо выдачи TODO-заглушки для ручного переноса — исправьте шаблон и повторите экспорт. |
| Переключатели экспорта в UI | Панель Recipes всегда выдаёт обвязку mTLS и кодек Group-IB. |
| Тело bootstrap | При включённом кодеке шаг bootstrap без явного тела отправляет manglePacket(vars["packet"]). |
| Хранение | Рецепты синхронизируются с базой проекта; состояние запуска (время последнего bootstrap, счётчик использований, кэшированные извлечения) живёт только в localStorage браузера и не расшаривается. |
[!NOTE] Сгенерированный коллектор — это отправная точка для авторизованного клиента с ограничением частоты против системы, которой вы владеете или которую вам разрешено тестировать: перед запуском проверьте выдаваемые заголовки, тела и обработку сертификатов.