@tuned-tensor/cli 0.13.1 → 0.15.0
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 +153 -69
- package/dist/{chunk-CAEBS5HH.js → chunk-YGN26POJ.js} +4 -3
- package/dist/chunk-YGN26POJ.js.map +1 -0
- package/dist/index.js +4405 -201
- package/dist/index.js.map +1 -1
- package/dist/local-runtime.js +124 -33
- package/dist/local-runtime.js.map +1 -1
- package/docs/local-runtime/architecture.md +11 -7
- package/docs/local-runtime/serving.md +171 -0
- package/docs/local-runtime/spark.md +4 -2
- package/package.json +3 -1
- package/training/adapter/src/model_contract.py +1 -1
- package/training/adapter/src/prefetch.py +1 -1
- package/training/adapter/src/serve.py +133 -267
- package/training/adapter/src/train.py +2 -2
- package/training/serving/pyproject.toml +9 -0
- package/training/serving/uv.lock +2785 -0
- package/dist/chunk-CAEBS5HH.js.map +0 -1
|
@@ -1,8 +1,12 @@
|
|
|
1
1
|
# Architecture
|
|
2
2
|
|
|
3
|
-
This
|
|
4
|
-
|
|
5
|
-
|
|
3
|
+
This document describes the local CUDA runtime bundled with the unified `tt`
|
|
4
|
+
agent and CLI. The standalone `tt-local` product surface is deprecated. Local
|
|
5
|
+
workflow commands need no TT token. Managed agent inference reuses a TT access
|
|
6
|
+
token; BYO inference uses the selected provider's credentials. Cloud operations
|
|
7
|
+
are explicit through `tt cloud` and use the TT account token.
|
|
8
|
+
|
|
9
|
+
The local adapter runtime boundary is text SFT of a registry-certified
|
|
6
10
|
Transformers causal LM into a LoRA adapter on CUDA. Certified checkpoints
|
|
7
11
|
are `Qwen/Qwen3.5-2B` (pinned to Hugging Face snapshot
|
|
8
12
|
`15852e8c16360a2fea060d615a32b45270f8a8fc`),
|
|
@@ -28,7 +32,7 @@ implementation details, not a public plugin framework.
|
|
|
28
32
|
|
|
29
33
|
## Boundaries
|
|
30
34
|
|
|
31
|
-
The
|
|
35
|
+
The local adapter runtime excludes:
|
|
32
36
|
|
|
33
37
|
- arbitrary training or evaluation commands;
|
|
34
38
|
- DPO, continued pretraining, and multimodal training;
|
|
@@ -40,7 +44,7 @@ The first version intentionally excludes:
|
|
|
40
44
|
The next model or method should arrive with its own locked dependencies,
|
|
41
45
|
resource defaults, data contract, and real CUDA acceptance test.
|
|
42
46
|
|
|
43
|
-
TT
|
|
47
|
+
TT bundles two local training methods:
|
|
44
48
|
|
|
45
49
|
- **Adapter** (`training/adapter`): certified Transformers checkpoints and
|
|
46
50
|
PEFT LoRA SFT. Driven by `tt pipeline run`.
|
|
@@ -90,7 +94,7 @@ The bundled Python project owns four small operations:
|
|
|
90
94
|
- `prefetch.py`: download and verify the pinned Hugging Face snapshot;
|
|
91
95
|
- `evaluate.py`: generate predictions without receiving reference answers;
|
|
92
96
|
- `train.py`: perform CUDA-only, model-specific LoRA SFT;
|
|
93
|
-
- `serve.py`:
|
|
97
|
+
- `serve.py`: prepare the verified base model and adapter for the vLLM serving runtime.
|
|
94
98
|
|
|
95
99
|
Training uses assistant-only loss. Prompt tokens have label `-100`, and
|
|
96
100
|
truncation removes older prompt tokens before it removes any answer token.
|
|
@@ -126,7 +130,7 @@ hide a valid artifact. Serving verifies the manifest again.
|
|
|
126
130
|
The runner config controls only:
|
|
127
131
|
|
|
128
132
|
- state, artifact, and Hugging Face cache paths;
|
|
129
|
-
- CUDA or CPU
|
|
133
|
+
- CUDA or CPU evaluation, with local serving through the CUDA vLLM runtime;
|
|
130
134
|
- deterministic generation and scoring limits.
|
|
131
135
|
|
|
132
136
|
The training project, Python entrypoints, working directory, and child
|
|
@@ -0,0 +1,171 @@
|
|
|
1
|
+
# Local serving and coding harnesses
|
|
2
|
+
|
|
3
|
+
`tt serve` verifies TT artifacts and launches **vLLM 0.28.0**. vLLM owns model
|
|
4
|
+
execution, batching, KV/prefix caching, streaming, and native tool-call parsing.
|
|
5
|
+
This local serving path connects the harness directly to vLLM; TT's managed
|
|
6
|
+
agent proxy is a separate inference option. The serving dependencies are locked
|
|
7
|
+
separately from training, in an external cache environment; an npm upgrade does
|
|
8
|
+
not mutate the training runtime.
|
|
9
|
+
|
|
10
|
+
## Requirements and scope
|
|
11
|
+
|
|
12
|
+
- The packaged serving runtime requires **Linux and NVIDIA CUDA**. CPU/macOS
|
|
13
|
+
serving is not supported by this runtime; CLI/package commands still work
|
|
14
|
+
there. Unsupported hardware or model/adapter combinations fail rather than
|
|
15
|
+
silently falling back to the old server.
|
|
16
|
+
- Install `uv` and prefetch the certified model with `tt models prefetch`.
|
|
17
|
+
First launch installs the locked serving dependencies and may compile kernels;
|
|
18
|
+
it needs substantially more time and disk than a warm request. CUDA JIT may
|
|
19
|
+
require a working CUDA toolkit/C++ toolchain. Model loading remains offline.
|
|
20
|
+
- Foundation checkpoints and image inputs are not supported by this path.
|
|
21
|
+
- Qwen3.5-2B base and a one-step, rank-16 `all-linear` TT-shaped adapter have been
|
|
22
|
+
exercised on GB10. The registry's Nemotron and Muse Glimmer architectures have
|
|
23
|
+
upstream support, but their exact adapters/hardware combinations are **not
|
|
24
|
+
certified by that Qwen smoke test**. No 70B model was tested here.
|
|
25
|
+
|
|
26
|
+
## Serve once, compare base and tuned
|
|
27
|
+
|
|
28
|
+
```bash
|
|
29
|
+
tt models prefetch tunedtensor.json
|
|
30
|
+
|
|
31
|
+
tt serve local-<run-id> --config local-runner.json \
|
|
32
|
+
--context-length 8192 --max-tokens 512
|
|
33
|
+
```
|
|
34
|
+
|
|
35
|
+
This exposes **both** `local-<run-id>` and `base:<base-model-id>` at the same
|
|
36
|
+
endpoint, sharing the base weights. The adapter is registered at startup; TT
|
|
37
|
+
never enables runtime adapter upload/loading. There is no merge/export step
|
|
38
|
+
and no modification of the verified weights. `tt serve base` starts base-only.
|
|
39
|
+
`active` still fails when no adapter is activated.
|
|
40
|
+
|
|
41
|
+
Artifact integrity, certified base revisions, and stored behavior-prompt
|
|
42
|
+
fingerprints retain their verification. A stored adapter's behavior prompt is
|
|
43
|
+
applied to both model IDs for comparison. `tt serve base` without explicit
|
|
44
|
+
`--spec` does not inject the adjacent spec; use `--spec tunedtensor.json` for that.
|
|
45
|
+
`--no-spec-prompt` is the explicit opt-out. A small generated template prefix
|
|
46
|
+
preserves the owner instructions while leaving tool messages and upstream chat
|
|
47
|
+
formatting intact; it never changes the saved tokenizer/template.
|
|
48
|
+
|
|
49
|
+
### Resource controls
|
|
50
|
+
|
|
51
|
+
- `--context-length`: total context budget, default 16,384 tokens. Keep it large
|
|
52
|
+
enough for the harness's instructions and tool results, not just the question.
|
|
53
|
+
- `--max-tokens`: generation budget, default 512. vLLM receives this through its
|
|
54
|
+
generation configuration; the upstream API owns per-request validation.
|
|
55
|
+
- `--gpu-memory-utilization`: fraction of device memory budgeted to vLLM,
|
|
56
|
+
default 0.8. On shared-memory machines leave room for the OS and other work.
|
|
57
|
+
For the small Qwen GB10 smoke we used **0.15**; this is not suitable for every
|
|
58
|
+
model size. Reduce the context or memory budget when upstream reports a fit
|
|
59
|
+
failure, and ensure the weights themselves still fit.
|
|
60
|
+
- `--max-concurrent-requests`: maximum sequences scheduled in a vLLM batch,
|
|
61
|
+
default one, maximum eight. This is upstream batching, **not** the previous
|
|
62
|
+
HTTP admission/429 contract; upstream may queue additional requests.
|
|
63
|
+
|
|
64
|
+
Health becomes ready after loading/warm-up. Ctrl-C terminates the process group.
|
|
65
|
+
A port conflict is checked before loading; upstream owns the final bind and any
|
|
66
|
+
race. The unreleased custom server's `--merge-adapter` flag is removed.
|
|
67
|
+
|
|
68
|
+
## Pi
|
|
69
|
+
|
|
70
|
+
Export a new isolated configuration rather than replacing global settings:
|
|
71
|
+
|
|
72
|
+
```bash
|
|
73
|
+
export PI_CODING_AGENT_DIR="$(mktemp -d)"
|
|
74
|
+
tt serve local-<run-id> --config local-runner.json \
|
|
75
|
+
--context-length 8192 --max-tokens 512 \
|
|
76
|
+
--print-client-config pi > "$PI_CODING_AGENT_DIR/models.json"
|
|
77
|
+
```
|
|
78
|
+
|
|
79
|
+
Use the same launch options as the running server. Exporting config verifies the
|
|
80
|
+
TT target but does not start a server. Adapter exports include both model IDs.
|
|
81
|
+
The exported `tt-local` provider ID names this local endpoint; it is not a
|
|
82
|
+
separate CLI or package and uses no TT account token. For example, in a
|
|
83
|
+
disposable coding-fixture directory:
|
|
84
|
+
|
|
85
|
+
```bash
|
|
86
|
+
pi --provider tt-local --model 'base:Qwen/Qwen3.5-2B' \
|
|
87
|
+
--tools read --no-extensions --no-skills --no-prompt-templates \
|
|
88
|
+
--no-context-files --no-session --offline --thinking off \
|
|
89
|
+
-p 'Read fixture.py and explain what its function returns.'
|
|
90
|
+
```
|
|
91
|
+
|
|
92
|
+
Repeat with `--model local-<run-id>` in a fresh session. `--tools read` is a
|
|
93
|
+
read-only tool allowlist, **not a filesystem sandbox**. Use a disposable account
|
|
94
|
+
or an enforcing harness permission boundary for untrusted tasks. Enable edits
|
|
95
|
+
or shell commands only when you intend to grant those permissions.
|
|
96
|
+
|
|
97
|
+
For question-only comparisons, `--no-tools` remains an optional experiment
|
|
98
|
+
setting. It is no longer a server requirement. `reasoning: false` and
|
|
99
|
+
`supportsReasoningEffort: false` in the Pi export describe this endpoint's
|
|
100
|
+
reasoning-control contract; **neither disables tool calls or asserts that the
|
|
101
|
+
model cannot reason**.
|
|
102
|
+
|
|
103
|
+
## OpenCode
|
|
104
|
+
|
|
105
|
+
OpenCode can connect directly using its existing custom provider support:
|
|
106
|
+
|
|
107
|
+
```json
|
|
108
|
+
{
|
|
109
|
+
"$schema": "https://opencode.ai/config.json",
|
|
110
|
+
"provider": {
|
|
111
|
+
"tt-local": {
|
|
112
|
+
"npm": "@ai-sdk/openai-compatible",
|
|
113
|
+
"name": "TT local endpoint",
|
|
114
|
+
"options": { "baseURL": "http://127.0.0.1:8000/v1" },
|
|
115
|
+
"models": {
|
|
116
|
+
"base:Qwen/Qwen3.5-2B": {
|
|
117
|
+
"name": "TT base",
|
|
118
|
+
"limit": { "context": 8192, "output": 512 }
|
|
119
|
+
}
|
|
120
|
+
}
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
```
|
|
125
|
+
|
|
126
|
+
Add the exact adapter ID from `/v1/models` to compare it. Set the actual server
|
|
127
|
+
budgets, configure OpenCode's permissions, and select
|
|
128
|
+
`opencode run --model 'tt-local/base:Qwen/Qwen3.5-2B' ...`. TT does not install a
|
|
129
|
+
second agent framework or change global OpenCode configuration.
|
|
130
|
+
|
|
131
|
+
## Tool support and security
|
|
132
|
+
|
|
133
|
+
TT selects upstream parsers for the registered models:
|
|
134
|
+
|
|
135
|
+
- Qwen3.5-2B: `qwen3_xml`.
|
|
136
|
+
- Nemotron 3.5 Lightning: `qwen3_coder` (ordinary non-thinking template mode).
|
|
137
|
+
- Muse Glimmer: `muse_glimmer`.
|
|
138
|
+
|
|
139
|
+
These are protocol integrations, not guarantees that a model will choose the
|
|
140
|
+
right tool or produce correct code. A complete test must observe a tool call,
|
|
141
|
+
execute an allowed tool, send its result back, and verify the final answer.
|
|
142
|
+
The harness owns tool execution/permissions; vLLM only generates the calls.
|
|
143
|
+
Fine-tuning can change tool reliability, so compare the tuned model too.
|
|
144
|
+
|
|
145
|
+
The default bind is `127.0.0.1:8000`. Non-loopback binds require both
|
|
146
|
+
`--allow-remote` and `--api-key-env NAME`. An authentication-only middleware
|
|
147
|
+
extends the bearer check to **all** upstream HTTP routes, including health,
|
|
148
|
+
tokenization, and administrative routes; vLLM's built-in guard covers only
|
|
149
|
+
selected prefixes. No token is put in argv or exported client configuration.
|
|
150
|
+
Pi uses `${NAME}` interpolation; OpenCode can use `"apiKey": "{env:NAME}"`.
|
|
151
|
+
Provide the variable separately to each process. Without `--api-key-env`, local
|
|
152
|
+
serving is unauthenticated. Use a trusted host or encrypted tunnel, never expose
|
|
153
|
+
plain HTTP directly to the Internet. Request/output logging and vLLM usage
|
|
154
|
+
telemetry are disabled by the TT launcher.
|
|
155
|
+
|
|
156
|
+
## API and measurement
|
|
157
|
+
|
|
158
|
+
Use `/health`, `/v1/models`, and `/v1/chat/completions`. API bodies, SSE events,
|
|
159
|
+
usage, tool calls, cancellation, and error semantics come from the pinned
|
|
160
|
+
upstream server, not a TT approximation. The old custom server's message/byte
|
|
161
|
+
limits, HTTP errors, and health JSON are not preserved as an API contract.
|
|
162
|
+
|
|
163
|
+
Measure startup and first-request compilation separately from steady-state
|
|
164
|
+
first-text latency and tokens/second. Compare identical prompts, templates,
|
|
165
|
+
budgets, and fresh harness sessions on an otherwise-idle machine. Test generated
|
|
166
|
+
code independently; a tiny one-step adapter proves integration, not better
|
|
167
|
+
coding. Pi's zero provider token prices do not mean zero hardware cost.
|
|
168
|
+
|
|
169
|
+
References: [vLLM LoRA](https://docs.vllm.ai/en/v0.28.0/features/lora/),
|
|
170
|
+
[Nemotron tool configuration](https://docs.nvidia.com/nim/large-language-models/latest/get-started/advanced/get-started-nemotron-3.5-lightning.html),
|
|
171
|
+
[OpenCode custom providers](https://opencode.ai/docs/providers/#custom-provider).
|
|
@@ -26,8 +26,10 @@ this GPU. Spark unified memory should show Nemotron and Muse Glimmer as
|
|
|
26
26
|
trainable; consumer cards typically only fit Qwen LoRA. `tt status` and the
|
|
27
27
|
shell agent reuse the cached report.
|
|
28
28
|
|
|
29
|
-
TT
|
|
30
|
-
for the Hugging Face cache plus run artifacts.
|
|
29
|
+
Local TT training requires Node 22.19+, `uv`, working CUDA PyTorch, and enough free space
|
|
30
|
+
for the Hugging Face cache plus run artifacts. Local commands need no TT
|
|
31
|
+
access token. Agent inference can use your TT token through the managed proxy,
|
|
32
|
+
or your own provider credentials and model.
|
|
31
33
|
|
|
32
34
|
## Create a project
|
|
33
35
|
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@tuned-tensor/cli",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.15.0",
|
|
4
4
|
"description": "Local TT agent and CUDA fine-tuning CLI for Tuned Tensor workflows",
|
|
5
5
|
"repository": {
|
|
6
6
|
"type": "git",
|
|
@@ -25,6 +25,8 @@
|
|
|
25
25
|
"training/adapter/pyproject.toml",
|
|
26
26
|
"training/adapter/uv.lock",
|
|
27
27
|
"training/adapter/src/*.py",
|
|
28
|
+
"training/serving/pyproject.toml",
|
|
29
|
+
"training/serving/uv.lock",
|
|
28
30
|
"training/foundation/pyproject.toml",
|
|
29
31
|
"training/foundation/uv.lock",
|
|
30
32
|
"training/foundation/src/*.py",
|
|
@@ -110,7 +110,7 @@ def assert_certified_model_config(
|
|
|
110
110
|
)
|
|
111
111
|
return
|
|
112
112
|
else:
|
|
113
|
-
raise ValueError(f"{label} is not a certified TT
|
|
113
|
+
raise ValueError(f"{label} is not a certified TT base-model architecture")
|
|
114
114
|
|
|
115
115
|
for name, expected in certified.items():
|
|
116
116
|
actual = _field(text_config, name)
|
|
@@ -147,7 +147,7 @@ def verify_snapshot(snapshot: Path, expected_model_id: str | None = None) -> tup
|
|
|
147
147
|
|
|
148
148
|
|
|
149
149
|
def main() -> None:
|
|
150
|
-
parser = argparse.ArgumentParser(description="Prefetch a TT
|
|
150
|
+
parser = argparse.ArgumentParser(description="Prefetch a TT Hugging Face base model for local use.")
|
|
151
151
|
parser.add_argument("--input", required=True)
|
|
152
152
|
parser.add_argument("--output", required=True)
|
|
153
153
|
args = parser.parse_args()
|