본문으로 건너뛰기

Batch Processing

Batch processing을 사용하면 수백 개 또는 수천 개의 prompt에 대해 Hermes agent를 병렬로 실행하고, 구조화된 trajectory data를 생성할 수 있습니다. 주된 용도는 training data generation입니다. 즉 fine-tuning이나 evaluation에 사용할 수 있는 ShareGPT 형식의 trajectory와 tool usage statistics를 만드는 데 사용됩니다.

개요

batch runner(batch_runner.py)는 prompt가 들어 있는 JSONL dataset을 처리합니다. 각 prompt는 tool access가 있는 완전한 agent session을 통해 실행되며, prompt마다 격리된 환경을 받습니다. 출력은 전체 대화 기록, tool call 통계, reasoning coverage metric을 포함한 구조화된 trajectory data입니다.

빠른 시작

# Basic batch run
python batch_runner.py \
--dataset_file=data/prompts.jsonl \
--batch_size=10 \
--run_name=my_first_run \
--model=anthropic/claude-sonnet-4.6 \
--num_workers=4

# Resume an interrupted run
python batch_runner.py \
--dataset_file=data/prompts.jsonl \
--batch_size=10 \
--run_name=my_first_run \
--resume

# List available toolset distributions
python batch_runner.py --list_distributions

dataset 형식

입력 dataset은 JSONL 파일입니다. 한 줄에 JSON object 하나가 들어갑니다. 각 entry에는 반드시 prompt field가 있어야 합니다.

{"prompt": "Write a Python function that finds the longest palindromic substring"}
{"prompt": "Create a REST API endpoint for user authentication using Flask"}
{"prompt": "Debug this error: TypeError: cannot unpack non-iterable NoneType object"}

entry에는 선택적으로 다음 field를 포함할 수 있습니다.

  • image 또는 docker_image: 해당 prompt의 sandbox에 사용할 container image입니다. Docker, Modal, Singularity backend에서 동작합니다.
  • cwd: task의 terminal session에 적용할 working directory override입니다.

설정 옵션

Parameter기본값설명
--dataset_file(required)JSONL dataset 경로
--batch_size(required)batch당 prompt 수
--run_name(required)이번 run의 이름. output dir와 checkpointing에 사용됩니다.
--distribution"default"sample할 toolset distribution
--modelclaude-sonnet-4.6사용할 model
--base_urlhttps://openrouter.ai/api/v1API base URL
--api_key(env var)model용 API key
--max_turns10prompt당 최대 tool-calling iteration
--num_workers4병렬 worker process 수
--resumefalsecheckpoint에서 재개
--verbosefalseverbose logging 활성화
--max_samplesalldataset에서 처음 N개 sample만 처리
--max_tokensmodel defaultmodel response당 최대 token 수

provider routing(OpenRouter)

Parameter설명
--providers_allowed허용할 provider를 쉼표로 구분해 지정합니다. 예: "anthropic,openai"
--providers_ignored무시할 provider를 쉼표로 구분해 지정합니다. 예: "together,deepinfra"
--providers_order선호 provider 순서를 쉼표로 구분해 지정합니다.
--provider_sort"price", "throughput", "latency" 중 하나로 정렬합니다.

reasoning 제어

Parameter설명
--reasoning_efforteffort level: none, minimal, low, medium, high, xhigh
--reasoning_disabledreasoning/thinking token을 완전히 비활성화

고급 옵션

Parameter설명
--ephemeral_system_prompt실행 중에는 사용하지만 trajectory에는 저장하지 않는 system prompt
--log_prefix_charslog preview에 표시할 문자 수. 기본값은 100입니다.
--prefill_messages_filefew-shot priming에 사용할 prefill message JSON 파일 경로

toolset distribution

각 prompt는 distribution에서 무작위로 sample된 toolset 집합을 받습니다. 이를 통해 training data가 다양한 tool 조합을 포함하게 됩니다. 사용 가능한 모든 distribution을 보려면 --list_distributions를 사용합니다.

현재 구현에서 distribution은 각 개별 toolset에 확률을 할당합니다. sampler는 toolset마다 독립적으로 coin flip을 수행한 뒤, 최소 하나의 toolset이 활성화되도록 보장합니다. 이는 미리 작성된 조합 table에서 하나를 고르는 방식과 다릅니다.

출력 형식

모든 출력은 data/<run_name>/에 저장됩니다.

