@octocodeai/freellama-mcp-server 0.10.0 → 0.12.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/CONFIGURATION.md +82 -3
- package/DEVELOPING.md +40 -9
- package/README.md +316 -213
- package/dist/agent-cli.js +16963 -0
- package/dist/index.js +4896 -4036
- package/dist/research/bash-agent.js +287 -108
- package/dist/research/coder-agent.js +455 -127
- package/dist/research/github-agent.js +276 -94
- package/dist/research/octocode-agent.js +276 -94
- package/docs/AGENT_CLI.md +234 -0
- package/docs/API.md +160 -0
- package/docs/ARCHITECTURE.md +158 -50
- package/docs/ASSESSMENT.md +131 -0
- package/docs/BENCHMARK.md +381 -0
- package/docs/BUILD_AND_NOTES.md +12 -3
- package/docs/CLI.md +62 -17
- package/docs/CPU_GPU_ROUTING.md +22 -9
- package/docs/DEFERRED_JOBS.md +17 -4
- package/docs/FEATURES.md +97 -43
- package/docs/LLAMACPP.md +133 -0
- package/docs/LOCAL_MODELS.md +26 -20
- package/docs/MODEL_FORMS_AND_RESULTS.md +14 -6
- package/docs/MODEL_INTROSPECTION.md +9 -2
- package/docs/MODEL_SELECTION.md +38 -9
- package/docs/MONITORING.md +110 -12
- package/docs/OLLAMA_REVIEW.md +226 -0
- package/docs/PRODUCTION.md +68 -25
- package/docs/PROMPTS.md +119 -0
- package/docs/README.md +22 -6
- package/docs/RELIABILITY.md +207 -0
- package/docs/RUST_RESOURCE_AUDIT.md +65 -0
- package/docs/SCOPES_AND_WARMING.md +12 -5
- package/docs/TESTING.md +112 -6
- package/docs/TUNING.md +12 -8
- package/docs/assets/benchmark-results-2026-11-14.html +4 -0
- package/docs/assets/tool-calling-2026-11-14-bonsai-9b/TABLE.md +14 -0
- package/docs/assets/tool-calling-2026-11-14-lfm3-vl/TABLE.md +14 -0
- package/docs/assets/tool-calling-table.md +14 -0
- package/docs/cookbooks/README.md +9 -2
- package/docs/cookbooks/batch-text.md +4 -2
- package/docs/cookbooks/classify.md +19 -3
- package/docs/cookbooks/coding.md +13 -4
- package/docs/cookbooks/find-code.md +8 -3
- package/docs/cookbooks/jobs.md +8 -8
- package/docs/cookbooks/memory-and-caching.md +2 -2
- package/docs/cookbooks/ocr.md +3 -3
- package/docs/cookbooks/research-agent.md +32 -2
- package/docs/cookbooks/speech-to-text.md +1 -1
- package/docs/cookbooks/sweep.md +4 -1
- package/docs/octocode/GITHUB.md +4 -4
- package/docs/octocode/LOCAL.md +5 -4
- package/native/index.d.ts +1 -1
- package/package.json +6 -6
- package/docs/COMPARISON.md +0 -40
package/docs/LOCAL_MODELS.md
CHANGED
|
@@ -1,9 +1,10 @@
|
|
|
1
1
|
# Local model catalog
|
|
2
2
|
|
|
3
|
-
|
|
4
|
-
published. The method for choosing a model on other hardware is in
|
|
5
|
-
[Choose local models](MODEL_SELECTION.md). For
|
|
6
|
-
or `freellama catalog`;
|
|
3
|
+
A dated comparison of local models for each job on one machine, separating measured results
|
|
4
|
+
from published claims. The method for choosing a model on other hardware is in
|
|
5
|
+
[Choose local models](MODEL_SELECTION.md). For current installed candidates, use `models {view:"catalog"}`
|
|
6
|
+
or `freellama catalog`; job execution first consults [machine-local calibration](MODEL_SELECTION.md#turn-measurements-into-routing-evidence),
|
|
7
|
+
then catalog fallback. The tables below do not pin that live choice. For exact calls, see the [cookbooks](cookbooks/README.md).
|
|
7
8
|
|
|
8
9
|
**Snapshot:** 2026-11-01. Apple M2 Pro, 32 GB unified memory, Ollama 0.40.13, FreeLlama 0.8.0. Other
|
|
9
10
|
work was running throughout, leaving about 4–14 GB available. Each model answered the same questions
|
|
@@ -30,11 +31,11 @@ Group a model by the job it does, using the capability Ollama reports. FreeLlama
|
|
|
30
31
|
| Speech | `speech` | `speech` | Text to speech | `audio {action:"speak", text}` |
|
|
31
32
|
| Embedding | `embedding` | `embedding_only` | Code search, duplicates, image search | `run_task {task:"embedding", files, nearest}` |
|
|
32
33
|
| Decision | `decision` | `decision` | Classify, triage, route, yes/no | `run_task {task:"decision", state, questions}` |
|
|
33
|
-
| Not runnable in Ollama | none | none | Rerankers, tiny classifiers, most dedicated speech models |
|
|
34
|
+
| Not runnable in Ollama | none | none | Rerankers, tiny classifiers, most dedicated speech models | Ollama cannot run these; the [managed llama.cpp adapter](LLAMACPP.md) supports only its documented text-task subset |
|
|
34
35
|
|
|
35
|
-
##
|
|
36
|
+
## Historical tested picks for each job
|
|
36
37
|
|
|
37
|
-
###
|
|
38
|
+
### Installed at the snapshot: fit alongside normal work
|
|
38
39
|
|
|
39
40
|
| Job | Model | File | Memory needed | Evidence |
|
|
40
41
|
|---|---|---:|---:|---|
|
|
@@ -42,13 +43,13 @@ Group a model by the job it does, using the capability Ollama reports. FreeLlama
|
|
|
42
43
|
| Find code for an issue | `embeddinggemma-2:740m-q8_0` | 1.3 GB | 1.4 GB | Measured: right file first 9/10, top 3 9/10; `nomic-embed-text` 6/10 and 8/10, but indexes in 42 s against 67 s |
|
|
43
44
|
| Find duplicates | `nomic-embed-text:v1.5` | 0.3 GB | 1.4 GB | Measured: 8/12 real issue pairs |
|
|
44
45
|
| Find an image by describing it | `embeddinggemma-2:740m-q8_0` | 1.3 GB | 1.4 GB | Measured: 5/5 screenshots, about 1 s per query |
|
|
45
|
-
| OCR, reading text in images | `hf.co/openbmb/MiniCPM-OCR-1.0-gguf:Q4_K_M` | 1.4 GB | 3.8 GB | Measured: 30/30 in all 3 rounds, 257 ms median; `
|
|
46
|
+
| OCR, reading text in images | `hf.co/openbmb/MiniCPM-OCR-1.0-gguf:Q4_K_M` | 1.4 GB | 3.8 GB | Measured: 30/30 in all 3 rounds, 257 ms median. Its tables come back as OTSL; `read-table` turns them into Markdown |
|
|
46
47
|
| Image understanding | `lfm3-vl:2b-q4_K_M` | 1.5 GB | 4.1 GB | Measured: 20/20 drawn images in all 3 rounds, 299 ms; `lfm3-omni` 18/20, `bonsai-2:9b` 17/20 |
|
|
47
48
|
| Speech to text | `lfm3-audio:2b-q4_K_M` | 1.7 GB | 5.5 GB | Measured: 1.7% word error on 12 generated sentences, 276 ms median, French and Spanish translation worked; `lfm3-omni` the same |
|
|
48
49
|
| Text to speech | `phonon:en` | 0.1 GB | not previewed | Measured: 0.8–1.7% word error when transcribed back, 102 ms median; both LFM3 models 0% at 950 ms, but the judge is an LFM3 model |
|
|
49
|
-
| Small coding tasks | `
|
|
50
|
+
| Small coding tasks | `bonsai-2:9b` | 3.2 GB | 10.3 GB | Measured: 19, 19, 17 of 25, 475 ms median, and every workflow case right in the 2026-11-12 field test. `lfm3:1.7b` scored 21, 20, 20 on the questions but answered workflows with tool calls nobody asked for, so it is no longer a pick |
|
|
50
51
|
|
|
51
|
-
###
|
|
52
|
+
### Installed at the snapshot: need more free memory
|
|
52
53
|
|
|
53
54
|
| Job | Model | File | Memory needed | Evidence |
|
|
54
55
|
|---|---|---:|---:|---|
|
|
@@ -66,7 +67,7 @@ Group a model by the job it does, using the capability Ollama reports. FreeLlama
|
|
|
66
67
|
| `bonsai-2:27b` | 8.3 GB | Installed. FreeLlama asks for 16.3 GB available; this machine never had more than 14.4 GB, so it is not measured here. Published: SWE-bench Verified 60.8%, LiveCodeBench 90.1% |
|
|
67
68
|
| `qwen3.6:27b-q4_K_M` | 17.4 GB | Needs 28.7 GB available, so only on a nearly empty 32 GB machine. Removed from this machine untested |
|
|
68
69
|
|
|
69
|
-
###
|
|
70
|
+
### Candidates at the snapshot: not installed, untested here
|
|
70
71
|
|
|
71
72
|
Pull a tag only with approval for that exact tag and size.
|
|
72
73
|
|
|
@@ -97,9 +98,11 @@ score) in one forward pass, with no generated text. Local decision models follow
|
|
|
97
98
|
The original Nimble 9B (not v3) scored 75.7% against Jev 1.13's 76.0% on the same 3,880 human-labeled
|
|
98
99
|
decisions; its publisher ran that test.
|
|
99
100
|
|
|
100
|
-
**
|
|
101
|
-
|
|
102
|
-
|
|
101
|
+
**Historical interpretation:** `strands-decider` was the smaller starting point and
|
|
102
|
+
`nimble-v3:9b-q4_K_M` a candidate for harder decisions in this sample. The 35/36 issue result
|
|
103
|
+
is one dataset, not a calibrated accuracy guarantee. Compare exact installed tags on your own
|
|
104
|
+
labeled data and use [machine-local evidence](MODEL_SELECTION.md#turn-measurements-into-routing-evidence)
|
|
105
|
+
before changing the live choice.
|
|
103
106
|
|
|
104
107
|
**Limits of this comparison:**
|
|
105
108
|
|
|
@@ -111,9 +114,9 @@ Other families:
|
|
|
111
114
|
|
|
112
115
|
- `d1`, `d1-omni` and `d3` publish other benchmarks, so they are not ranked here. `d1-omni` matters when decisions need images or audio.
|
|
113
116
|
- `jevos-v4` claims 28–130 ms on a laptop CPU with its own binary and also ships GGUF files. No JevBench score was found, and loading in Ollama was not checked.
|
|
114
|
-
- `openjev`
|
|
117
|
+
- `openjev` was listed as 27B under CC-BY-NC in this snapshot; inspect the current repository license before use.
|
|
115
118
|
|
|
116
|
-
##
|
|
119
|
+
## Candidates found on Hugging Face and Ollama, 2026-10-31
|
|
117
120
|
|
|
118
121
|
Trending on 2026-10-31 and filtered to what could fit. Quality is the publishers' claim. **Path**:
|
|
119
122
|
Ollama is an official tag, HF GGUF pulls as `hf.co/<repo>:<quant>`, and "not via Ollama" needs another
|
|
@@ -152,25 +155,28 @@ through the real CLI.
|
|
|
152
155
|
| Model | Local questions | GitHub questions | Notes |
|
|
153
156
|
|---|---:|---:|---|
|
|
154
157
|
| `lfm3-audio:2b-q4_K_M` | 3, 3, 3 of 8 | 3, 3, 3 of 6 | Guessed names and repeated calls; 3.2 calls per question |
|
|
155
|
-
| `lfm3:1.7b-q4_K_M` | 6, 5, 5 of 8 | 1, 1, 1 of 6 | Good on local lookups, weak on GitHub; 2 calls per question, 20 s median |
|
|
158
|
+
| `lfm3:1.7b-q4_K_M` | 6, 5, 5 of 8 | 1, 1, 1 of 6 | Good on local lookups, weak on GitHub; 2 calls per question, 20 s median. No longer a pick |
|
|
156
159
|
| `bonsai-2:9b` | 4, 5, 5 of 8 | 3, 5, 5 of 6 | 2.2 calls per question; 82 s median per question |
|
|
157
160
|
| Nemotron-3.5-Bolt-E4B | 6, 6, 6 of 8 | 5, 5, 5 of 6 | 2.2 calls per question; 96 s median per question; needs 13.5 GB |
|
|
158
161
|
|
|
159
162
|
Three rounds each. An answer counts as right only if it contains every expected fact and rests on at
|
|
160
|
-
least one tool call.
|
|
163
|
+
least one tool call. These historical research outcomes are separate from the newer
|
|
164
|
+
[tool-calling smoke suite](RELIABILITY.md#measured-on-2026-11-14), which has two exact models and
|
|
165
|
+
one trial per public case and does not establish general agent reliability.
|
|
161
166
|
|
|
162
167
|
## What runs in FreeLlama
|
|
163
168
|
|
|
164
169
|
- **Managed, with routing, memory checks and receipts:** chat, coding, vision, embeddings, decisions.
|
|
165
170
|
- **Through serve's passthrough, with memory checks:** speech and transcription (`audio`).
|
|
166
|
-
- **
|
|
171
|
+
- **Managed llama.cpp text tasks:** one operator-run loopback `llama-server`, selected explicitly as `name/model`; see the [supported task subset and lifecycle limits](LLAMACPP.md).
|
|
172
|
+
- **Not supported:** separate images per question in one decision, because Ollama shares images across all questions.
|
|
167
173
|
- **Hugging Face:** GGUF repositories work in discovery and pull through Ollama as `hf.co/<repo>:<quant>`. Multimodal GGUF needs an Ollama-supported architecture.
|
|
168
174
|
|
|
169
175
|
## Still open
|
|
170
176
|
|
|
171
177
|
- Measure `bonsai-2:27b` when 16.3 GB is available.
|
|
172
178
|
- Measure audio embeddings through `files`; image embeddings are measured, audio ones are not.
|
|
173
|
-
-
|
|
179
|
+
- Evaluate the dated candidates above only after checking current availability and approving any exact-tag download.
|
|
174
180
|
- Test `embeddinggemma-2` on duplicates; only `nomic-embed-text` is measured there.
|
|
175
181
|
|
|
176
182
|
## Detailed results
|
|
@@ -1,10 +1,14 @@
|
|
|
1
1
|
# Model forms and measured results
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
Dated measurements describe one machine and workload. Current job/workflow selection uses
|
|
4
|
+
[machine-local calibration](MODEL_SELECTION.md#turn-measurements-into-routing-evidence) before
|
|
5
|
+
catalog fallback; the historical ratings below do not determine that choice. Newer
|
|
6
|
+
[tool-calling evidence](RELIABILITY.md#measured-on-2026-11-14) covers two models with one trial on
|
|
7
|
+
each of seven public cases, separately from the older single-call examples below.
|
|
4
8
|
|
|
5
9
|
## Model forms
|
|
6
10
|
|
|
7
|
-
|
|
11
|
+
Ollama-managed forms get routing, admission and a receipt; passthrough forms reach Ollama through `serve`
|
|
8
12
|
with the raw stream cap and memory checks but no routing or receipt.
|
|
9
13
|
|
|
10
14
|
| Form | Ollama endpoint | Through FreeLlama | Measured here |
|
|
@@ -19,21 +23,25 @@ with the raw stream cap and memory checks but no routing or receipt.
|
|
|
19
23
|
| Transcription and translation | `/v1/audio/transcriptions`, `/v1/audio/translations` | MCP `audio`, through the passthrough's memory checks; LFM3 audio needs Ollama 0.40.12+ | `lfm3-audio:2b-q4_K_M` transcription 7.5% word error over 5 sentences; translation not measured |
|
|
20
24
|
| Image generation | removed from Ollama in 0.32.6 | not available | — |
|
|
21
25
|
|
|
22
|
-
|
|
26
|
+
The [managed llama.cpp adapter](LLAMACPP.md) also supports explicit bounded text tasks; it does
|
|
27
|
+
not inherit Ollama's modalities, automatic catalog discovery or placement evidence.
|
|
28
|
+
|
|
29
|
+
Find Ollama forms with `models {view:"library", capabilities:["decision"]}` (or `audio`,
|
|
23
30
|
`embedding`, `vision`...), or a Hugging Face GGUF build with a `query`.
|
|
24
31
|
|
|
25
32
|
### Local models, measured
|
|
26
33
|
|
|
27
34
|
One Apple M2 Pro (32 GB), Ollama 0.40.8, FreeLlama 0.6.1, 2026-10-30, while other builds kept the
|
|
28
35
|
one-minute load near 14 on 12 cores. Each check has a known answer; the batteries are small, so read
|
|
29
|
-
the ratings as
|
|
36
|
+
the ratings as historical editorial judgments for these exact tags, not a benchmark score or
|
|
37
|
+
a measured probability of success. They predate the auditable [reliability corpus](RELIABILITY.md).
|
|
30
38
|
|
|
31
39
|
| Model | Download | Forms | Result | Speed (warm) | Rating | Use it for |
|
|
32
40
|
|---|---:|---|---|---|---:|---|
|
|
33
|
-
| `gpt-oss:20b` | 13.8 GB | text, tools, thinking, JSON | 7/7: exact output, arithmetic, bat-and-ball, code reading, JSON extraction, tool call, 9/9 ticket routing | 1.4 s per routed ticket; 12 s first call with load | 9/10 |
|
|
41
|
+
| `gpt-oss:20b` | 13.8 GB | text, tools, thinking, JSON | 7/7: exact output, arithmetic, bat-and-ball, code reading, JSON extraction, tool call, 9/9 ticket routing | 1.4 s per routed ticket; 12 s first call with load | 9/10 | Candidate for the measured text tasks; broader tool reliability unmeasured in that round |
|
|
34
42
|
| `nomic-embed-text:v1.5` | 274 MB | embedding | Retrieval 4/4 top-1; ticket routing 9/9 from two examples per team | 51 ms per item, batched | 9/10 | Search, deduplication, cheap classification |
|
|
35
43
|
| `strands-decider:2b-nvfp4` | 1.3 GB | decision | Ticket routing 9/9, return-policy yes/no 3/3, damage rubric 2/3 | 0.17 s per question | 8/10 | Fast routing and policy checks with probabilities; rubric scores run low at the top level |
|
|
36
|
-
| `glm-ocr:latest` | 2.2 GB | vision (OCR) | 4/4 phrases read from a dense report strip; 0/7 on text tasks | 11 s per strip at a 400-token cap | 8/10 OCR, 1/10 text |
|
|
44
|
+
| `glm-ocr:latest` | 2.2 GB | vision (OCR) | 4/4 phrases read from a dense report strip; 0/7 on text tasks | 11 s per strip at a 400-token cap | 8/10 OCR, 1/10 text | OCR candidate for screenshots; scans were not measured |
|
|
37
45
|
|
|
38
46
|
### What they did for a coding agent
|
|
39
47
|
|
|
@@ -1,6 +1,9 @@
|
|
|
1
1
|
# Inspecting model precision, placement and activations
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
External API review: 1 November 2026. That session's locally installed Ollama CLI reported 0.40.13;
|
|
4
|
+
its server was unreachable, so no live model or activation was inspected. The commands below are
|
|
5
|
+
instructions, not recorded observations. The FreeLlama integration boundary was updated on
|
|
6
|
+
14 November 2026; the historical API review is not a new verification of upstream versions.
|
|
4
7
|
|
|
5
8
|
## What “which bit/neuron was enabled” can mean
|
|
6
9
|
|
|
@@ -109,7 +112,11 @@ This example was not run. It assumes a compatible research model already loaded
|
|
|
109
112
|
|
|
110
113
|
## FreeLlama integration boundary
|
|
111
114
|
|
|
112
|
-
|
|
115
|
+
Ordinary discovery and observed placement use stock Ollama. The optional
|
|
116
|
+
[managed llama.cpp adapter](LLAMACPP.md) provides bounded text inference, not activation traces
|
|
117
|
+
or verified physical placement. Neither engine path exposes hidden activations through FreeLlama.
|
|
118
|
+
Static metadata and residency are separate from activation tracing; label traces unsupported
|
|
119
|
+
unless a specific backend adapter actually provides them.
|
|
113
120
|
|
|
114
121
|
If deeper tracing is added, use a separate explicitly enabled debug runner or an instrumented Ollama backend, with bounded capture and paged artifacts. Rust should manage jobs, limits, cancellation and trace metadata. It should not infer neuron activity from GPU utilization, memory use, token probabilities or generated reasoning text.
|
|
115
122
|
|
package/docs/MODEL_SELECTION.md
CHANGED
|
@@ -4,13 +4,15 @@ To offload a task, select an installed model with the required capabilities and
|
|
|
4
4
|
then check its memory fit under the intended concurrency. FreeLlama applies model eligibility
|
|
5
5
|
and admission; the calling agent still verifies the output.
|
|
6
6
|
|
|
7
|
-
The
|
|
7
|
+
The dated tables in this guide describe single machines; they do not qualify live routing on
|
|
8
|
+
another host. Current job selection uses [machine-local evidence](#turn-measurements-into-routing-evidence)
|
|
9
|
+
first, then the portable catalog fallback. The historical sources are:
|
|
8
10
|
[Recommended starting points](#recommended-starting-points-by-form) from an Apple M2 Pro with 32 GB,
|
|
9
11
|
the sections after it from an Apple M4 Pro with 48 GB unified memory. Re-run
|
|
10
12
|
`npx @octocodeai/freellama doctor`, `models`, `bench-all`, and your quality suite on the target hardware.
|
|
11
13
|
`doctor.machine.memory_bytes` is host RAM; a discrete GPU's usable VRAM must be observed separately.
|
|
12
14
|
|
|
13
|
-
For
|
|
15
|
+
For a dated per-job comparison and candidates from one machine, see the [local model catalog](LOCAL_MODELS.md).
|
|
14
16
|
|
|
15
17
|
For supported features and sourced publisher use-case guidance, inspect
|
|
16
18
|
`models {view:"installed", includeLibrary:true}` through MCP. [Model metadata](#model-metadata) explains digest matching, variant capabilities,
|
|
@@ -19,7 +21,7 @@ custom-model fallbacks, and how to read family claims without treating them as q
|
|
|
19
21
|
```mermaid
|
|
20
22
|
flowchart TD
|
|
21
23
|
T{"What must the task do?"}
|
|
22
|
-
T -->|"Generate text, code, or inspect images"| L["
|
|
24
|
+
T -->|"Generate text, code, or inspect images"| L["Inspect installed models with the required capabilities"]
|
|
23
25
|
T -->|"Create retrieval vectors"| E["Use a small embedding model"]
|
|
24
26
|
T -->|"Classify, route, or answer yes/no"| D["Use a small decision model"]
|
|
25
27
|
T -->|"Transcribe or speak"| A["Use an audio or speech model"]
|
|
@@ -46,14 +48,14 @@ calls shown are the current ones. Later and larger measurements, audio and memor
|
|
|
46
48
|
| Text, tools, JSON, reasoning | `gpt-oss:20b` (13.8 GB) | 7/7: exact output, arithmetic, bat-and-ball, code reading, JSON extraction, tool call, 9/9 ticket routing | 1.4 s per routed ticket | `run_task {model:"gpt-oss:20b", prompt, think:"low"}`; add `tools` or `format:"json"` |
|
|
47
49
|
| Embeddings | `nomic-embed-text:v1.5` (274 MB) | Retrieval 4/4 top-1; ticket routing 9/9 from two examples per team | 51 ms per item, batched | `run_task {task:"embedding", files:["src/**/*.rs"] or input:[...], nearest:{query:"..."}}`: ranked labels, not vectors |
|
|
48
50
|
| Decisions (classify, route, score) | `strands-decider:2b-nvfp4` (1.3 GB) | Ticket routing 9/9, return-policy yes/no 3/3, damage rubric 2/3 | 0.17 s per question | `run_task {task:"decision", model, state or files:[path], questions}`; one line per answer |
|
|
49
|
-
| OCR | `
|
|
51
|
+
| OCR | `hf.co/openbmb/MiniCPM-OCR-1.0-gguf:Q4_K_M` (1.4 GB) | 30/30 rendered text images in all 3 rounds | 257 ms median | `run_task {workflow:"read-text", files:[path]}` (or `job:"ocr"`) |
|
|
50
52
|
|
|
51
53
|
`gpt-oss:20b` reasons before answering, and its reasoning counts as output. FreeLlama sends no
|
|
52
54
|
output cap of its own and sizes the context from what the model has needed before, so leave room
|
|
53
55
|
for the reasoning if you set `num_predict` yourself. It needed about 17 GB available, so FreeLlama held
|
|
54
|
-
it when other work left less.
|
|
55
|
-
|
|
56
|
-
explicitly if you also cap the output. The `strands-decider` tags need Apple silicon, and decision
|
|
56
|
+
it when other work left less. OCR models read text from images only; asked a chat question, one keeps generating to its output
|
|
57
|
+
limit. Use them through the `ocr` job's trained prompts. `stopOnRepetition` stops one that loops and is
|
|
58
|
+
on by default without `num_predict`; set it explicitly if you also cap the output. The `strands-decider` tags need Apple silicon, and decision
|
|
57
59
|
models answer only through Ollama's decision API, which `run_task {task:"decision"}` reaches with
|
|
58
60
|
FreeLlama's routing and memory checks. A busy CPU does not refuse them; low memory does.
|
|
59
61
|
|
|
@@ -124,7 +126,7 @@ These examples do not establish that a tag is installed or suitable on your host
|
|
|
124
126
|
|
|
125
127
|
Dedicated OCR models answer best to the prompts their model card documents; name the image in
|
|
126
128
|
`run_task {files}` rather than pasting base64 `images`. A model that repeats its answer until its
|
|
127
|
-
output limit stops early with `stopOnRepetition`, on by default without `num_predict`. See [
|
|
129
|
+
output limit stops early with `stopOnRepetition`, on by default without `num_predict`. See [Loop control](FEATURES.md#loop-control)
|
|
128
130
|
for the early stop and the `output_check` receipt.
|
|
129
131
|
|
|
130
132
|
`muse-glimmer:30b-mlx` was a credible alternative and answered 29 of 30 questions correctly
|
|
@@ -166,6 +168,33 @@ this machine and workload, not a universal model-placement rule. Follow
|
|
|
166
168
|
|
|
167
169
|
## Turn measurements into routing evidence
|
|
168
170
|
|
|
171
|
+
Run `freellama bench-all --include EXACT_INSTALLED_TAG` on the serving machine, repeating
|
|
172
|
+
`--include` for other installed tags. The default output is `benchmark-report.json` in the
|
|
173
|
+
FreeLlama home (`FREELLAMA_HOME`, otherwise `~/.octocode/freellama`), which `serve` discovers on
|
|
174
|
+
its next start. `--output` chooses a different report path. No models are downloaded. Existing
|
|
175
|
+
resident models are left loaded; only models this run successfully warmed are eligible for cleanup.
|
|
176
|
+
|
|
177
|
+
Schema 2 reports record an observation timestamp, server version, artifact digests, OS, CPU,
|
|
178
|
+
RAM, available GPU identity and a domain-separated hash of the OS machine identifier. Raw machine
|
|
179
|
+
identifiers and hostnames are not included. Routing requires the same host/hardware signature,
|
|
180
|
+
exact endpoint (apart from a trailing slash), and current model digest. Remote endpoints, unknown
|
|
181
|
+
machine identity, reports from another host, and older reports remain readable but do not qualify
|
|
182
|
+
local throughput. Regenerate them on this machine. Primary-endpoint scores never qualify a separate
|
|
183
|
+
CPU-assigned runner. GPU details absent from the OS remain unknown; server settings and upgrades can
|
|
184
|
+
change performance without changing this signature, so rerun after those changes.
|
|
185
|
+
|
|
186
|
+
Job and workflow selection first asks the Rust router for a locally benchmarked model. Ordinary
|
|
187
|
+
jobs request the fastest route; capable workflows require a task quality policy as well. OCR also
|
|
188
|
+
requires quality evidence, and image search requires vision-capable embeddings. Without matching
|
|
189
|
+
evidence, selection falls back to installed catalog picks and their live memory preview. If no
|
|
190
|
+
tested catalog pick is installed, a capability-qualified installed model may run with an untested
|
|
191
|
+
warning. A conservative preview miss can still reach the authoritative runtime admission gate,
|
|
192
|
+
which admits, waits or refuses; selection never reserves memory. An explicit caller `model` wins.
|
|
193
|
+
The result states when local throughput guided the choice; a throughput screen alone does not
|
|
194
|
+
establish job accuracy. `models {view:"catalog"}` shows portable starting points, not the final
|
|
195
|
+
calibrated decision. This calibrated-first path applies to `run_task` jobs/workflows and virtual
|
|
196
|
+
gateway models; `delegate_research` has its own [catalog-and-routing sequence](cookbooks/research-agent.md).
|
|
197
|
+
|
|
169
198
|
`bench-all` measures local performance. A quality benchmark measures correctness. FreeLlama needs
|
|
170
199
|
both the generated task policy and local benchmark data before grading a route medium confidence.
|
|
171
200
|
See the [CLI reference](CLI.md#earn-medium-routing-confidence) for the commands.
|
|
@@ -211,7 +240,7 @@ feature with `capability`, `use`, `reason`, and `basis:"supported_feature"`;
|
|
|
211
240
|
| Feature | Supported workflow | What to evaluate separately |
|
|
212
241
|
|---|---|---|
|
|
213
242
|
| `completion` | Text generation | Coding, summarization, reasoning, and instruction-following accuracy |
|
|
214
|
-
| `tools` | Tool calls | Argument correctness, tool selection, and agent-loop reliability |
|
|
243
|
+
| `tools` | Tool calls | Argument correctness, tool selection, and agent-loop reliability; see the [bounded public smoke evidence](RELIABILITY.md#public-tool-calling-smoke-suite) |
|
|
215
244
|
| `vision` | Image input | OCR and visual understanding accuracy |
|
|
216
245
|
| `audio` | Audio workflows advertised by the model | Supported audio task and accuracy |
|
|
217
246
|
| `embedding` | Retrieval and similarity vectors | Retrieval quality on your documents |
|
package/docs/MONITORING.md
CHANGED
|
@@ -16,13 +16,15 @@ token and keeps it only for the browser tab.
|
|
|
16
16
|
|
|
17
17
|
| Endpoint | CLI | MCP | What it returns |
|
|
18
18
|
|---|---|---|---|
|
|
19
|
+
| `GET /health` | | `doctor` (`platform_health`) | Liveness, admission capacity, and configured backends; answers as soon as serve listens |
|
|
20
|
+
| `GET /ready` | `freellama ready` | `doctor` (`readiness`) | 200 once the primary Ollama (and CPU backend, when configured) answers and its catalog reads; otherwise 503 with `waiting_for` |
|
|
19
21
|
| `GET /status` | `freellama status` | `doctor {view:"status"}` | Live view of every backend, the raw proxy, loaded models, host, Ollama settings, and today's usage |
|
|
20
22
|
| `GET /usage?days=N` | `freellama usage --days N` | `doctor {view:"usage", days:N}` | Totals per day and per model (default 7 days) |
|
|
21
23
|
| `GET /metrics` | | | Prometheus text exposition |
|
|
22
24
|
| `GET /config` | `freellama config` | | Effective runtime settings and the source of each |
|
|
23
25
|
| `POST /config/reload` | `freellama config --reload` | | Re-read the runtime file now; `422` keeps the last good values |
|
|
24
26
|
| `GET /jobs` | `freellama jobs` | `task_jobs {action:"list"}` | Deferred job metadata without prompts or retained results |
|
|
25
|
-
| `GET /jobs/:id` | `freellama jobs --id <uuid>` | `task_jobs {action:"get", jobId}` | One job receipt and its retained result or error |
|
|
27
|
+
| `GET /jobs/:id` | `freellama jobs --id <uuid>` | `task_jobs {action:"get", jobId}` | One job receipt and its retained result or error. `?wait_ms=N` (at most 5000) holds the read until the job changes; the reply then carries `long_poll: true` |
|
|
26
28
|
| `POST /jobs/:id/cancel` | `freellama jobs --id <uuid> --cancel` | `task_jobs {action:"cancel", jobId}` | Cancellation receipt after local permits are released |
|
|
27
29
|
| `DELETE /jobs/:id` | `freellama jobs --id <uuid> --remove` | `task_jobs {action:"remove", jobId}` | Stops active work, releases local permits, and removes the retained record |
|
|
28
30
|
|
|
@@ -49,9 +51,20 @@ token and keeps it only for the browser tab.
|
|
|
49
51
|
A remote endpoint is never probed and is reported as unknown.
|
|
50
52
|
- **`usage_today`**: tasks, errors, tokens, and busy time since midnight UTC.
|
|
51
53
|
- **`task_jobs`**: deferred task IDs, selected models, configured backends, priorities, total
|
|
52
|
-
deadlines, states, and waiting reasons.
|
|
54
|
+
deadlines, states, and waiting reasons. MCP `doctor {view:"status"}` keeps only the active jobs
|
|
55
|
+
plus counts by state; `task_jobs {action:"list"}` lists them all. States cover discovery, admission, resources, runner
|
|
53
56
|
transitions, loading, execution, and completion. Metadata excludes the original payload.
|
|
54
57
|
|
|
58
|
+
On Windows, host memory comes from a bounded, unprivileged PowerShell CIM query. The
|
|
59
|
+
`windows_cim` observation converts `Win32_OperatingSystem.TotalVisibleMemorySize` and
|
|
60
|
+
`FreePhysicalMemory` from KiB to bytes; available memory is the latter, with kind
|
|
61
|
+
`windows_free_physical_memory`. Missing, malformed, overflowing, or inconsistent readings remain
|
|
62
|
+
unknown. See [Microsoft's field definitions](https://learn.microsoft.com/en-us/windows/win32/cimwin32prov/win32-operatingsystem).
|
|
63
|
+
The default `require-memory` policy holds admission when this observation fails, as on Linux and
|
|
64
|
+
macOS. CPU load, OS pressure, thermal, swap and GPU measurements remain unavailable on Windows;
|
|
65
|
+
`require-all` therefore holds admission. An operator can explicitly choose `best-effort` to admit
|
|
66
|
+
with unknown memory telemetry; observed low memory still follows the configured low-memory policy.
|
|
67
|
+
|
|
55
68
|
A task receipt explains its own wait. `admission.mode` is `resident_shared` (the runner was
|
|
56
69
|
reused without the backend load lock) or `nonresident_transition_exclusive` (this task loaded the
|
|
57
70
|
runner under it). `admission.reason` says why a present runner could not be shared when its identity
|
|
@@ -66,7 +79,9 @@ Use `run_task {defer:true}` in MCP or `task --defer` in the CLI to get a job han
|
|
|
66
79
|
status request omits results; fetching one ID returns its retained result or structured failure.
|
|
67
80
|
Terminal states are `completed`, `failed`, `cancelled`, and `expired`. Cancellation is per task,
|
|
68
81
|
waits for local permits to be released, and does not unload a shared runner. Process-local job
|
|
69
|
-
retention limits are documented in [CLI controls](CLI.md#execute-tasks).
|
|
82
|
+
retention limits are documented in [CLI controls](CLI.md#execute-tasks). The optional durable-job
|
|
83
|
+
mode retains receipts/results in the file-backed store without replaying inference; its recovery
|
|
84
|
+
and idempotency rules are in [durable deferred jobs](DEFERRED_JOBS.md).
|
|
70
85
|
|
|
71
86
|
Removal uses the same exact job ID. It cancels active work before discarding the record, returns
|
|
72
87
|
`{id, removed:true, status, scope:"process_memory"}`, and omits the saved result. The ID then returns
|
|
@@ -87,6 +102,13 @@ including after an Ollama restart. Each config receipt includes `observed_at` an
|
|
|
87
102
|
invalidates the use of measurements taken under different parallelism or KV cache settings.
|
|
88
103
|
FreeLlama admission limits remain governed by its runtime configuration.
|
|
89
104
|
|
|
105
|
+
These Ollama residency and process-setting observations do not apply to the optional managed
|
|
106
|
+
llama.cpp adapter. Its receipt identifies `execution.engine:"llamacpp"`, an operator-configured
|
|
107
|
+
memory forecast and processor assignment, with physical placement unknown. Its bounded text
|
|
108
|
+
tasks share admission pools and the host-memory governor; their results do not train Ollama
|
|
109
|
+
placement, residency or preload facts. See the [engine contract](LLAMACPP.md) for supported tasks
|
|
110
|
+
and the single live protocol smoke's limits.
|
|
111
|
+
|
|
90
112
|
`host.gpu_activity` is nullable. When available, it identifies its `source`,
|
|
91
113
|
`scope: "observed_devices_all_processes"`, `window: "driver_defined"`, and individual `devices`.
|
|
92
114
|
Each device has an identity, nullable `busy_percent`, and nullable `memory_busy_percent`. Apple
|
|
@@ -96,14 +118,17 @@ Use `host.sample_age_ms` to check freshness.
|
|
|
96
118
|
|
|
97
119
|
NVIDIA activity comes from the same bounded `nvidia-smi` query as memory. Apple Silicon activity
|
|
98
120
|
comes from the accelerator's `PerformanceStatistics` in a bounded IORegistry read. Those Apple
|
|
99
|
-
properties are driver-specific and may disappear or change
|
|
100
|
-
|
|
121
|
+
properties are driver-specific and may disappear or change. A sample that may have reached the
|
|
122
|
+
64 KiB output cap or omits a recognized device's busy counter is discarded rather than treated as
|
|
123
|
+
complete. Malformed NVIDIA device rows likewise discard the activity sample. AMD, Windows, unsupported drivers, and unavailable reads report unknown activity. The counters include other processes, use a driver-defined observation
|
|
101
124
|
window, and do not attribute activity to a FreeLlama task or establish bandwidth or energy
|
|
102
|
-
efficiency. They are
|
|
125
|
+
efficiency. They are diagnostic by default. The opt-in GPU headroom guard below also uses valid
|
|
126
|
+
busy counters to hold new GPU work.
|
|
103
127
|
|
|
104
128
|
Each backend's admission `queue_depth` includes both `slot_waiters` and `resource_waiters`.
|
|
105
|
-
|
|
106
|
-
|
|
129
|
+
An Ollama resource waiter returns its execution slot after at most two seconds; llama.cpp yields
|
|
130
|
+
after its initial bounded probe. Both remain in the bounded queue until capacity recovers, their
|
|
131
|
+
deadline expires, or they are cancelled.
|
|
107
132
|
|
|
108
133
|
Model affinity is bounded: `affinity_max_skips` (4) and `affinity_max_wait_ms` (2000) in the same
|
|
109
134
|
receipt are how often, and how long, an older waiter can be passed over before its class is served
|
|
@@ -116,6 +141,20 @@ process-wide memory for request bodies being read or held by running requests,
|
|
|
116
141
|
queue wait and is then refused with 503 `request_body_budget_exhausted`; raise it, or lower
|
|
117
142
|
`FREELLAMA_MAX_REQUEST_BYTES`, when large uploads are normal.
|
|
118
143
|
|
|
144
|
+
Managed response buffering also uses `FREELLAMA_MAX_REQUEST_BYTES` (64 MiB by default) as a
|
|
145
|
+
per-response byte ceiling. Ollama JSON, embedding and decision responses, error bodies, and total
|
|
146
|
+
NDJSON stream bytes share this limit. Oversized Ollama output returns `502` with
|
|
147
|
+
`code:"upstream_response_too_large"`, `retry_safe:false` and `execution_outcome:"unknown"`;
|
|
148
|
+
do not replay it automatically. This ceiling is separate from the shared request-body budget
|
|
149
|
+
and does not represent total process heap usage. See [stream bounds](ARCHITECTURE.md#request-shapes)
|
|
150
|
+
for backpressure and cancellation behavior.
|
|
151
|
+
|
|
152
|
+
The management catalog and compatibility proxy share a separate 4 MiB cap for internal model lists,
|
|
153
|
+
`/api/show`, residency observations and server versions. Oversized or failed observations remain
|
|
154
|
+
unknown; they cannot establish a model's residency or allocation forecast. An oversized external
|
|
155
|
+
engine model list appears under `unreachable` in the merged list. Direct raw metadata requests
|
|
156
|
+
still stream their upstream responses unchanged.
|
|
157
|
+
|
|
119
158
|
## Record usage
|
|
120
159
|
|
|
121
160
|
Every managed task, and every raw Ollama or OpenAI-compatible generation, updates in-memory usage
|
|
@@ -167,7 +206,7 @@ FreeLlama waits for safe capacity within a deadline and bounds the retained back
|
|
|
167
206
|
| Managed queue full | `429` | `admission_queue_full` |
|
|
168
207
|
| Raw proxy over its cap after `raw_queue_wait_seconds` | `429` | |
|
|
169
208
|
| Managed wait exceeded `max_queue_wait_seconds` (or the task's `max_wait_seconds`) | `503` | `admission_timeout` |
|
|
170
|
-
| OS pressure, swapping, CPU, thermal, or required telemetry still holds when the waiting budget expires
|
|
209
|
+
| A new load still does not fit available memory with its reserve, or OS pressure, swapping, CPU, thermal, or required telemetry still holds, when the waiting budget expires. Low available RAM refuses by default on every OS; `--low-memory advisory` (`FREELLAMA_LOW_MEMORY=advisory`) makes it a warning. Low RAM and swapping never hold an already-resident runner, and CPU load and thermal never hold one on the GPU | `503` | `resource_admission_unavailable` |
|
|
171
210
|
| Backend circuit open | `503` | `upstream_circuit_open` |
|
|
172
211
|
|
|
173
212
|
These capacity refusals carry a `Retry-After` header and `retry_after_seconds` in the body. For a queue it
|
|
@@ -176,6 +215,63 @@ task's cost), and the backend's recent average service time, which excludes queu
|
|
|
176
215
|
seconds). A task can ask for a shorter wait with `max_wait_seconds` (`maxWaitSeconds`
|
|
177
216
|
in MCP); the server caps it at the configured maximum.
|
|
178
217
|
|
|
218
|
+
## Leave capacity for other applications
|
|
219
|
+
|
|
220
|
+
Resource thresholds belong to the operator, not to a model name or a fixed machine size. Start
|
|
221
|
+
`serve` with CPU and, optionally, GPU headroom targets:
|
|
222
|
+
|
|
223
|
+
```bash
|
|
224
|
+
freellama serve \
|
|
225
|
+
--resource-hold-load-per-cpu 0.75 \
|
|
226
|
+
--resource-resume-load-per-cpu 0.5 \
|
|
227
|
+
--resource-hold-gpu-busy-percent 80 \
|
|
228
|
+
--resource-resume-gpu-busy-percent 60
|
|
229
|
+
```
|
|
230
|
+
|
|
231
|
+
These are **admission targets, not utilization quotas**. They hold new work until observations
|
|
232
|
+
recover; they do not pause, kill, or throttle work already executing. One admitted inference can
|
|
233
|
+
still saturate a device. Use OS/container CPU quotas and upstream/device isolation when a hard
|
|
234
|
+
resource partition is required. Direct calls to Ollama bypass FreeLlama's guard.
|
|
235
|
+
|
|
236
|
+
| Setting | Default | Meaning |
|
|
237
|
+
|---|---|---|
|
|
238
|
+
| `--resource-hold-load-per-cpu` | `1.5` | Hold CPU-bound work when one-minute load / logical CPUs reaches this value |
|
|
239
|
+
| `--resource-resume-load-per-cpu` | `1.0` | Recover the CPU hold at or below this value |
|
|
240
|
+
| `--resource-hold-gpu-busy-percent` | Disabled | Hold GPU work when any observed device reaches this busy percentage |
|
|
241
|
+
| `--resource-resume-gpu-busy-percent` | Disabled | Recover only when all observed devices are at or below this percentage |
|
|
242
|
+
|
|
243
|
+
The four flags also accept environment variables named `FREELLAMA_RESOURCE_HOLD_LOAD_PER_CPU`,
|
|
244
|
+
`FREELLAMA_RESOURCE_RESUME_LOAD_PER_CPU`, `FREELLAMA_RESOURCE_HOLD_GPU_BUSY_PERCENT`, and
|
|
245
|
+
`FREELLAMA_RESOURCE_RESUME_GPU_BUSY_PERCENT`. They are startup settings, not runtime-TOML keys;
|
|
246
|
+
changing them requires restarting your own FreeLlama service. Inspect the effective policy under
|
|
247
|
+
`host.policy` in raw `status` (or the full saved `doctor` response).
|
|
248
|
+
|
|
249
|
+
CPU load is **not CPU utilization**: `0.75` does not guarantee 25% idle CPU. It scales with logical
|
|
250
|
+
CPU count and includes the OS's runnable/waiting load. Both CPU thresholds must be finite and
|
|
251
|
+
positive, with resume less than hold; no fixed upper ceiling is imposed. Missing CPU telemetry
|
|
252
|
+
follows `--resource-telemetry-policy`; use `require-all` if unavailable CPU-load observations must
|
|
253
|
+
block work. CPU load holds CPU-assigned work and work on hosts without an observed accelerator;
|
|
254
|
+
it does not hold an observed GPU runner merely because a compiler is busy. Raw Ollama requests
|
|
255
|
+
with explicit integer `options.num_gpu: 0` use CPU admission without rewriting the body; this is
|
|
256
|
+
request intent, not proof of physical placement. Unknown raw/OpenAI-compatible placement stays
|
|
257
|
+
conservatively GPU-gated when the optional GPU guard is enabled.
|
|
258
|
+
|
|
259
|
+
Both GPU settings must be supplied together and satisfy `0 <= resume < hold <= 100`. GPU activity
|
|
260
|
+
is optional by default so unsupported machines continue to work. When explicitly enabled, missing,
|
|
261
|
+
partial, or invalid GPU busy counters refuse GPU admission with `gpu_activity` in the assessment's
|
|
262
|
+
`missing_telemetry`, even with `best-effort`; CPU-assigned work remains eligible. Enable this guard
|
|
263
|
+
only on hosts exposing the counters described above. It conservatively considers the busiest of
|
|
264
|
+
all observed GPUs, not a per-model device assignment. CPU-only or remote Ollama deployments should
|
|
265
|
+
enforce resource controls on the machine actually executing work: remote upstreams bypass local
|
|
266
|
+
resource admission. Holds recover after two fresh healthy samples by default, avoiding rapid
|
|
267
|
+
stop/start at a single threshold.
|
|
268
|
+
|
|
269
|
+
For memory headroom, the existing `--resource-hold-available-percent` and
|
|
270
|
+
`--resource-resume-available-percent` settings default to 15 and 20. The per-load reserve is
|
|
271
|
+
size-aware rather than a promise to keep that entire share unused for every small model. Use
|
|
272
|
+
`model_memory_budget` in the runtime file to cap combined model residency on unified-memory/CPU
|
|
273
|
+
backends. GPU busy percentage is not a VRAM reserve.
|
|
274
|
+
|
|
179
275
|
## Circuit breaker
|
|
180
276
|
|
|
181
277
|
After `breaker_failures` consecutive upstream failures on a backend (connection errors, `500`,
|
|
@@ -187,9 +283,9 @@ model do not count. Set `breaker_failures = 0` to disable it.
|
|
|
187
283
|
## Adaptive concurrency
|
|
188
284
|
|
|
189
285
|
Managed task costs are configurable through the runtime file's `[task_costs]` table. Valid keys
|
|
190
|
-
are `completion`, `coding`, `code_repair`, `tools`, `browser`, `vision`, `embedding`, and
|
|
286
|
+
are `completion`, `coding`, `code_repair`, `tools`, `browser`, `vision`, `embedding`, `decision`, and
|
|
191
287
|
`long_context`. Each value is a positive integer through 4294967295. Omitted kinds retain their
|
|
192
|
-
defaults: vision four, embeddings one, and other tasks two. Embeddings multiply their base by
|
|
288
|
+
defaults: vision four, embeddings and decisions one, and other tasks two. Embeddings multiply their base by
|
|
193
289
|
`ceil(input_items/4)`; the acquired charge cannot exceed the pool's current limit.
|
|
194
290
|
|
|
195
291
|
For a qualified light OCR workload, `[task_costs]` with `vision = 2` permits two vision requests
|
|
@@ -245,7 +341,9 @@ Omitted managed `keep_alive` values use finite retention informed by measured re
|
|
|
245
341
|
starting from `base_seconds` (300, Ollama's own default) and shortened by `pressure_factor` under a
|
|
246
342
|
host hold. Explicit values take precedence. The background pressure sweep releases, under
|
|
247
343
|
FreeLlama's own low-memory estimate, only runners idle longer than `base_seconds ×
|
|
248
|
-
pressure_factor` (75 s by default); swapping or OS memory pressure
|
|
344
|
+
pressure_factor` (75 s by default); swapping or OS memory pressure shortens that to `min_seconds`
|
|
345
|
+
(15 s). A runner counts as used when a task ran on it here or when another client moved its Ollama
|
|
346
|
+
`expires_at` since the sweep's last check; the audit then lists it as `used_elsewhere`. For governed prewarming, profile compatibility, and retention
|
|
249
347
|
settings, see [Scope history and model warming](SCOPES_AND_WARMING.md).
|
|
250
348
|
|
|
251
349
|
When a model about to load needs room, FreeLlama unloads idle runners itself (`keep_alive: 0`)
|