> ## Documentation Index
> Fetch the complete documentation index at: https://runcrate.ai/docs/llms.txt
> Use this file to discover all available pages before exploring further.

# Arrays and sweeps

> Run many copies of a job from one request: shards with count, or a parameter sweep with params, a few at a time.

One request can start a group of jobs: the same command on many machines, each with its own index or its own settings. Use it for batch inference over shards, evaluations, and hyperparameter sweeps.

## count: shards

```json theme={"theme":{"light":"github-light","dark":"catppuccin-mocha"}}
{
  "command": "python infer.py --shard $RUNCRATE_JOB_INDEX --of $RUNCRATE_JOB_COUNT",
  "gpu_type": ["L40S", "A100-80GB"],
  "max_runtime_minutes": 60,
  "count": 10,
  "max_parallel": 4
}
```

Each job sees `RUNCRATE_JOB_INDEX` (0 to count - 1), `RUNCRATE_JOB_COUNT` and `RUNCRATE_GROUP_ID`.

## params: a sweep

```json theme={"theme":{"light":"github-light","dark":"catppuccin-mocha"}}
{
  "command": "python train.py --lr $LR --batch $BATCH",
  "gpu_type": "H100",
  "max_runtime_minutes": 120,
  "env": { "BATCH": "64" },
  "params": [{ "LR": "0.1" }, { "LR": "0.01" }, { "LR": "0.001", "BATCH": "128" }]
}
```

One job per entry. Each entry is merged over `env`, so the third job gets `LR=0.001` and `BATCH=128`.

## max\_parallel

At most `max_parallel` jobs of the group are on machines at once (default: all of them). The others stay `queued` with `queue_reason: "max_parallel"` and start as earlier ones end. Every job also [waits for capacity](/docs/jobs/capacity) and [retries](/docs/jobs/retries) on its own; its capacity wait starts when `max_parallel` lets it go.

## What comes back

The answer is the group with its jobs:

```json theme={"theme":{"light":"github-light","dark":"catppuccin-mocha"}}
{
  "data": {
    "id": "8d0b...",
    "count": 10,
    "max_parallel": 4,
    "status_counts": { "queued": 6, "starting": 4, "running": 0, "succeeded": 0, "failed": 0, "cancelled": 0, "timed_out": 0 },
    "cost_usd": null,
    "created_at": "2026-10-20T09:00:00Z",
    "jobs": [{ "id": "...", "job_index": 0, "group_id": "8d0b...", "...": "..." }]
  }
}
```

| Endpoint | What it does |
| - | - |
| `GET /job-groups/{id}` | The group: how many jobs are in each status, and the cost of all of them. |
| `GET /jobs?group_id={id}` | Its jobs. |
| `POST /job-groups/{id}/cancel` | Cancels every job of the group that has not ended. |

Jobs are named after the group with their index (`jobs-8d0b1c2e-3`), or `name-3` when you give a `name`.

## Budget

A group is checked against the environment's monthly budget before any job starts, by what it could cost: count x the lowest rate of its GPUs x `max_runtime_minutes`. If that is more than what is left of the budget, the request is refused with `BUDGET_REACHED` and nothing starts. Each launch is checked again as usual.

A volume can be attached to one machine at a time, so `storage_id` cannot be used with `count` or `params`.

## Ask your agent

```text theme={"theme":{"light":"github-light","dark":"catppuccin-mocha"}}
Evaluate checkpoints 1 to 8 with eval.py on A100s, 4 at a time, and give me a table of the scores.
```

The agent calls `run_job` with `params: [{"CKPT": "1"}, ..., {"CKPT": "8"}]` and `max_parallel: 4`, follows each job's logs, and uses `get_job_group` to know when all are done.


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.