badgr-cli 1.0.43 → 1.0.45

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -2,6 +2,8 @@
2
2
 
3
3
  Badgr supports many GPU workloads through two commands: `serve` for persistent endpoints, `run` for jobs.
4
4
 
5
+ > **Safety promise:** every run has `--max-cost`, live logs, automatic teardown, and a receipt. Run `badgr down <id>` any time to stop billing immediately.
6
+
5
7
  ```bash
6
8
  npm install -g badgr-cli
7
9
  ```
@@ -23,56 +25,75 @@ badgr run . --cmd "python train.py" --max-cost 5
23
25
  # 4. Serve an OpenAI-compatible inference endpoint
24
26
  badgr serve meta-llama/Llama-3.1-8B-Instruct --max-cost 10
25
27
 
26
- # 5. Use the endpoint with any OpenAI SDK client
27
- # export BADGR_ENDPOINT=<URL printed by badgr serve>
28
- # client = OpenAI(api_key=os.environ["BADGR_API_KEY"], base_url=os.environ["BADGR_ENDPOINT"])
28
+ # 5. Stop billing
29
+ badgr down <deployment-id>
29
30
 
30
- # 5. View cost, route, and retry receipts
31
+ # 6. View cost, route, and retry receipts
31
32
  badgr receipts
33
+ ```
32
34
 
33
- # 6. Stop billing
34
- badgr down <deployment-id>
35
+ `badgr serve` prints a URL you can point any OpenAI SDK client at — see [OpenAI compatibility](#openai-compatibility).
36
+
37
+ ---
38
+
39
+ ## Also try: image generation
40
+
41
+ ```bash
42
+ badgr comfyui batch --workflow sdxl-basic --prompt "a cat on a beach" --max-cost 5
35
43
  ```
36
44
 
45
+ Runs a blessed ComfyUI workflow, no setup, and prints image URLs when done. No manual teardown needed — it stops itself. Details in [`badgr comfyui batch` options](#badgr-comfyui-batch-options).
46
+
37
47
  ---
38
48
 
39
49
  ## Commands
40
50
 
51
+ ```text
52
+ login
53
+ run
54
+ serve
55
+ status
56
+ logs
57
+ down
58
+ receipts
59
+ test
60
+ ```
61
+
41
62
  | Command | What it does |
42
63
  |---------|-------------|
43
64
  | `badgr login` | Save API key to `~/.badgr/config.json` |
44
- | `badgr serve <model>` | Start a persistent OpenAI-compatible endpoint |
45
65
  | `badgr run <command>` | Run a one-off GPU job (any container command) |
66
+ | `badgr serve <model>` | Start a persistent OpenAI-compatible endpoint |
46
67
  | `badgr status` | Show what's running and what's billing |
47
- | `badgr down <id>` | Terminate a deployment — stops billing immediately |
48
68
  | `badgr logs <id>` | Fetch log output from a deployment |
69
+ | `badgr down <id>` | Terminate a deployment — stops billing immediately |
49
70
  | `badgr receipts [n]` | Cost, route, and retry receipts (default 10) |
50
- | `badgr capacity` | Check available GPU capacity right now |
51
- | `badgr billing` | Show balance and add funds |
52
71
  | `badgr test` | Run an end-to-end test (provision → run → teardown) |
53
- | `badgr workload list` | List saved workloads with run stats |
54
- | `badgr workload run <name>` | Rerun a saved workload by name or ID |
55
- | `badgr workload info <name>` | Show stats, route history, and recent jobs for a workload |
56
- | `badgr workload delete <name>` | Delete a saved workload |
57
- | `badgr workspace list` | List workspace trackers (job history + cost per context) |
58
- | `badgr workspace create <name>` | Create a workspace tracker, optionally linked to a storage path |
59
- | `badgr workspace info <name>` | Show jobs, cost, and files for a workspace |
60
- | `badgr workspace delete <name>` | Archive a workspace tracker |
72
+
73
+ More commands below, under [Advanced](#advanced): `comfyui`, `train`, `transcribe`, `embed`, `workload`, `workspace`, `capacity`, `billing`.
61
74
 
62
75
  `badgr serve` — for anything that needs a persistent endpoint: LLM serving, embeddings, image generation APIs, transcription APIs.
63
76
 
64
77
  `badgr run` — for anything that starts, runs, and exits: batch inference, fine-tuning, evals, image/video batch jobs, audio processing.
65
78
 
66
- **Shortcuts** — wrappers around `run` / `serve` for common workloads:
79
+ ---
67
80
 
68
- | `badgr comfyui run <workflow.json>` | Launch ComfyUI, queue workflow, return endpoint URL |
69
- | `badgr comfyui batch --workflow ...` | Productized batch image generation — no ComfyUI setup, blessed workflow only |
70
- | `badgr train <config.yaml>` | LoRA / fine-tuning job, stream logs |
71
- | `badgr train lora --base-model ...` | Productized LoRA training — preset + dataset, no config file needed |
72
- | `badgr transcribe <audio>` | Whisper transcription, print transcript |
73
- | `badgr embed <model> <input>` | Text embeddings, output JSONL |
81
+ ## Common flags
74
82
 
75
- `badgr serve --list-aliases` lists the blessed vLLM model shortcuts (`qwen-7b`, `llama-8b`, `qwen-coder-7b`) that can be used in place of a full model ID.
83
+ These appear on most commands (`run`, `serve`, `comfyui`, `train`, `transcribe`, `embed`) documented once here instead of repeated in every table below.
84
+
85
+ | Flag | Default | Description |
86
+ |------|---------|-------------|
87
+ | `--gpu <type>` | auto | GPU type override — see [GPU options](#gpu-options) |
88
+ | `--tier 1\|2` | 1 | `1` = reliable managed routing (default); `2` = lower-cost marketplace routing |
89
+ | `--region US\|EU\|AU` | — | Region preference. If omitted, Badgr chooses best available capacity |
90
+ | `--max-price <$/hr>` | — | Hard spend cap per GPU-hour |
91
+ | `--count <n>` | 1 | Number of GPUs |
92
+ | `--env KEY=VALUE` | — | Environment variable (repeatable) |
93
+ | `--max-cost <$>` | — | Auto-stop when total spend reaches this amount — **required** for `run`, `comfyui run`, `comfyui batch`, `train lora` |
94
+ | `--detach` | off | Launch and return immediately, don't stream logs (`serve` uses `--no-wait` instead — see below) |
95
+
96
+ Each command section below lists only its own extra flags.
76
97
 
77
98
  ---
78
99
 
@@ -84,21 +105,26 @@ badgr serve meta-llama/Llama-3.1-8B-Instruct --gpu L40S --region EU
84
105
 
85
106
  | Flag | Default | Description |
86
107
  |------|---------|-------------|
87
- | `--gpu <type>` | auto | GPU type override — Badgr Auto selects based on model size if omitted |
88
108
  | `--image <img>` | — | Serve a custom container instead of a HuggingFace model |
89
109
  | `--task <task>` | — | vLLM task override, e.g. `embed` for embedding models |
90
- | `--env KEY=VALUE` | — | Environment variable (repeatable) |
91
- | `--tier 1\|2` | 1 | `1` = reliable execution (default); `2` = lower-cost burst capacity |
92
- | `--count <n>` | 1 | Number of GPUs (1–8) |
93
- | `--region US\|EU\|AU` | — | Optional region preference. If omitted, Badgr chooses best available capacity. |
94
- | `--max-price <$/hr>` | — | Hard spend cap per GPU-hour |
95
- | `--max-cost <$>` | — | Auto-stop when total spend reaches this amount |
96
110
  | `--health-path <path>` | auto | Readiness path to poll (auto-detected for ComfyUI → `/system_stats`) |
97
- | `--no-wait` | | Skip endpoint health check and return immediately |
111
+ | `--no-wait` | off | Skip endpoint health check and return immediately |
98
112
  | `--list-aliases` | — | List blessed vLLM model aliases (`qwen-7b`, `llama-8b`, `qwen-coder-7b`) and exit — no provisioning, no API key required |
99
113
 
100
114
  Blessed aliases expand to a full model ID + preset GPU, e.g. `badgr serve qwen-7b` → `Qwen/Qwen2.5-7B-Instruct` on an RTX 4090. Run `badgr serve --list-aliases` to see the current list.
101
115
 
116
+ ### Model support levels
117
+
118
+ `badgr serve qwen-7b` is the happy path — a tested route with no extra setup. `badgr serve` also accepts any other model ID or a custom container:
119
+
120
+ | Level | What it means |
121
+ |-------|---------------|
122
+ | **Tested route** (`badgr serve qwen-7b`) | One of the aliases above — tested and officially supported. |
123
+ | **Best-effort Hugging Face model** (`badgr serve <org>/<model>`) | Any other Hugging Face model ID. Badgr will try a compatible route — not a guarantee every model works. |
124
+ | **Custom container** (`badgr serve --image ...`) | You own the server behavior; Badgr manages runtime, logs, spend caps, teardown, and the receipt. |
125
+
126
+ Gated Hugging Face models (e.g. Llama, Gemma) may need `--env HF_TOKEN=$HF_TOKEN`. Badgr only prints that hint if the deployment actually fails to start.
127
+
102
128
  ---
103
129
 
104
130
  ## `badgr run` options
@@ -121,18 +147,26 @@ Badgr zips and uploads the folder (Flow 1) or clones the repo (Flow 2), picks a
121
147
  | Flag | Default | Description |
122
148
  |------|---------|-------------|
123
149
  | `--cmd <command>` | — | Command to run inside the uploaded project or cloned repo (required for folder/GitHub flows) |
124
- | `--gpu <type>` | auto | GPU type override — Badgr Auto selects if omitted |
125
150
  | `--min-vram <GB>` | — | Minimum VRAM in GB — optional constraint for Auto routing |
126
- | `--image <img>` | — | Custom Docker image — bypasses the runner. Mutually exclusive with workspace auto-detection. |
127
- | `--env KEY=VALUE` | — | Environment variable (repeatable) |
128
- | `--tier 1\|2` | 1 | `1` = reliable execution (default); `2` = lower-cost burst capacity |
129
- | `--count <n>` | 1 | Number of GPUs |
130
- | `--region US\|EU\|AU` | — | Optional region preference. If omitted, Badgr chooses best available capacity. |
131
- | `--max-price <$/hr>` | — | Hard spend cap per GPU-hour |
151
+ | `--image <img>` | — | Custom Docker image — bypasses the runner |
132
152
  | `--max-runtime <min>` | — | Auto-stop after N minutes |
133
- | `--max-cost <$>` | — | Auto-stop when total spend reaches this amount (required) |
134
- | `--detach` | — | Launch and return immediately, don't stream logs |
135
153
  | `--save <name>` | — | Save this job as a named workload after it completes |
154
+ | `--workspace <name-or-id>` | — | Link this run to a workspace (name or `ws_` ID) |
155
+ | `--output <path>` | — | See "Crash recovery" below |
156
+ | `--checkpoint <path>` | — | See "Crash recovery" below |
157
+ | `--retry-safe` | off | See "Crash recovery" below |
158
+ | `--resume-cmd "<cmd>"` | — | See "Crash recovery" below |
159
+
160
+ **Crash recovery is a convention, not a feature Badgr runs for you.** Badgr just passes these through into the container as environment variables — *your* script has to read them and actually write the files:
161
+
162
+ | Flag | Container sees | Your script needs to |
163
+ |------|-----------------|-----------------------|
164
+ | `--output <path>` | `BADGR_OUTPUT_DIR=<path>` | Write outputs it wants preserved to that path |
165
+ | `--checkpoint <path>` | `BADGR_CHECKPOINT_DIR=<path>` | Write/read resumable checkpoints at that path |
166
+ | `--retry-safe` | `BADGR_RETRY_SAFE=1` | Confirm it's safe to re-run from scratch (e.g. it checkpoints/dedupes internally) |
167
+ | `--resume-cmd "<cmd>"` | *(not passed to the container)* | Nothing — Badgr just prints this command back to you on failure, so you have it without digging through shell history |
168
+
169
+ On failure, `badgr run` / `badgr serve` / `badgr comfyui run` all print a `Class:`/`Next:` pair identifying what went wrong (e.g. `out_of_memory`, `image_pull_failed`, `cuda_unavailable`) and a suggested next step.
136
170
 
137
171
  ---
138
172
 
@@ -147,16 +181,10 @@ Requires either `--max-cost` or `--persistent` to prevent runaway billing.
147
181
 
148
182
  | Flag | Default | Description |
149
183
  |------|---------|-------------|
150
- | `--gpu <type>` | auto (16+ GB VRAM) | GPU type override |
151
- | `--max-cost <$>` | — | Auto-stop when total spend reaches this amount |
152
- | `--max-price <$/hr>` | — | Hard spend cap per GPU-hour |
153
- | `--tier 1\|2` | 1 | Provider tier |
154
- | `--region US\|EU\|AU` | — | Region preference |
155
184
  | `--check-nodes <n1,n2>` | — | Verify custom nodes are installed after startup |
156
- | `--no-wait` | | Skip health check, return immediately |
157
- | `--persistent` | | Run until manually stopped (no spending cap) |
158
- | `--env KEY=VALUE` | | Environment variable (repeatable) |
159
- | `--yes` / `-y` | — | Skip duplicate-deployment warning |
185
+ | `--no-wait` | off | Skip health check, return immediately |
186
+ | `--persistent` | off | Run until manually stopped (no spending cap) |
187
+ | `--yes` / `-y` | off | Skip duplicate-deployment warning |
160
188
 
161
189
  ---
162
190
 
@@ -176,253 +204,175 @@ Blessed workflows: `sdxl-basic` (SDXL text-to-image, default sampler settings).
176
204
  | `--workflow <name>` | — | Blessed workflow ID (required) — currently `sdxl-basic` |
177
205
  | `--prompts <file>` | — | Text file, one prompt per line |
178
206
  | `--prompt <text>` | — | Inline prompt (repeatable) — combine with `--prompts` if needed |
179
- | `--max-cost <$>` | — | Auto-stop when total spend reaches this amount (required unless `--dry-run`) |
180
207
  | `--max-runtime <min>` | 60 | Auto-stop after N minutes |
181
208
  | `--gpu-type <type>` | workflow default | GPU type override |
182
- | `--tier 1\|2` | 1 | Provider tier |
183
209
  | `--dry-run` | — | Preview the batch (workflow, GPU, prompt count, cost) without provisioning |
184
210
 
185
211
  Polls until complete and prints image URLs, or detaches with `badgr status` guidance if it outlives `--max-runtime`.
186
212
 
187
213
  ---
188
214
 
189
- ## `badgr train` options
190
-
191
- ```bash
192
- badgr train config.yaml --gpu A100 --max-runtime 240 --env HF_TOKEN=$HF_TOKEN
193
- ```
194
-
195
- Detects framework (axolotl, unsloth, trl) from config content, but **only Axolotl configs run today** — the container command for `unsloth`/`trl`/unrecognized configs isn't wired up yet, so `badgr train` blocks before provisioning rather than billing a GPU that's guaranteed to fail. Use `--framework axolotl` to force it, or use `badgr train lora` for a config-free productized path. Default max-runtime is 120 min.
196
-
197
- | Flag | Default | Description |
198
- |------|---------|-------------|
199
- | `--gpu <type>` | auto (40+ GB VRAM preferred) | GPU type override |
200
- | `--max-runtime <min>` | 120 | Auto-stop after N minutes |
201
- | `--max-cost <$>` | — | Auto-stop when total spend reaches this amount |
202
- | `--max-price <$/hr>` | — | Hard spend cap per GPU-hour |
203
- | `--tier 1\|2` | 1 | Provider tier |
204
- | `--region US\|EU\|AU` | — | Region preference |
205
- | `--framework <name>` | auto-detect | Force framework: `axolotl`, `unsloth`, `trl` (only `axolotl` currently runs) |
206
- | `--env KEY=VALUE` | — | Environment variable (repeatable) |
207
- | `--detach` | — | Launch and return immediately, don't stream logs |
208
-
209
- ---
210
-
211
- ## `badgr train lora` options
215
+ ## Receipts
212
216
 
213
- Productized LoRA training — pass a base model and dataset, no Axolotl config file needed. Badgr generates the config from a preset and returns a downloadable adapter.
217
+ Every `badgr serve` and `badgr run` action generates a receipt:
214
218
 
215
219
  ```bash