data/my_run/
|-- trajectories.jsonl # Combined final output (all batches merged)
|-- batch_0.jsonl # Individual batch results
|-- batch_1.jsonl
|-- ...
|-- checkpoint.json # Resume checkpoint
`-- statistics.json # Aggregate tool usage stats

trajectory 형식

trajectories.jsonl의 각 줄은 JSON object입니다.

{
"prompt_index": 42,
"conversations": [
{"from": "human", "value": "Write a function..."},
{"from": "gpt", "value": "I'll create that function...",
"tool_calls": [...]},
{"from": "tool", "value": "..."},
{"from": "gpt", "value": "Here's the completed function..."}
],
"metadata": {
"batch_num": 2,
"timestamp": "2026-01-15T10:30:00",
"model": "anthropic/claude-sonnet-4.6"
},
"completed": true,
"partial": false,
"api_calls": 3,
"toolsets_used": ["terminal", "file"],
"tool_stats": {
"terminal": {"count": 2, "success": 2, "failure": 0},
"read_file": {"count": 1, "success": 1, "failure": 0}
},
"tool_error_counts": {
"terminal": 0,
"read_file": 0
}
}

conversations field는 fromvalue field를 사용하는 ShareGPT 유사 형식입니다. tool stats는 가능한 모든 tool을 포함하도록 정규화되며, 사용하지 않은 tool은 0을 기본값으로 갖습니다. 이렇게 해야 HuggingFace dataset 호환성을 위해 entry 간 schema가 일관됩니다.

checkpointing

batch runner는 fault tolerance를 위해 견고한 checkpointing을 제공합니다.

  • Checkpoint file: 각 batch가 완료될 때 저장되며, 완료된 prompt index를 추적합니다.
  • Content-based resume: --resume을 사용하면 runner가 기존 batch file을 scan하고 prompt의 실제 text content로 완료 여부를 matching합니다. index만 보지 않으므로 dataset 순서가 바뀌어도 복구할 수 있습니다.
  • Failed prompts: 성공적으로 완료된 prompt만 done으로 표시됩니다. 실패한 prompt는 resume 시 다시 시도됩니다.
  • Batch merging: 완료 시 이전 run의 batch file을 포함한 모든 batch file이 하나의 trajectories.jsonl로 병합됩니다.

resume 동작 방식

  1. 모든 batch_*.jsonl file에서 완료된 prompt를 scan합니다. content matching을 사용합니다.
  2. 이미 완료된 prompt를 제외하도록 dataset을 filter합니다.
  3. 남은 prompt를 다시 batch로 나눕니다.
  4. 남은 prompt만 처리합니다.
  5. 모든 batch file, 즉 old + new를 최종 출력으로 병합합니다.

quality filtering

batch runner는 자동 quality filtering을 적용합니다.

  • No-reasoning filter: assistant turn에 reasoning이 하나도 없는 sample은 버립니다. <REASONING_SCRATCHPAD>나 native thinking token이 없는 경우입니다.
  • Corrupted entry filter: 유효한 tool list에 없는 hallucinated tool name이 있는 entry는 final merge 중에 걸러냅니다.
  • Reasoning statistics: 전체 run에서 reasoning이 있는 turn과 없는 turn의 비율을 추적합니다.

statistics

완료 후 runner는 종합 통계를 출력합니다.

  • Tool usage: tool별 call count와 success/failure rate
  • Reasoning coverage: assistant turn 중 reasoning이 있는 비율
  • Samples discarded: reasoning 부족으로 filter된 sample 수
  • Duration: 전체 처리 시간

통계는 programmatic analysis를 위해 statistics.json에도 저장됩니다.

사용 사례

training data generation

fine-tuning을 위한 다양한 tool-use trajectory를 생성합니다.

python batch_runner.py \
--dataset_file=data/coding_prompts.jsonl \
--batch_size=20 \
--run_name=coding_v1 \
--model=anthropic/claude-sonnet-4.6 \
--num_workers=8 \
--distribution=default \
--max_turns=15

model evaluation

표준화된 prompt 전반에서 model이 tool을 얼마나 잘 사용하는지 평가합니다.

python batch_runner.py \
--dataset_file=data/eval_suite.jsonl \
--batch_size=10 \
--run_name=eval_gpt4 \
--model=openai/gpt-4o \
--num_workers=4 \
--max_turns=10

prompt별 container image

특정 환경이 필요한 benchmark의 경우, 각 prompt가 자체 container image를 지정할 수 있습니다.

{"prompt": "Install numpy and compute eigenvalues of a 3x3 matrix", "image": "python:3.11-slim"}
{"prompt": "Compile this Rust program and run it", "image": "rust:1.75"}
{"prompt": "Set up a Node.js Express server", "image": "node:20-alpine", "cwd": "/app"}

batch runner는 각 prompt를 실행하기 전에 Docker image에 접근할 수 있는지 확인합니다.