glm-launch 2026.6.1__tar.gz

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.
@@ -0,0 +1,10 @@
1
+ # Python-generated files
2
+ __pycache__/
3
+ *.py[oc]
4
+ build/
5
+ dist/
6
+ wheels/
7
+ *.egg-info
8
+
9
+ # Virtual environments
10
+ .venv
@@ -0,0 +1,32 @@
1
+ default_language_version:
2
+ python: python3.13
3
+
4
+ repos:
5
+ - repo: https://github.com/pre-commit/pre-commit-hooks
6
+ rev: v5.0.0
7
+ hooks:
8
+ - id: check-added-large-files
9
+ - id: check-case-conflict
10
+ - id: check-json
11
+ - id: check-merge-conflict
12
+ - id: check-symlinks
13
+ - id: check-toml
14
+ - id: end-of-file-fixer
15
+ - id: trailing-whitespace
16
+ - repo: https://github.com/astral-sh/ruff-pre-commit
17
+ rev: v0.6.9
18
+ hooks:
19
+ - id: ruff
20
+ args: [--fix, --exit-non-zero-on-fix]
21
+ - id: ruff-format
22
+ - repo: https://github.com/asottile/pyupgrade
23
+ rev: v3.18.0
24
+ hooks:
25
+ - id: pyupgrade
26
+ alias: autoformat
27
+ args: [--py313-plus]
28
+ - repo: https://github.com/abravalheri/validate-pyproject
29
+ rev: "v0.21"
30
+ hooks:
31
+ - id: validate-pyproject
32
+ additional_dependencies: ["validate-pyproject-schema-store[all]"]
@@ -0,0 +1,54 @@
1
+ # CLAUDE.md
2
+
3
+ This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
4
+
5
+ ## Project Overview
6
+
7
+ glm-cli-git is a Python CLI tool that wraps LLM coding tools (`claude`, `codex`, `opencode`) with GLM settings. It requires Python 3.13+ and uses Typer for CLI handling. Configuration is driven by environment variables (`GLM_BASE_URL`, `GLM_API_KEY`, `GLM_AUTH_TOKEN`).
8
+
9
+ ## Commands
10
+
11
+ ```bash
12
+ # Show top-level help
13
+ uv run src/main.py --help
14
+
15
+ # Show available providers
16
+ uv run src/main.py launch --help
17
+
18
+ # Launch claude (requires GLM_BASE_URL env var)
19
+ uv run src/main.py launch claude
20
+
21
+ # Launch claude with a specific model
22
+ uv run src/main.py launch claude --model "some-model"
23
+
24
+ # Launch codex (always passes --oss)
25
+ uv run src/main.py launch codex --model "some-model"
26
+
27
+ # Launch opencode (writes config JSON, then runs)
28
+ uv run src/main.py launch opencode --model "some-model"
29
+
30
+ # Pass extra args through to the underlying tool
31
+ uv run src/main.py launch claude -- --verbose
32
+
33
+ # Time a request against the configured GLM endpoint
34
+ uv run src/main.py bench
35
+
36
+ # List known Z.ai GLM models (built-in list)
37
+ uv run src/main.py models
38
+
39
+ # Fetch the live model list from the Z.ai API (needs GLM_AUTH_TOKEN)
40
+ uv run src/main.py models --remote
41
+
42
+ # Bootstrap the current shell with GLM env vars (so a plain `claude` uses Z.ai)
43
+ eval "$(uv run src/main.py shell)"
44
+ ```
45
+
46
+ ## Architecture
47
+
48
+ Single-module project with entry point at `src/main.py` (the installed `glm-launch` console script calls `cli()`, which defaults to the `claude` provider when no command is given). Uses Typer with a two-level command structure: `glm launch <provider>`. Providers are also registered at the top level so `glm-launch <provider>` works without the `launch` prefix. Each provider gets its own `@launch_app.command()` with provider-specific setup logic:
49
+
50
+ - **claude** — Sets `ANTHROPIC_BASE_URL`, `ANTHROPIC_API_KEY`, `ANTHROPIC_AUTH_TOKEN`, `ANTHROPIC_DEFAULT_*_MODEL`, `CLAUDE_CODE_SUBAGENT_MODEL`, `CLAUDE_CODE_EFFORT_LEVEL`, `CLAUDE_CODE_ATTRIBUTION_HEADER`, and `CLAUDE_CODE_AUTO_COMPACT_WINDOW` env vars from GLM settings, passes `--model` flag. Falls back to `~/.claude/local/claude` if not on PATH.
51
+ - **codex** — Always passes `--oss` flag, passes `-m` for model. No env vars or config files.
52
+ - **opencode** — Writes provider config to `~/.config/opencode/opencode.json` and recent model state to `~/.local/state/opencode/model.json`, then execs the binary. No env vars.
53
+
54
+ All providers exec the underlying binary via `os.execvpe()` for full stdio passthrough.
@@ -0,0 +1,354 @@
1
+ Metadata-Version: 2.4
2
+ Name: glm-launch
3
+ Version: 2026.6.1
4
+ Summary: Wrap claude/codex/opencode with Z.ai GLM settings
5
+ Requires-Python: >=3.13
6
+ Requires-Dist: typer
7
+ Description-Content-Type: text/markdown
8
+
9
+ # glm-cli-git
10
+
11
+ A Python CLI tool that wraps LLM coding tools (`claude`, `codex`, `opencode`) with [GLM](https://docs.z.ai/) settings. Instead of running a local proxy, it configures environment variables and config files, then exec's the underlying binary directly.
12
+
13
+ Requires Python 3.13+.
14
+
15
+ ## Usage
16
+
17
+ ```bash
18
+ # 1. Set your Z.AI auth token
19
+ export GLM_AUTH_TOKEN="your-zai-api-key"
20
+
21
+ # 2. Launch Claude Code routed through Z.AI (defaults to glm-5.2)
22
+ uv run glm-launch # bare command defaults to `claude`
23
+ uv run glm-launch claude # same thing, explicit
24
+
25
+ # Pick a different model
26
+ uv run glm-launch claude --model glm-5.1 # long-horizon flagship
27
+ uv run glm-launch claude --model glm-5-turbo # fast
28
+ uv run glm-launch claude --model glm-4.5-air # cheap
29
+
30
+ # Bootstrap your current shell so a plain `claude` uses Z.AI
31
+ eval "$(uv run glm-launch shell)"
32
+ claude
33
+
34
+ # See available models (built-in list, or --remote for the live API list)
35
+ uv run glm-launch models
36
+ uv run glm-launch models --remote
37
+
38
+ # Sanity-check connectivity / latency
39
+ uv run glm-launch bench
40
+ ```
41
+
42
+ > Examples use the installed `glm-launch` entrypoint. Before `uv sync` you can run
43
+ > the script directly with `uv run src/main.py …` — the two are interchangeable.
44
+
45
+ ## Installation
46
+
47
+ ```bash
48
+ uv sync
49
+ ```
50
+
51
+ This installs a `glm-launch` entrypoint. Run commands via `uv run glm-launch <command>`, or `uv tool install .` to get `glm-launch` on your PATH directly. You can also run the script without installing via `uv run src/main.py <command>`.
52
+
53
+ ### Run without cloning (`uvx`)
54
+
55
+ You can run `glm-launch` directly with [`uvx`](https://docs.astral.sh/uv/guides/tools/) (`uv tool run`) — no clone or manual install needed.
56
+
57
+ ```bash
58
+ # From GitHub (works today)
59
+ uvx --from git+https://github.com/jefftriplett/glm-launch glm-launch launch claude
60
+
61
+ # Pin to a tag/branch/commit
62
+ uvx --from git+https://github.com/jefftriplett/glm-launch@main glm-launch models
63
+ ```
64
+
65
+ Once published to PyPI, this simplifies to:
66
+
67
+ ```bash
68
+ # Coming soon — not yet on PyPI
69
+ uvx glm-launch launch claude
70
+ ```
71
+
72
+ ## Commands
73
+
74
+ ### `launch claude`
75
+
76
+ Launch [Claude Code](https://docs.anthropic.com/en/docs/claude-code) with GLM environment settings. Sets Anthropic env vars to route requests through Z.AI's Anthropic-compatible endpoint, then exec's the `claude` binary.
77
+
78
+ > The `launch` prefix is optional: `glm-launch claude` is equivalent to `glm-launch launch claude`, and a bare `glm-launch` defaults to `claude`. The same applies to `codex` and `opencode`.
79
+
80
+ ```bash
81
+ uv run glm-launch launch claude
82
+ ```
83
+
84
+ **Options:**
85
+
86
+ | Flag | Env var | Default | Description |
87
+ |------|---------|---------|-------------|
88
+ | `--model` / `-m` | — | `glm-5.2` | Model name passed to `claude --model` |
89
+ | `--base-url` | `GLM_BASE_URL` | `https://api.z.ai/api/anthropic` | API endpoint |
90
+ | `--api-key` | `GLM_API_KEY` | `""` | API key |
91
+ | `--auth-token` | `GLM_AUTH_TOKEN` | **(required)** | Z.AI auth token |
92
+ | `--api-timeout-ms` | `API_TIMEOUT_MS` | `3000000` | Request timeout in milliseconds |
93
+ | `--default-haiku-model` | `ANTHROPIC_DEFAULT_HAIKU_MODEL` | `glm-4.5-air` | Model for Haiku-tier requests |
94
+ | `--default-sonnet-model` | `ANTHROPIC_DEFAULT_SONNET_MODEL` | `glm-5.2` | Model for Sonnet-tier requests |
95
+ | `--default-opus-model` | `ANTHROPIC_DEFAULT_OPUS_MODEL` | `glm-5.2` | Model for Opus-tier requests |
96
+ | `--subagent-model` | `CLAUDE_CODE_SUBAGENT_MODEL` | `glm-4.5-air` | Model used for spawned subagents |
97
+ | `--effort-level` | `CLAUDE_CODE_EFFORT_LEVEL` | `max` | Effort level for the agent loop |
98
+ | `--attribution-header` | `CLAUDE_CODE_ATTRIBUTION_HEADER` | `0` | Attribution header toggle (`0` disables it) |
99
+ | `--auto-compact-window` | `CLAUDE_CODE_AUTO_COMPACT_WINDOW` | `200000` | Auto-compact context window in tokens (empty to leave unset) |
100
+
101
+ The following env vars are set before exec'ing `claude`:
102
+
103
+ - `ANTHROPIC_BASE_URL` — from `--base-url` / `GLM_BASE_URL`
104
+ - `ANTHROPIC_API_KEY` — from `--api-key` / `GLM_API_KEY`
105
+ - `ANTHROPIC_AUTH_TOKEN` — from `--auth-token` / `GLM_AUTH_TOKEN`
106
+ - `API_TIMEOUT_MS` — from `--api-timeout-ms` / `API_TIMEOUT_MS`
107
+ - `ANTHROPIC_DEFAULT_HAIKU_MODEL` — from `--default-haiku-model`
108
+ - `ANTHROPIC_DEFAULT_SONNET_MODEL` — from `--default-sonnet-model`
109
+ - `ANTHROPIC_DEFAULT_OPUS_MODEL` — from `--default-opus-model`
110
+ - `CLAUDE_CODE_SUBAGENT_MODEL` — from `--subagent-model`
111
+ - `CLAUDE_CODE_EFFORT_LEVEL` — from `--effort-level`
112
+ - `CLAUDE_CODE_ATTRIBUTION_HEADER` — from `--attribution-header`
113
+ - `CLAUDE_CODE_AUTO_COMPACT_WINDOW` — from `--auto-compact-window` (only when non-empty)
114
+
115
+ **Examples:**
116
+
117
+ ```bash
118
+ # Use defaults (glm-5.2, Z.AI endpoint)
119
+ uv run glm-launch launch claude
120
+
121
+ # Flagship reasoning/coding model (the default)
122
+ uv run glm-launch launch claude --model glm-5.2
123
+
124
+ # Long-horizon agentic flagship
125
+ uv run glm-launch launch claude --model glm-5.1
126
+
127
+ # Fast, speed-optimized GLM-5 variant
128
+ uv run glm-launch launch claude --model glm-5-turbo
129
+
130
+ # Lightweight, low-cost model for cheaper runs
131
+ uv run glm-launch launch claude --model glm-4.5-air
132
+
133
+ # Tune the model tiers independently (e.g. cheap subagents, flagship main)
134
+ uv run glm-launch launch claude \
135
+ --model glm-5.2 \
136
+ --subagent-model glm-4.5-air \
137
+ --default-haiku-model glm-4.5-air
138
+
139
+ # Pass extra args through to claude
140
+ uv run glm-launch launch claude -- --verbose
141
+
142
+ # Override via env vars
143
+ GLM_AUTH_TOKEN="my-token" uv run glm-launch launch claude
144
+ ```
145
+
146
+ Run `uv run glm-launch models` to see all valid model names (or `--remote` for the live list).
147
+
148
+ If `claude` is not on your PATH, the tool falls back to `~/.claude/local/claude`.
149
+
150
+ ### `launch codex`
151
+
152
+ Launch [Codex](https://github.com/openai/codex) with the `--oss` flag for local Ollama usage.
153
+
154
+ ```bash
155
+ uv run glm-launch launch codex
156
+ ```
157
+
158
+ **Options:**
159
+
160
+ | Flag | Default | Description |
161
+ |------|---------|-------------|
162
+ | `--model` / `-m` | — | Model name passed to `codex -m` |
163
+
164
+ **Examples:**
165
+
166
+ ```bash
167
+ # Launch with default settings
168
+ uv run glm-launch launch codex
169
+
170
+ # Specify a model
171
+ uv run glm-launch launch codex --model "some-model"
172
+
173
+ # Pass extra args through to codex
174
+ uv run glm-launch launch codex -- --some-flag
175
+ ```
176
+
177
+ ### `launch opencode`
178
+
179
+ Launch [opencode](https://opencode.ai/) after writing provider config. Writes an Ollama-compatible provider to `~/.config/opencode/opencode.json` and updates the recent model state at `~/.local/state/opencode/model.json`, then exec's the `opencode` binary.
180
+
181
+ ```bash
182
+ uv run glm-launch launch opencode --model "some-model"
183
+ ```
184
+
185
+ **Options:**
186
+
187
+ | Flag | Env var | Default | Description |
188
+ |------|---------|---------|-------------|
189
+ | `--model` / `-m` | — | — | Model name to configure in opencode |
190
+ | `--base-url` | `GLM_BASE_URL` | **(required)** | Base URL for the API endpoint |
191
+
192
+ **Examples:**
193
+
194
+ ```bash
195
+ # Launch with a model
196
+ GLM_BASE_URL="http://localhost:11434/v1" uv run glm-launch launch opencode --model "llama3"
197
+
198
+ # Pass extra args through to opencode
199
+ uv run glm-launch launch opencode --model "llama3" -- --some-flag
200
+ ```
201
+
202
+ ### `shell`
203
+
204
+ Print `export` lines that bootstrap your current shell with the GLM env vars — without launching anything. Eval the output and a plain `claude` (or any Anthropic SDK tool) will talk to Z.AI.
205
+
206
+ ```bash
207
+ eval "$(uv run glm-launch shell)"
208
+ claude
209
+ ```
210
+
211
+ Accepts the same model/auth options as `launch claude` (`--model`, `--auth-token`, `--default-*-model`, etc.). Secrets are shell-quoted; empty values are skipped. Sets `ANTHROPIC_MODEL` plus all the `ANTHROPIC_*` / `CLAUDE_CODE_*` vars listed under `launch claude`.
212
+
213
+ ```bash
214
+ # Inspect what would be exported
215
+ uv run glm-launch shell
216
+
217
+ # Bootstrap with a specific model
218
+ eval "$(uv run glm-launch shell --model glm-5.1)"
219
+ ```
220
+
221
+ ### `models`
222
+
223
+ List Z.AI GLM models. By default prints a built-in, annotated list; `--remote` fetches the live list from the Z.AI PaaS endpoint.
224
+
225
+ ```bash
226
+ # Built-in list (no token needed)
227
+ uv run glm-launch models
228
+
229
+ # Live list from the API (needs GLM_AUTH_TOKEN)
230
+ uv run glm-launch models --remote
231
+ ```
232
+
233
+ **Options:**
234
+
235
+ | Flag | Env var | Default | Description |
236
+ |------|---------|---------|-------------|
237
+ | `--remote` / `-r` | — | `false` | Fetch the live list from the Z.AI API |
238
+ | `--models-url` | `GLM_MODELS_URL` | `https://api.z.ai/api/paas/v4/models` | PaaS models endpoint (used with `--remote`) |
239
+ | `--auth-token` | `GLM_AUTH_TOKEN` | — | Auth token (required with `--remote`) |
240
+ | `--timeout` | — | `30.0` | Request timeout in seconds |
241
+
242
+ The live endpoint is the OpenAI-compatible PaaS base (`/api/paas/v4/models`) and uses `Authorization: Bearer <token>` — distinct from the Anthropic-style chat base (`/api/anthropic`) used by `launch claude` and `bench`.
243
+
244
+ ### `bench`
245
+
246
+ Time a single `/v1/messages` round-trip against the configured GLM endpoint. Useful as a sanity check that your auth token, base URL, and chosen model are reachable.
247
+
248
+ ```bash
249
+ uv run glm-launch bench
250
+ ```
251
+
252
+ **Options:**
253
+
254
+ | Flag | Env var | Default | Description |
255
+ |------|---------|---------|-------------|
256
+ | `--model` / `-m` | — | `glm-5.2` | Model to benchmark |
257
+ | `--base-url` | `GLM_BASE_URL` | `https://api.z.ai/api/anthropic` | API endpoint |
258
+ | `--auth-token` | `GLM_AUTH_TOKEN` | **(required)** | Auth token for the endpoint |
259
+ | `--timeout` | — | `30.0` | Request timeout in seconds |
260
+
261
+ Sends a minimal 32-token request and prints the round-trip time. Exits non-zero on HTTP error or timeout.
262
+
263
+ **Example output:**
264
+
265
+ ```
266
+ glm-5.2 via https://api.z.ai/api/anthropic
267
+ OK (200) in 412ms
268
+ ```
269
+
270
+ ### `doctor`
271
+
272
+ Check your environment for correct setup. Reports on environment variables, binary availability, and config files.
273
+
274
+ ```bash
275
+ uv run glm-launch doctor
276
+ ```
277
+
278
+ **Checks performed:**
279
+
280
+ - **Environment variables** — Whether `GLM_BASE_URL`, `GLM_API_KEY`, `GLM_AUTH_TOKEN`, `API_TIMEOUT_MS`, and the `ANTHROPIC_DEFAULT_*_MODEL` vars are set. Secrets are masked in output.
281
+ - **Binaries** — Whether `claude`, `codex`, and `opencode` are found on PATH (with fallback to `~/.claude/local/claude` for claude).
282
+ - **Config files** — Whether `~/.config/opencode/opencode.json` and `~/.local/state/opencode/model.json` exist.
283
+
284
+ Exits with code 1 if any binary is missing, 0 otherwise.
285
+
286
+ **Example output:**
287
+
288
+ ```
289
+ Environment variables:
290
+ GLM_BASE_URL: (not set)
291
+ GLM_API_KEY: (not set)
292
+ GLM_AUTH_TOKEN: (not set)
293
+ API_TIMEOUT_MS: (not set)
294
+ ANTHROPIC_DEFAULT_HAIKU_MODEL: (not set)
295
+ ANTHROPIC_DEFAULT_SONNET_MODEL: (not set)
296
+ ANTHROPIC_DEFAULT_OPUS_MODEL: (not set)
297
+
298
+ Binaries:
299
+ claude: /usr/local/bin/claude
300
+ codex: /usr/local/bin/codex
301
+ opencode: /usr/local/bin/opencode
302
+
303
+ Config files:
304
+ /home/user/.config/opencode/opencode.json: exists
305
+ /home/user/.local/state/opencode/model.json: not found
306
+
307
+ All checks passed.
308
+ ```
309
+
310
+ ## Environment variables
311
+
312
+ | Variable | Used by | Description |
313
+ |----------|---------|-------------|
314
+ | `GLM_BASE_URL` | `launch claude`, `launch opencode`, `shell` | API base URL |
315
+ | `GLM_API_KEY` | `launch claude`, `shell` | API key |
316
+ | `GLM_AUTH_TOKEN` | `launch claude`, `shell`, `bench`, `models --remote` | Z.AI auth token (required) |
317
+ | `GLM_MODELS_URL` | `models --remote` | PaaS models endpoint |
318
+ | `API_TIMEOUT_MS` | `launch claude`, `shell` | Request timeout in milliseconds |
319
+ | `ANTHROPIC_DEFAULT_HAIKU_MODEL` | `launch claude`, `shell` | Model for Haiku-tier requests |
320
+ | `ANTHROPIC_DEFAULT_SONNET_MODEL` | `launch claude`, `shell` | Model for Sonnet-tier requests |
321
+ | `ANTHROPIC_DEFAULT_OPUS_MODEL` | `launch claude`, `shell` | Model for Opus-tier requests |
322
+ | `CLAUDE_CODE_SUBAGENT_MODEL` | `launch claude`, `shell` | Model used for spawned subagents |
323
+ | `CLAUDE_CODE_EFFORT_LEVEL` | `launch claude`, `shell` | Effort level for the agent loop |
324
+ | `CLAUDE_CODE_ATTRIBUTION_HEADER` | `launch claude`, `shell` | Attribution header toggle (`0` disables it) |
325
+ | `CLAUDE_CODE_AUTO_COMPACT_WINDOW` | `launch claude`, `shell` | Auto-compact context window in tokens |
326
+
327
+ ## How it works
328
+
329
+ Each provider follows the same pattern:
330
+
331
+ 1. Resolve the binary on PATH (with optional fallback path)
332
+ 2. Set up configuration (env vars for claude, config files for opencode, flags for codex)
333
+ 3. `os.execvpe()` the binary — fully replacing the glm process with the underlying tool for direct stdio passthrough
334
+
335
+ For Claude specifically, Z.AI exposes an Anthropic-compatible endpoint at `https://api.z.ai/api/anthropic`, so no local proxy is needed. The CLI sets the standard `ANTHROPIC_*` env vars and Claude Code talks directly to Z.AI.
336
+
337
+ ## Development
338
+
339
+ Common tasks are wrapped in a [`justfile`](https://github.com/casey/just). Run `just` with no arguments to list them.
340
+
341
+ | Recipe | Description |
342
+ |--------|-------------|
343
+ | `just bootstrap` | Upgrade `pip`/`uv`, then `uv sync` |
344
+ | `just sync` | `uv sync` the project dependencies |
345
+ | `just lock` | `uv lock` the dependency versions |
346
+ | `just build` | `uv build` the wheel and sdist |
347
+ | `just publish` | `uv publish` to PyPI |
348
+ | `just bump *ARGS` | Bump the CalVer version with `bumpver` (e.g. `just bump`) |
349
+ | `just bump-dry *ARGS` | Preview a version bump without writing changes |
350
+ | `just lint *ARGS` | Run the [prek](https://github.com/j178/prek) hooks (defaults to `--all-files`) |
351
+ | `just fmt` | Format the `justfile` itself |
352
+ | `just demo` | Smoke-test the CLI by listing models |
353
+
354
+ Versioning follows [CalVer](https://calver.org/) (`YYYY.MM.INC1`), and lint hooks (ruff, pyupgrade, validate-pyproject) are configured in `.pre-commit-config.yaml` and run with `prek`.