216
- badgr train lora --base-model mistralai/Mistral-7B-v0.1 --dataset ./train.jsonl --preset small --max-cost 20
217
- badgr train lora --base-model meta-llama/Llama-3.1-8B-Instruct --dataset https://example.com/data.jsonl --preset medium --max-cost 40
220
+ badgr receipts # last 10
221
+ badgr receipts 50 # last 50
218
222
  ```
219
223
 
220
- Dataset sources: local file (uploaded first), direct URL (`https://`, `s3://`), or `--file-id` from a prior `badgr` upload.
221
-
222
- | Flag | Default | Description |
223
- |------|---------|-------------|
224
- | `--base-model <id>` | — | HuggingFace model ID (required) — validated to exist before provisioning |
225
- | `--dataset <path\|url>` | — | Local file, direct URL, or `s3://` URI |
226
- | `--file-id <id>` | — | Badgr upload ID instead of `--dataset` |
227
- | `--preset small\|medium` | `small` | Training profile — see below |
228
- | `--max-cost <$>` | — | Auto-stop when total spend reaches this amount (required unless `--dry-run`) |
229
- | `--max-runtime <min>` | 240 | Auto-stop after N minutes |
230
- | `--gpu-type <type>` | preset default | GPU type override |
231
- | `--tier 1\|2` | 1 | Provider tier |
232
- | `--dry-run` | — | Preview the job (preset, GPU, rank, epochs, cost) without provisioning |
233
-
234
- **Presets:**
224
+ Each receipt includes runtime, estimated/settled cost, status, retries, teardown/billing result, and job/deployment ID.
235
225
 
236
- | Preset | GPU | LoRA rank | Epochs | Best for |
237
- |--------|-----|-----------|--------|----------|
238
- | `small` (default) | RTX 4090 | 16 | 3 | Fast, low-cost — good default for most datasets |
239
- | `medium` | A100 | 32 | 5 | Larger rank/more epochs — bigger datasets or higher quality |
226
+ ---
240
227
 
241
- On completion, prints an `adapter_url` — download with `GET /v1/jobs/{job_id}/adapter`, or via `badgr workload info` if saved.
228
+ ## OpenAI compatibility
242
229
 
243
- ---
230
+ `badgr serve` provisions a vLLM endpoint that is fully OpenAI-compatible:
244
231
 
245
- ## `badgr transcribe` options
232
+ ```python
233
+ import os
234
+ from openai import OpenAI
246
235
 
247
- ```bash
248
- badgr transcribe recording.mp3 --max-cost 2
249
- badgr transcribe s3://bucket/meeting.mp3 --model large-v3 --language en
236
+ # Export BADGR_ENDPOINT from the URL printed by `badgr serve`
237
+ client = OpenAI(
238
+ api_key=os.environ["BADGR_API_KEY"],
239
+ base_url=os.environ["BADGR_ENDPOINT"],
240
+ )
241
+ resp = client.chat.completions.create(
242
+ model="meta-llama/Llama-3.1-8B-Instruct",
243
+ messages=[{"role": "user", "content": "Hello"}],
244
+ )
250
245
  ```
251
246
 
252
- Accepts a public URL, S3/GCS URI, or a local file under 50 MB. Default max-runtime is 30 min.
253
-
254
- | Flag | Default | Description |
255
- |------|---------|-------------|
256
- | `--model <name>` | `large-v3` | Whisper model |
257
- | `--gpu <type>` | auto (8+ GB VRAM) | GPU type override |
258
- | `--language <code>` | — | Language hint (e.g. `en`, `fr`) |
259
- | `--output <format>` | — | Output format: `txt`, `srt`, `vtt` |
260
- | `--max-runtime <min>` | 30 | Auto-stop after N minutes |
261
- | `--max-cost <$>` | — | Auto-stop when total spend reaches this amount |
262
- | `--max-price <$/hr>` | — | Hard spend cap per GPU-hour |
263
- | `--tier 1\|2` | 1 | Provider tier |
264
- | `--region US\|EU\|AU` | — | Region preference |
265
- | `--env KEY=VALUE` | — | Environment variable (repeatable) |
266
- | `--detach` | — | Launch and return immediately, don't stream logs |
247
+ ```js
248
+ import OpenAI from "openai";
249
+ const client = new OpenAI({
250
+ apiKey: process.env.BADGR_API_KEY,
251
+ baseURL: process.env.BADGR_ENDPOINT, // URL printed by `badgr serve`
252
+ });
253
+ ```
267
254
 
268
255
  ---
269
256
 
270
- ## `badgr embed` options
257
+ ## GPU options
271
258
 
272
- ```bash
273
- badgr embed BAAI/bge-large-en-v1.5 documents.txt --max-cost 2
274
- badgr embed BAAI/bge-large-en-v1.5 s3://bucket/corpus.jsonl
275
- badgr embed documents.txt # uses default model
276
- ```
259
+ Badgr Auto selects the best eligible GPU for your workload. Add `--gpu <type>` or `--min-vram <GB>` only when you need more control.
277
260
 
278
- Accepts a public URL, S3/GCS URI, or a local text file under 10 MB. Outputs JSONL (`{"text": ..., "embedding": [...]}`). Default max-runtime is 30 min.
261
+ | Flag value | GPU | VRAM | Best for |
262
+ |-----------|-----|------|---------|
263
+ | RTX_3090 | NVIDIA RTX 3090 | 24 GB | Dev, inference |
264
+ | RTX_4090 | NVIDIA RTX 4090 | 24 GB | Inference, training, dev |
265
+ | L40S | NVIDIA L40S | 48 GB | Inference, vLLM, embeddings |
266
+ | A100 | NVIDIA A100 | 40–80 GB | Training, inference |
267
+ | H100 | NVIDIA H100 | 80 GB | Large model training |
279
268
 
280
- | Flag | Default | Description |
281
- |------|---------|-------------|
282
- | `--gpu <type>` | auto (8+ GB VRAM) | GPU type override |
283
- | `--batch-size <n>` | — | Embedding batch size |
284
- | `--max-runtime <min>` | 30 | Auto-stop after N minutes |
285
- | `--max-cost <$>` | — | Auto-stop when total spend reaches this amount |
286
- | `--max-price <$/hr>` | — | Hard spend cap per GPU-hour |
287
- | `--tier 1\|2` | 1 | Provider tier |
288
- | `--region US\|EU\|AU` | — | Region preference |
289
- | `--env KEY=VALUE` | — | Environment variable (repeatable) |
290
- | `--detach` | — | Launch and return immediately, don't stream logs |
269
+ Additional GPU types may be routable depending on current capacity — check with `badgr capacity`. Pricing is confirmed before provisioning; use `--dry-run` to see it first. Full GPU support details: see [NOTES.md](../../NOTES.md#gpu-support) in the repo root.
291
270
 
292
271
  ---
293
272
 
294
- ## Workloads
273
+ ## Routing
295
274
 
296
- A workload is a saved job configuration. Once saved, you can rerun it by name instead of retyping all the flags. Badgr tracks success rate, average cost, average runtime, and the last known-good route so reruns are faster and cheaper over time.
275
+ `--tier 1` (default) uses managed provider routing reliable, consistent performance. `--tier 2` uses marketplace routing for lower-cost options. Most users should stick with the default.
297
276
 
298
- **Save a workload** by adding `--save <name>` to any `badgr run` call:
277
+ Preview any command before provisioning with `--dry-run`, e.g.:
299
278
 
300
279
  ```bash
301
- badgr run . --cmd "python train.py" --gpu A100 --env HF_TOKEN=$HF_TOKEN --max-cost 10 --save my-training-job
280
+ badgr serve meta-llama/Llama-3.1-8B-Instruct --dry-run
302
281
  ```
303
282
 
304
- **Rerun a saved workload:**
283
+ ---
305
284
 
306
- ```bash
307
- badgr workload run my-training-job
308
- badgr workload run my-training-job --max-cost 5 # override spend cap
309
- badgr workload run my-training-job --set HF_TOKEN=newval # override an env var
310
- ```
285
+ ## Advanced
286
+
287
+ Less common commands — training, transcription, embeddings, and the workload/workspace trackers. Same flags as `run`/`serve` unless noted (see [Common flags](#common-flags)).
311
288
 
312
- **Inspect and manage workloads:**
289
+ ### `badgr train` / `badgr train lora`
313
290
 
314
291
  ```bash
315
- badgr workload list # list all saved workloads with stats
316
- badgr workload info my-training-job # stats, route history, recent jobs
317
- badgr workload delete my-training-job
292
+ badgr train config.yaml --gpu A100 --max-runtime 240 --env HF_TOKEN=$HF_TOKEN
318
293
  ```
319
294
 
320
- | `badgr workload run` flag | Description |
321
- |---|---|
322
- | `--max-cost <$>` | Override the saved spend cap for this run |
323
- | `--max-runtime <min>` | Override the saved runtime limit for this run |
324
- | `--set KEY=VALUE` | Override a saved config value for this run (repeatable) |
325
-
326
- ---
327
-
328
- ## Workspaces
329
-
330
- Workspaces are an advanced infrastructure concept — most users never need to manage them directly. When you run `badgr run .`, Badgr handles code upload, dependency caching, and artifact storage automatically. Workspaces are only needed when you want to group jobs under a named context for cost tracking, or link jobs to persistent S3/GCS storage.
295
+ Detects framework (axolotl, unsloth, trl) from the config file, but **only Axolotl configs run today** — `unsloth`/`trl`/unrecognized configs are blocked before provisioning rather than billing a GPU that's guaranteed to fail. Default max-runtime is 120 min.
331
296
 
332
297
  ```bash
333
- badgr workspace create my-project --storage s3://my-bucket/runs --desc "nightly evals"
334
- badgr run . --cmd "python eval.py" --workspace my-project --max-cost 5
335
- badgr workspace info my-project # jobs, total cost, files
336
- badgr workspace list
337
- badgr workspace delete my-project
298
+ badgr train lora --base-model mistralai/Mistral-7B-v0.1 --dataset ./train.jsonl --preset small --max-cost 20
338
299
  ```
339
300
 
340
- | `badgr workspace create` flag | Description |
341
- |---|---|
342
- | `--storage <path>` | S3/GCS path to associate with this workspace |
343
- | `--desc <text>` | Optional description |
344
-
345
- ---
346
-
347
- ## Routing
348
-
349
- Badgr Auto selects the best eligible route based on GPU type, VRAM, availability, region, workload requirements, and reliability. Advanced users can optionally choose an execution tier or hardware constraint.
350
-
351
- Most users should use the default Badgr Auto route. Tiers are an optional advanced control.
301
+ Productized LoRA training pass a base model and dataset, no Axolotl config file needed. Badgr generates the config from a preset and returns a downloadable adapter.
352
302
 
353
- **Tier 1** (default) Reliable execution. Best for production workloads, model serving, and jobs where startup reliability matters most. Uses managed routing, readiness checks, fallback, and teardown controls.
303
+ | Flag | Default | Description |
304
+ |------|---------|-------------|
305
+ | `--framework <name>` | auto-detect | Force framework: `axolotl`, `unsloth`, `trl` (only `axolotl` currently runs) |
306
+ | `--base-model <id>` | — | HuggingFace model ID (required for `train lora`) — validated to exist before provisioning |
307
+ | `--dataset <path\|url>` | — | Local file, direct URL, or `s3://` URI |
308
+ | `--file-id <id>` | — | Badgr upload ID instead of `--dataset` |
309
+ | `--preset small\|medium` | `small` | `small` = RTX 4090, rank 16, 3 epochs. `medium` = A100, rank 32, 5 epochs |
310
+ | `--gpu-type <type>` | preset default | GPU type override for `train lora` |
311
+ | `--dry-run` | — | Preview the job without provisioning |
354
312
 
355
- **Tier 2** Lower-cost burst execution. An optional advanced control for cost-sensitive workloads. Availability may vary.
313
+ On completion, `train lora` prints an `adapter_url` download with `GET /v1/jobs/{job_id}/adapter`, or via `badgr workload info` if saved.
356
314
 
357
- Preview before provisioning:
315
+ ### `badgr transcribe`
358
316
 
359
317
  ```bash
360
- badgr serve meta-llama/Llama-3.1-8B-Instruct --dry-run
318
+ badgr transcribe recording.mp3 --max-cost 2
361
319
  ```
362
320
 
363
- ---
321
+ Whisper transcription. Accepts a public URL, S3/GCS URI, or a local file under 50 MB. Default max-runtime is 30 min.
364
322
 
365
- ## Receipts
323
+ | Flag | Default | Description |
324
+ |------|---------|-------------|
325
+ | `--model <name>` | `large-v3` | Whisper model |
326
+ | `--language <code>` | — | Language hint (e.g. `en`, `fr`) |
327
+ | `--output <format>` | — | Output format: `txt`, `srt`, `vtt` |
366
328
 
367
- Every `badgr serve` and `badgr run` action generates a receipt:
329
+ ### `badgr embed`
368
330
 
369
331
  ```bash
370
- badgr receipts # last 10
371
- badgr receipts 50 # last 50
332
+ badgr embed BAAI/bge-large-en-v1.5 documents.txt --max-cost 2
372
333
  ```
373
334
 
374
- Each receipt includes: receipt ID, GPU type, provisioning latency, price/hr, retry count, and status.
375
-
376
- ---
377
-
378
- ## OpenAI compatibility
335
+ Text embeddings via vLLM. Accepts a public URL, S3/GCS URI, or a local text file under 10 MB. Outputs JSONL (`{"text": ..., "embedding": [...]}`). Default max-runtime is 30 min.
379
336
 
380
- `badgr serve` provisions a vLLM endpoint that is fully OpenAI-compatible:
337
+ | Flag | Default | Description |
338
+ |------|---------|-------------|
339
+ | `--batch-size <n>` | — | Embedding batch size |
381
340
 
382
- ```python
383
- import os
384
- from openai import OpenAI
341
+ ### Workloads
385
342
 
386
- # Export BADGR_ENDPOINT from the URL printed by `badgr serve`
387
- client = OpenAI(
388
- api_key=os.environ["BADGR_API_KEY"],
389
- base_url=os.environ["BADGR_ENDPOINT"],
390
- )
391
- resp = client.chat.completions.create(
392
- model="meta-llama/Llama-3.1-8B-Instruct",
393
- messages=[{"role": "user", "content": "Hello"}],
394
- )
395
- ```
343
+ A workload is a saved job configuration, created with `--save <name>` on `badgr run`. Rerun by name instead of retyping all the flags; Badgr tracks success rate, average cost, and the last known-good route.
396
344
 
397
- ```js
398
- import OpenAI from "openai";
399
- const client = new OpenAI({
400
- apiKey: process.env.BADGR_API_KEY,
401
- baseURL: process.env.BADGR_ENDPOINT, // URL printed by `badgr serve`
402
- });
345
+ ```bash
346
+ badgr run . --cmd "python train.py" --max-cost 10 --save my-training-job
347
+ badgr workload run my-training-job
348
+ badgr workload list
349
+ badgr workload info my-training-job
350
+ badgr workload delete my-training-job
403
351
  ```
404
352
 
405
- ---
406
-
407
- ## GPU options
353
+ | Subcommand | Description |
354
+ |------------|-------------|
355
+ | `list [n]` | List saved workloads |
356
+ | `info <name>` | Stats, route history, recent jobs |
357
+ | `run <name>` | Submit a new job using the workload's saved config (`--max-cost`, `--max-runtime`, `--set KEY=VALUE` to override) |
358
+ | `delete <name>` | Delete the workload record |
408
359
 
409
- Badgr Auto selects the best eligible GPU for your workload. Add `--gpu <type>` or `--min-vram <GB>` only when you need more control.
360
+ ### Workspaces
410
361
 
411
- Available GPU types may vary by region and current capacity. Run `badgr capacity` or use `--dry-run` to confirm availability before provisioning.
362
+ Most users never need this `badgr run .` handles upload, caching, and artifact storage automatically. Workspaces are for grouping jobs under a named cost/context bucket, optionally linked to S3/GCS storage.
412
363
 
413
- | Flag value | GPU | VRAM | Best for |
414
- |-----------|-----|------|---------|
415
- | RTX_3090 | NVIDIA RTX 3090 | 24 GB | Dev, inference |
416
- | RTX_4090 | NVIDIA RTX 4090 | 24 GB | Inference, training, dev |
417
- | L40S | NVIDIA L40S | 48 GB | Inference, vLLM, embeddings |
418
- | A100 | NVIDIA A100 | 40–80 GB | Training, inference |
419
- | H100 | NVIDIA H100 | 80 GB | Large model training |
420
-
421
- Additional GPU types may be routable depending on current capacity — check with `badgr capacity`.
364
+ ```bash
365
+ badgr workspace create my-project --storage s3://my-bucket/runs --desc "nightly evals"
366
+ badgr run . --cmd "python eval.py" --workspace my-project --max-cost 5
367
+ badgr workspace info my-project
368
+ badgr workspace list
369
+ badgr workspace delete my-project
370
+ ```
422
371
 
423
- Pricing is confirmed before provisioning. Use `--dry-run` to see pricing before committing.
372
+ ### Other commands
424
373
 
425
- Full GPU support details: see [NOTES.md](../../NOTES.md#gpu-support) in the repo root.
374
+ - `badgr capacity [--gpu <type>]` check available GPU capacity right now
375
+ - `badgr billing status` / `badgr billing add <amount>` — check balance / add funds
426
376
 
427
377
  ---
428
378
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "badgr-cli",
3
- "version": "1.0.43",
3
+ "version": "1.0.45",
4
4
  "description": "Badgr — run or serve GPU workloads from one command",
5
5
  "type": "module",
6
6
  "bin": {
package/src/badgr.js CHANGED
@@ -20,14 +20,17 @@ import { embedCommand } from './commands/embed.js';
20
20
  import { templateCommand } from './commands/template.js';
21
21
  import { workloadCommand } from './commands/workload.js';
22
22
  import { workspaceCommand } from './commands/workspace.js';
23
+ import { detectCommand } from './commands/detect.js';
23
24
 
24
25
  const HELP = `
25
26
  ${chalk.bold('badgr')} — run or serve GPU workloads from one command
26
27
 
27
28
  ${chalk.bold('COMMANDS')}
28
29
  ${chalk.cyan('badgr login')} Authenticate with your API key
30
+ ${chalk.cyan('badgr detect <path>')} Inspect a project and report the GPU job Badgr would run
29
31
  ${chalk.cyan('badgr run <command>')} Run a one-off GPU job
30
32
  ${chalk.cyan('badgr serve <model>')} Serve a model with an OpenAI-compatible endpoint
33
+ ${chalk.cyan('badgr serve openwebui')} Serve Open WebUI — chat UI, connects to a model endpoint
31
34
  ${chalk.cyan('badgr status')} Show what's running and what's billing
32
35
  ${chalk.cyan('badgr logs <id>')} Stream logs for a running job or endpoint
33
36
  ${chalk.cyan('badgr down <id>')} Stop a deployment and end billing
@@ -53,12 +56,20 @@ ${chalk.bold('SHORTCUTS')} ${chalk.dim('(wrappers around run / serve for common
53
56
  ${chalk.cyan('badgr serve --list-aliases')} List blessed vLLM model shortcuts (qwen-7b, llama-8b, …)
54
57
 
55
58
  ${chalk.bold('EXAMPLES')}
59
+ ${chalk.dim('# Point Badgr at any project and see what it detects:')}
60
+ badgr detect .
61
+ badgr run . --max-cost 5 --save my-job
62
+ badgr workload run my-job
63
+
56
64
  ${chalk.dim('# Verify the stack works end-to-end:')}
57
65
  badgr test
58
66
 
59
67
  ${chalk.dim('# Serve a model (OpenAI-compatible):')}
60
68
  badgr serve meta-llama/Llama-3.1-8B-Instruct --max-cost 10
61
69
 
70
+ ${chalk.dim('# Serve Open WebUI, connected to a model endpoint:')}
71
+ badgr serve openwebui --model qwen-7b --max-cost 10
72
+
62
73
  ${chalk.dim('# Serve a Hugging Face GGUF file via llama.cpp:')}
63
74
  badgr serve --runtime llama.cpp \\
64
75
  --hf-repo org/model-repo \\
@@ -141,6 +152,7 @@ async function main() {
141
152
 
142
153
  switch (cmd) {
143
154
  case 'login': return loginCommand(chalk, saveConfig);
155
+ case 'detect': return detectCommand(config, rest, chalk);
144
156
  case 'run': return runCommand(config, rest, chalk);
145
157
  case 'serve': return serveCommand(config, rest, chalk);
146
158
  case 'status': return statusCommand(config, rest, chalk);