Repository navigation
🚀 LeanCTX 3.12.0: meet the Cockpit
The new Cockpit, Savings view. Our own dogfooding numbers since Oct 17: every figure is measured from the signed savings ledger on this machine.
3.12.0 brings the LeanCTX Cockpit: one local place for everything LeanCTX does for your agents. What it kept out of the context, what it cost, what it protected and what it can prove. It is free for everyone, runs only on 127.0.0.1, needs no account, and installs itself.
lean-ctx update # then start any agent session; the Cockpit installs itself
lean-ctx cockpit # opens it in your browser✨ The Cockpit
- One place for savings, spend and proof.
lean-ctx cockpit(orlean-ctx dashboard) starts in the background, reuses a running instance, picks a free port and stops withlean-ctx cockpit stop. - Your familiar commands open it. On a terminal,
lean-ctx gain,gain --web,gain --live,watch,wrappedandcockpit --exportopen the matching view. Scripts, CI,--jsonand--terminalkeep their text output exactly as before. - Every page, free, no plan checks.
- Cockpit shows protection and open findings side by side.
- Savings, Spend and the Ledger of every call.
- Report.
- Numbers explained, with every formula and price source.
- Security, Context, Sources, Agents, Proof, Decisions.
- Memory, Packages, Inbox and Improvements.
- Honest numbers. Every figure carries a trust label: measured, estimated, evidenced or derived.
- Installs itself, signed and verified.
- A fresh install with install.sh, PowerShell, npm or Homebrew ships it.
- An update from 3.11 and AUR's
lean-ctx-binget it at the next agent session, without a command. - Every package is checked against the LeanCTX signing keys before it runs.
- Opt out with
LEAN_CTX_NO_COCKPIT=1.
- Light and dark, desktop to phone.
📚 Knowledge from your repository
lean-ctx import docsturnsAGENTS.md,CLAUDE.md,.cursorrules,.cursor/rulesanddocs/into project facts, each anchored to its file and section.lean-ctx import gitlearns decisions, fixes and dead ends from your commit history. It reads no diffs and no authors.- Every fact passes the same secret and personal-data screening as any other import.
lean-ctx knowledge export-agents-md --writewrites them back as a marked section ofAGENTS.md.
🔒 Security: eight advisories fixed
- GHSA-rxv5-4c3x-g4q6:
ctx_executecode in languages other than shell now needs your approval, in the same dialog asctx_shell. - GHSA-rrww-7924-w72f: project provider configs load only in trusted workspaces.
- GHSA-h693-v7jv-vmv9: the SSRF guard blocks NAT64, 6to4 and Teredo IPv6 forms.
- GHSA-53h5-q4m8-vg3x: gateway-held provider keys need the lean-ctx token.
- GHSA-pv78-9chr-hj3c: proof and knowledge export paths stay inside the project.
- GHSA-gvg8-285q-m62g: signed handoffs prove who signed, not only that nothing changed.
- GHSA-jhf9-3pv4-m469: "no web fetches" policy packs also close provider egress.
- GHSA-79fg-7cj5-4xmm: an untrusted project config cannot widen write paths.
Thank you to everyone who reported them responsibly.
🧭 Focus
3.12.0 keeps what selects, controls and proves context, and drops what measured no benefit.
- 36 rarely used MCP tools are removed. Calling one names its successor.
- The hosted services that needed an account close. Personal Cloud ended today: its routes answer
410 personal_cloud_ended, your local data is unaffected, and the stored data is deleted 30 days after release. Existing hosted team servers keep running until their teams move to LeanCTX Hive with 3.12.1. - The local Engine and the whole Cockpit stay free.
- LeanCTX Hive, shared knowledge for teams and your own machines, follows with 3.12.1.
- Upgrade guide: docs/guides/upgrade-3.12.md. Focus changes: docs/migration/focus-2026-10.md.
🪟 Also in this release
- Windows: checkpoint packages, imports and source re-checks work again, and so do file locks and atomic file replacement.
- Semantic search without ONNX Runtime: the new built-in
potion-codemodel runs in pure Rust. - Pi and Oh My Pi are recognised as AI clients.
- You choose which AI tools
setupconfigures, and updates stay inside that choice (--dry-runshows the plan). - Dependencies: zip 9.0.5 (critical advisory GHSA-m665-v7pm-7grj), rustls 0.23.46 and @hono/node-server 2.1.5.
Full changelog (every change, breaking changes, removed features)
Focus release. The local Engine and the whole Cockpit are free and local, with no
account and no plan checks; the hosted services that needed an account close. LeanCTX
Hive (shared knowledge for teams and your own machines) follows with 3.12.1. LeanCTX also keeps what
selects, controls and proves context and drops what measured no benefit. 3.12.0 includes
every change prepared for 3.11.5, which is not released separately. Upgrade notes:
docs/guides/upgrade-3.12.md (retired services) and
docs/migration/focus-2026-10.md (focus changes,
successor tools and restore lines).
Breaking changes at a glance: Personal Cloud, the ctxpkg.com registry and the hosted
per-customer team servers close on the 3.12.0 release day (writes stop, the services answer
410) and their stored data is deleted 30 days after release, without migration; the
engine's cloud client, the login, register, account, sync, cloud, team and
enterprise commands, remote pack install|update|publish and addon add ns/name are
removed; hosted Wrapped publication, the leaderboard, the README badge and the billing CLI
are gone; the capability registry is schema 3 (price classes hive and retired); the
built-in personal-data detectors are email, phone and payment cards. From the focus work:
36 MCP tools are removed (34 retired plus ctx_intent and ctx_task; a call names the
successor); the Autonomy Drivers, Workflow Evidence Ledger, Intent Route,
invocation-context-binding, invocation-evidence-manifest and tokenizer-translation-driver
contracts are withdrawn; ctx_work_graph action="execute" and lean-ctx pair are removed
(the host starts agents with action="start"); cognitive_mode and the read-path autonomy
drivers are retired; role budgets, SLOs and anomaly detection are gone; domain and
compliance packs moved to Pro/Enterprise; .lean-ctx.toml write and read-only keys apply
only in a trusted workspace; decision receipts are schema_version: 2 with keyed object
digests, so SDKs before 3.12.0 reject them (engine and SDK ship together); the engine's
built-in dashboard UI is replaced by the Cockpit. The SDK Agent Tools v1 contract is
unchanged. Telemetry is unchanged. lean-ctx-protocol renames hive::project to
hive::vault (VaultV1, VaultRefV1, vault_id); the published crates need Rust 1.87.
Added
-
ctx_execute code needs your approval (GHSA-rxv5-4c3x-g4q6). Code in any language other
than shell runs only after approval in the same dialog as ctx_shell — once, for this
session, always (global execute_allowed_languages) or deny, per language; a batch asks once
per language and runs nothing if one is denied. Without the dialog (client without
elicitation, shell_approval=off) the code is refused — list the language in
execute_allowed_languages to run it without asking. -
Knowledge from the repository itself.
lean-ctx import docs [<file|dir>…]turns
AGENTS.md,CLAUDE.md,.cursorrules,.cursor/rulesanddocs/into project facts:
each bullet or paragraph is one fact, categorised by its nearest heading (conventions,
procedures, decisions, architecture, gotchas, dead ends, experiences) and anchored to its file
and section.lean-ctx import git [--limit N]mines the local history: reverts become dead
ends, fixes experiences, and commits that decide, switch or replace something decisions, each
anchored to its commit; trailers and lines naming a person by email are dropped first, and no
diff or author is read. Every file and every fact passes the same admission as any other import
(path rules, project policy, secret and PII detection): a masked value stays masked, a withheld
one yields nothing and is counted. A re-import updates the fact at the same anchor instead of
adding a second one. Each fact under a heading carries a code anchor on its section, so an edit
there marks it to verify; a fact whose section (or file) is gone on re-import is marked to
verify (source_removed) and becomes current again when the section returns.
lean-ctx knowledge export-agents-md [--write]writes these categories as a marked section of
AGENTS.md(only public facts; the rest of the file is kept), and importing that section yields
the same facts again. -
The whole Cockpit is free and ships with official installs. Improvements, Spend
history, Ledger filters and export, Report, Delivery insights, Memory Care, Package
Studio, recipes and comparison always render, without an account, plan check, teaser or
trial banner. The Cockpit computes the analyses itself against two lease-free engine
routes (POST /api/dashboard-analysis/inputsand/apply). Every figure carries a
trust label (measured, estimated, evidenced, derived) and Numbers explained gives each
one's formula and price source; Decisions lists what the gateway decided on this device,
without content. Former#accountand#cloudlinks land on Settings, and Security
shows the active filter packs.install.sh(LEAN_CTX_NO_COCKPITskips it),install.ps1
(-NoCockpit), npm and Homebrew install the signed Cockpit bundle beside the Engine;
lean-ctx cockpit install --from <dir|file.tar.gz> [--allow-downgrade]installs one
offline. The Cockpit is a free binary under the LeanCTX Cockpit EULA; its source stays
private. Source builds show a page pointing to the official installs. -
GET /api/gateway/detectorsnames what content is screened for:
{"pii": {"sources": [...], "policy_filters": [...]}, "filter_packs": [...]}—
pii.sourcesin every source (the checksum-validated payment cards),
pii.policy_filterswhen a policy pack's[filters] piiis on (cards, email,
phone), and the labels of the installed filter-pack rules. The control
document carries the same object asdetectors. -
Knowledge validity classes (S05). A fact is a
convention(category convention or
decision, orvalidity:"convention") orcontent(bound to its sources). Checkouts linked
to the same team project withlean-ctx project linkshare conventions whatever their
branch; a code-bound fact is served there only while its files are identical, otherwise
it is withheld as stale. Recall shows the class,/api/knowledgeaddsvalidity_class. -
Launcher-bound Workspace authority (#2120). A launcher starts the MCP server with
LEAN_CTX_WORKSPACE_FILE=<file>; the file's primary root and up to 64 additional roots
(read-write or read-only;/, the home directory, its ancestors and agent config
directories are refused) are then the only roots that server's tools, MCP resources, search indexes and
repo roots reach (lean-ctx's own data directories included). Client roots,
extra_roots/allow_paths, the home jail scope andctx_multi_reporoots grant nothing
while bound; response and file caches are not served across revisions. Each tool call
takes one snapshot, so a root detached withlean-ctx workspace removeis gone on the
next call without a restart; concurrent servers with the same primary root keep their
own roots. The file is checked fail-closed (owner, mode 0600, no symlink, no
foreign-writable directory, outside its own roots and lean-ctx's directories; Unix hosts
only for now) and changed only by compare-and-swap on its revision (lean-ctx workspace create|add|remove|show|diagnose). Without the variable nothing changes. Guide:
docs/reference/13-security-and-governance.md§1.6. -
Choose and preview what a context package holds.
pack createtakes--layers,
--category,--keyand--fact <category/key>;--previewlists exactly what would be
packed (fact titles, status, sources, validity, counts, what is left out) and writes
nothing.ctx_pack action=createtakes the same aslayers,categories,keys,
factsandpreview. Knowledge facts carry astatus:verifiedwhen a provider (or a
derivation from sourced facts) backs them, elseassumption; it is recorded in the
package.--redistributable(redistributable: trueover MCP) grants recipients the
right to pass the package on. Without a selection,pack createbuilds the same layers as
before; at--level 2the context graph now follows the chosen layers too. -
lean-ctx project use <path>. When several workspace roots
were candidates,ctx_session statusand the Cockpit name the chosen project and how to
switch (lean-ctx project use <path>); the first root is still chosen by default. -
Provider credentials and checks.
lean-ctx provider check <source> --json --stdin
tests candidate credentials read from stdin;provider credentials set|list|removekeeps
them in the engine's store (values never printed);provider init --project-root <dir>.
PostgreSQL connection strings are passed topsqlthrough its environment, never argv. -
Idempotent retries.
ctx_agent action=postandctx_handoff action=createaccept a
request_id: a retry returns the first result, a changed request with the same id is
refused. A team knowledge write with--if-revisionwhose reply was lost is sent once
more and reported as already stored. -
Reproducible context packages. Package timestamps come from
SOURCE_DATE_EPOCHor the
newest source, so the same input builds the same bytes. -
Dashboard stages Connect → Select → Control → Deliver → Prove. The cockpit is organised along the path context takes. New views: Sources & Hosts (each connector's declared capabilities, each configured host's coverage), Policy & Decisions (gateway mode, organization and project policy layers, the reasons content was withheld or changed; rule patterns are never shown), Delivery & Egress (how far each delivery is known to have gone; an observed model egress kept apart from context handed to a host) and Audit & Coverage (audit chain, observations, coverage gaps). Earlier links such as
#context/livestill open the same view. -
Connector contract for GitLab, GitHub and Jira. Every connector declares what it supports (search, list, get, delta, per-item access and revision re-check, delete events); a stored item is reused for another reader only after a re-check with that reader's own credential. GitHub answers are no longer cached; an expired cache entry is never served.
-
One context decision vocabulary.
lean-ctx inspect --jsonand the dashboard show each receipt's lineage: the request route, the decision per object (allow, deny, redact, transform, unavailable) and how far the delivery is known to have gone. A receipt that records no per-source access check says so (source_rights: not_recorded) instead of implying permission. -
Pi and Oh My Pi are recognised as AI clients. Pi has no built-in MCP client and connects through extensions that announce themselves as
pi-lean-ctx,pi-mcp-adapterorpi-mcp-probe; Oh My Pi announces itself asomp-coding-agent. Both were counted as an unrecognised client (other) in the anonymous usage statistics and are now reported aspiandoh_my_pi. Only the existing client-family field gains two values; no client name is sent and nothing new is collected. Capabilities offered over MCP stay as before. -
Semantic search without ONNX Runtime. A new built-in embedding model,
potion-code(potion-code-16M, a static model2vec table, MIT), runs in pure Rust: nolibonnxruntime, no attention pass. When no model is configured, lean-ctx now uses MiniLM where ONNX Runtime is installed andpotion-codeeverywhere else — installations without ONNX Runtime previously had no semantic search at all. Measured on 8,086 documented functions of the lean-ctx source (docstring → code,core/embeddings/eval.rs): MiniLM reaches MRR 0.348 / recall@10 0.570 and indexed them in 557 s on CPU;potion-codereaches MRR 0.247 / recall@10 0.431 and indexed them in 0.07 s, answering a query in 9 µs instead of 26 ms. The model is pinned to an exact revision and the SHA-256 of both files, and its safetensors weights are bounds-checked before any read. Choose explicitly with[embedding] model = "potion-code"or"minilm". -
lean-ctx results drawn like Claude Code's own. The Claude Code plugin draws
ctx_patchevidence through Claude Code's diff renderer (gutters, colored+/-, syntax highlighting),ctx_readcode (lines,anchored,full,raw, several files) syntax-highlighted and numbered from the real line with anchor hashes hidden on screen, andctx_searchhits with a dimpath:line, the highlighted line and the enclosing symbol. Only the display changes: Claude receives every result unchanged, and output the plugin does not recognise is drawn as before. Turn it off with the plugin's Color lean-ctx output setting. Inspired by community member Kirill Naumenko's leanctx-colored. -
ctx_readreads the file that was clearly meant. When the requested path does not exist but exactly one file matches it unambiguously — the same name in another case, or the same relative path under one other directory (src/x.rsforrust/src/x.rs) —ctx_readreads that file and says so in a closing[lean-ctx: …]line, after the same path-jail check as any read. Typos and other extensions remain suggestions only, and byte-exact reads (raw) never substitute. "File not found" was the most frequentctx_readfailure in 3.11.4. -
Fewer shell blocks. The default shell allowlist admits the read-only byte inspectors
od,hexdump,stringsandcmp. A nestedbash -c/sh -cis still not run, but the message now says to pass the inner command directly — it already runs in a shell — instead of suggestinglean-ctx allow bash, which would admit every script. Blocked inline code (python3 -c, heredoc stdin,node -e,perl -0pi -e— together ~400 of ~500 measured shell blocks) now comes with the allowed path in one step: the exact script file to write (with the interpreter's extension) and the command to run it, or the Edit tool /ctx_patchfor in-place text changes. The restriction itself is unchanged. -
More argument spellings.
ctx_composeacceptsquery,question,promptorgoalfortask; actx_searchqueries[]entry acceptsregex/queryforpatternandglobforinclude. -
A long
lean-ctx callreports where it is and stops instead of hanging (#2063). Every 30 seconds it names the phase it is in on stderr (for exampledense: embedding engine load), and after 300 seconds it stops with exit code 124, liketimeout.LEAN_CTX_CALL_TIMEOUT_SECSsets the limit (0= none).LEAN_CTX_PHASE_TIMING=1prints the duration of every phase of semantic search andctx_compose, so a slow call can be attributed to the index, the embedding engine, ranking or graph enrichment. -
The Claude Code cockpit sidebar can be turned off (#2057).
/cockpit offcloses the sidebar and keeps it closed in new sessions;/cockpit onbrings it back, and/cockpitstill opens it once. The choice is stored as the plugin's Open the LeanCTX cockpit sidebar option, also in/config. With the sidebar off, the five-minute receipt re-verification that only the sidebar shows stops too; the pulse line, spinner and turn cards stay. -
The cockpit's pulse line and turn cards can be turned off too (#2057).
/cockpit pulse offhides the line above the prompt that follows lean-ctx calls while Claude works;/cockpit cards offhides the card shown when a turn ends or a milestone is reached, the milestone notification, and the gateway summary added to Claude Code's "done in" line. Both hold for new sessions,onbrings them back, and both are options in/config(Show the LeanCTX pulse line, Show LeanCTX turn and milestone cards). The sidebar still lists every turn and milestone, and the spinner stays. -
Fewer "Prompt from the lean-ctx plugin" wakes, and a switch to turn them off. Background jobs that finished one after another while Claude was idle each started their own wake, a row in the transcript and a turn each. A job that finishes while an earlier wake still waits for its turn is now held like one that finishes mid-turn: if Claude reads it in that turn, no wake follows; otherwise it wakes once afterwards. A wake that never starts its turn holds nothing back for longer than a minute. The plugin option Wake Claude when a lean-ctx background job finishes (
wake_on_job_finish) turns watching off, and the live skill then tells Claude to check jobs itself. Claude Code keeps plugin prompts in the transcript; it offers no hidden variant. -
The proxy's context snapshot says how long it has measured (#703). The cumulative section of
proxy-introspect.jsongainsmeasurement_started_at_epoch_secondsandmeasurement_elapsed_seconds(monotonic, from the first request this proxy process saw), so the vision-encoding go/no-go can tell a normal usage day from a short sample. The file stays local and holds no prompt content; vision encoding stays off. -
ctx_handoff action=export ledger=<path>exports a stored ledger (e.g. a merged
one) as a signed transfer bundle; withlean-ctx team artifact publishandimport
this is the team path for merged ledgers — no extra store. -
ctx_handoff action=merge: one ledger from several agents. Parallel agents of one
project hand their ledgers tomerge(2–8); the result is a new ledger another agent
pulls. Every input is re-authorized first (a withheld input refuses the merge), the
result is a byte-for-byte subset of the inputs (duplicates collapse, conflicting fact
values are all kept and reported, nothing is ranked or rewritten), each part keeps the
binding it had, every input source is re-read for the result's lineage, and the same
set of ledgers always merges to the same bytes and file. The new optional ledger field
merged_fromlists the inputs' content digests. Replaces the never-wired
result_fusion/capsule_wiremodules. -
Engine:
lean-ctx engine context-presented-use— the holder of a presenter
capability asks whether text delivered under it is still usable (check), keeps a
recovery copy (retain) and gets a kept copy back (expand). Every answer re-checks
the capability and the current source rights; the capability enters through
--presenter-capability-fileonly. Contract:docs/contracts/engine-context-sources-v2.md. -
Enterprise suite:
POST /v1/engine/presented-use, behind the API key, its tenant
and its current rights to exactly the sources the text derives from. Presenter
operations have their own audit labels (materialize_v2,presented_use,
presenter_revoke); a revocation now leaves an audit record. -
SDK: use and revoke in Python, Go, Rust, JVM, .NET and TypeScript; the TypeScript
EnterpriseEngineClientgainscontextMaterializeSourcesV2. V1 methods and routes
are unchanged.
Changed
-
lean-ctx-protocol: vaults (breaking).
hive::projectishive::vault;ProjectV1,
ProjectResolveRequestV1,MetricsProjectV1andRepoRefV1areVaultV1,
VaultResolveRequestV1,MetricsVaultV1andVaultRefV1;project_idisvault_id,
repoisvaultand opt-inreposisvaultson the wire; schemas
leanctx.hive.vault/v1andvault-resolve-request/v1; bus channels
org:<org>/vault:<vault_id>/<name>.invisible()covers the soft hyphen, the Mongolian
vowel separator, the combining grapheme joiner, the Hangul fillers, the Khmer inherent
vowels, U+2060–206F, the line and paragraph separators, interlinear annotations and the
remaining format controls;listvalue items are text. The identity domain bytes, the
vault id value and the sealed AADs are unchanged. -
Rust 1.87.
lean-ctx-protocol,lean-ctx-oclaandlean-ctx-embeddeclare
rust-version = "1.87"(was 1.85), for ctutils 0.4.4 (see Security). -
You choose which AI tools lean-ctx configures, and updates stay inside that choice.
lean-ctx setupand the firstlean-ctx onboardon a terminal (includinginstall.sh)
ask which of the detected tools to connect and remember the answer assetup.agents.
--agents claude,cursor(ornone; install.sh:LEAN_CTX_AGENTS) sets it without a
prompt and rejects unknown names.lean-ctx updatenow refreshes only the chosen tools —
or, on installs without a recorded choice, only tools that are already connected — and
never configures a newly installed tool; it lists those it left untouched.
lean-ctx init --agent <name>adds a tool to a recorded choice. New--dry-runfor
setup,onboardandupdateshows which files and tools a run would touch and writes
nothing. Without a terminal and without a choice (npm install, CI),onboardconfigures
no new tool and points tolean-ctx setup;LEAN_CTX_AGENTS=alloronboard --yes
restores connecting every detected tool. -
The local audit trail is sealed into segments. After the first full verification on
3.12.0 the trail rotates at 64 MB or at day change into signed, immutable segments; the
existing trail becomes segment 0 and nothing is deleted. Readers no longer hold the trail
lock through a pass, so a large trail no longer withholds agent reads while the Cockpit is
open. Downgrading to 3.11.x after a rotation is not supported for audit verification (an
older engine reports the chain as invalid). -
The gateway evidence store is bounded. Receipts are stored packed, an existing packed
store from earlier development builds is read as is, and a background pass keeps the store
under its cap by removing the oldest unprotected evidence (the last 24 hours, the latest
receipts and open tasks are kept).lean-ctx doctorshows the store's size, cap and last
maintenance;lean-ctx inspect --maintainruns a pass now. -
Prompt-injection detection is precise (detector set 2.1.0). Patterns match instructions
rather than words in code or logs, and a flagged object is recorded once per process, so
security counts, receipts and Hive metrics no longer multiply one finding. -
Intelligence runtime packages need Engine 3.12.0. New runtime packages no longer declare
the retired hosted index; a 3.11.x Engine keeps its installed runtime but does not take new
packages. Engine 3.12.0 also accepts an already installed runtime from the 3.11 line. -
Capability registry schema 3. New price classes
hive(withhive_plan=
pro,teamorenterprise) andretired, and the deliveryhive_service; the
classespro_paid,cloud_paid,team_paidandenterprise_paidare refused in a
schema-3 record. Free and local:pro.dashboard.knowledge_workflows,
pro.runtime.adaptive_context,memory_curation,context_policy. Hive Pro:
pro.runtime.semantic_detectors,code_security,personal_protection. Hive Team:
team coordination, artifacts,private_registry,managed_connectors. Hive Enterprise:
enterprise.*,team.sso_oidc,team.audit_retention. Retired:pro.cloud_sync,
pro.hosted_index,team.revenue_share. Ids and aliases are unchanged. -
Local features never depend on a plan. Contract
docs/contracts/local-free-invariant-v2.md:
local decisions do not change underLEAN_CTX_LICENSE,LEAN_CTX_PLAN,
LEAN_CTX_ACCOUNTor a forged entitlement cache, every free capability is accountless,
and plan checks may only live incore/hive(scripts/check-local-free.py, wired into
preflight and CI). -
Built-in personal-data detectors: email, phone and payment cards. Swiss AHV, IBAN
and US SSN with their validators leave the Engine (built-in detector set 2.1.0) and are
delivered as Hive filter packs; IBANs no longer raise a text to Confidential. The
Cockpit's Security views name the built-in classes and the installed filter packs. -
Telemetry is unchanged. Its transport and send loop moved out of the removed cloud
code with the same endpoints, cadence, consent and opt-out; the version is still
recorded on the first and every hundredth call. -
The optional runtime is licensed through Hive or a commercial licence. Its own
activation, provisioning, renewal and sync services are gone; the runtime disclosure
names Hive or a commercial licence. -
Session continuity is per agent. The wake-up briefing, session search results and
every other session read or write, including consolidation, use only the agent's own
session or an explicit handoff, never the project's latest one. Project knowledge stays shared.
Resume your own session after a restart withctx_session{"action":"load","session_id":"<id>"}. -
There is only the Cockpit.
lean-ctx cockpit [--no-open] [--port N](alias
lean-ctx dashboard, port 3333) starts or opens the local server that hosts the
Cockpit, a signed runtime package. The server stays the single entry point: after its
token check it forwards the Cockpit's pages and/api/gateway/*to the Cockpit and
answers every other/api/*route itself. The engine's built-in web UI is removed;
without the Cockpit,/says how to install it.lean-ctx gain --webopens the
Savings view,gain --livethe Calls (Ledger) view of recorded calls (the terminal
live loop is gone; there is no separate Live view), andlean-ctx gain --terminal
is the terminal summary. Reads may name their project with
X-LeanCTX-Project(workspace pool only, per request; anything else is 403), and slow
reads (/api/roi,/api/value,/api/health, …) are served from labelled display
snapshots (X-LeanCTX-Observed-At,X-LeanCTX-Snapshot,X-LeanCTX-Refreshing). -
Every dashboard command opens the Cockpit.
lean-ctx cockpitis the command and
lean-ctx dashboardan equal alias. On a terminal it reuses the server already running
for this data dir or starts one in the background, waits until it answers (bounded),
lets it start the Cockpit, opens the browser at the view and returns the prompt
(Opened the Cockpit → #route; the token goes only to the browser and is never
printed).lean-ctx cockpit --foregroundkeeps the server in the terminal (the mode
without a terminal, e.g. Docker), andlean-ctx cockpit stopstops the background server
by its recorded PID. On a terminal,lean-ctx gainand its views (--graph,--daily,
--by-tool,--score,--tasks,--deep,--pipeline→#savings;--cost,
--agents→#spend;--heatmap→#context?detail=heatmap),gain --web
(#savings),gain --liveandwatch(#calls),wrappedandcockpit --export
(#report) open the Cockpit. Without a terminal, in CI, withLEAN_CTX_NO_COCKPIT, with
--terminalor a machine format (--json,--md,--raw,--export,
--format json|markdown,--svg,--share,--copy,--reset) the text output is
unchanged, so agent shells and scripts see what they saw before;gain --web|--live
there print the view instead of starting a server. Without an installed Cockpit the
text report is printed with one line:Cockpit not installed — lean-ctx cockpit install.cockpit --export --output=FILEkeeps writing the offline report, and
gain --wrapped,--svgand--sharekeep exporting. The proxy'sGET /dashboard
page nameslean-ctx cockpitand links the running Cockpit (/api/statsstays). -
The Cockpit starts reliably. The server records itself (PID, process identity,
port, version; no secret) indashboard.launch.jsonin the state dir. A start reuses
this data dir's healthy server, restarts its own background server when it hangs,
rejects the saved token or runs an older engine version, and moves past a port another
program or another LeanCTX data dir holds (also IPv6-only listeners onlocalhost) to
the next free one — an explicit--port/LEAN_CTX_PORTis never swapped but named
with the fix. The server ends cleanly onSIGTERMand removes its record. -
Reports point at the Cockpit. Setup, onboarding,
help, the cheat sheet name
lean-ctx cockpit(Savings · Spend · Proof). On a terminal, the human output of
spend,savings,roi,value,output-savings,token-report,cep,heatmap
anddoctorends with one dim stderr line naming the matching Cockpit view; never with
--json,--md,--raw,--exportor--format json|markdown, never when stdout is
redirected, in CI or withLEAN_CTX_NO_COCKPITset. The reports themselves are
unchanged. -
Decision receipts v2: keyed object digests. New receipts carry
schema_version: 2;
eachdecisions[].objectis an HMAC-SHA256 under the installation's receipt key
(<data>/gateway/receipt.key), named in the newobject_digestfield (algorithm and key
id), so a receipt no longer confirms a guessed plaintext. Version 1 receipts still parse
and verify. Without a usable receipt key no receipt is issued: governed and sovereign
mode refuse the delivery, developer mode sends without a receipt. All six SDKs parse v1
and v2 and offer key-holder verification (receipt_key_id,keyed_object_digest).
Contract:docs/contracts/context-gateway-v2.md. -
A live provider list is admitted item by item. Under
classification = "block"one
confidential issue no longer withholds the wholectx_provideranswer: that item is
left out (title included), an injection-like title stays fenced as data, the rest is
delivered, and knowledge is derived from the delivered items only. -
Stored context gets a full semantic check later. When the bounded check of stored
context (knowledge, archive, handoff, recovery) stays partial, the text is queued and
checked in full while the agent is idle; the next use applies the result (redact,
withhold ornot_inspected). Live reads keep their 2 s budget. A model set that does
not declare its languages and document types claims no coverage (not_inspected). -
doctorandstatusreport what is really active. Shadow mode reads "active" only
for hosts with installed hooks;gainanddoctorshare one proxy check (configured
and answering as lean-ctx);doctorprints no colour without a TTY, withNO_COLORor
TERM=dumb, and exits non-zero only for a failed scored check (a fresh install exits 0). -
install.shfails closed. A missingSHA256SUMSor a missing entry for the
download aborts the install. The script says it does not verify the cosign signature
(lean-ctx updatedoes) and what onboarding will change (LEAN_CTX_NO_ONBOARD=1skips it). -
Received packages are passed on only under their author's grant.
pack export
(signed or not),pack send,pack publishandctx_pack action=exportrefuse a package
this machine received (import, registry install, receive) unless its manifest carries
redistributable: trueunder the full manifest signature. Packages built here with
pack createexport as before; a package stored before 3.12.0 counts as received until it
is re-created. Facts merged from a package without that grant stay out ofpack create. -
Auto-loaded packages belong to their project. A package enabled for auto-load in one
project no longer loads in any other project (entries from earlier versions must be
re-enabled per project); package facts reach the model fenced as untrusted data and are
never written into agent rule files. -
Work Graph: the host starts agents, LeanCTX controls them. New
ctx_work_graph action="start"binds a host-launched child to its node: fenced claim, node and path
leases, verified hand-over of the signed context capsule, and the child's narrow
delivery profile as launch environment when the host is configured as delivery issuer.
A receipt,cancelor lease expiry stops the node and revokes the child's delivery
immediately.receiptandcancelalso accept the owner of the delegating parent node
(docs/architecture/work-graph-host-start.md). -
Context packages: the signature covers the whole manifest. Packages are additionally
signed over the full manifest (signature.manifest_value), so kind, visibility,
dependencies, scope, provenance or licence cannot be changed after signing. Older packages
verify as "identity only" and say so. The hosted registry andpack publishrecompute
integrity from the bytes instead of trusting the manifest. -
Cockpit: which project and which knowledge. The dashboard reports
the project it is bound to and where that binding came from (GET /api/scope); without a
binding it shows no project data instead of the most recently active project. Knowledge
shows its visibility and state. -
Semantic model sets declare what they cover. A model set can declare the languages and
document types (prose, code, data) it was qualified for; text outside that coverage is
reported as not inspected instead of covered, and a host that does not apply declarations is
refused by the worker. The built-in floor stays authoritative in every case. -
Leases are bound to their project. Path and symbol leases of
ctx_agentand the Work
Graph name the project, so the same relative path in two projects no longer conflicts, and
a Work Graph claim and an agent lease on the same file now exclude each other. Lease paths
must lie inside the project.if_revisionon mutatingctx_work_graphactions refuses a
write when the graph changed sinceobserve(write_revision). -
Context packages: the spec's map form for
dependenciesandoptional_dependenciesis
read; optional dependencies are attempted and their failures reported instead of skipped;
integrity and signature hex must be lowercase; the seven conformance vectors run in CI. -
lean-ctx migrate legacy-contextlists data from earlier releases that is no longer
served because it carries no project (oldctx_memoryfacts, global archived facts,
unbound archives, project-less handoff ledgers, quarantined shared knowledge) and adopts
chosen items into one project you name, through normal admission, with a journal
(--dry-runfirst). Archives and facts whose recorded session proves the project are
adopted automatically. -
The background cognition loop is off by default (
[autonomy] cognition_loop_enabled): it rewrote stored knowledge without a recorded decision. -
The
[cognitive: high echo ratio]suffix is removed. -
structure_first,journal_enabledandauto_capturedefault tofalse
everywhere. Their docs said opt-in and every user with aconfig.tomlalready got
false; only installs without a config file gottrue. Set them explicitly to keep
the old behaviour. -
OCaml, Haskell and Julia tree-sitter grammars are no longer in the default build
(−14.6 MB, −13 % binary)..ml/.mli/.hs/.jlsignatures fall back to the regex
extractors; build with--features grammars-long-tailto keep the parsers. -
The Engine identifies itself as the Context Gateway for AI Systems. README, agent instructions, CLI help, MCP server metadata and package descriptions use Select · Control · Learn · Prove, with local knowledge and observable-evidence limits stated. Security and support contacts use
hello@thinkery.ch. -
Usage statistics arrive within half an hour. While LeanCTX is in use, the anonymous daily totals are now re-sent every 30 minutes (at most 48 times per UTC day) instead of at doubling intervals that stretched to two hours after a handful of sends, which left a day's evening activity unreported until the next morning. Only the timing changes: the same cumulative totals are sent, and nothing new is collected.
lean-ctx telemetry showstates the limit. -
ctx_readwithengine_interface="v1"says how to recover. The engine interface reads one file per call. Its refusal ofpathsnow tells the agent to passpathonce per file or to leave outengine_interfacefor a batch read, and its refusal of other modes says to leave it out; one OpenCode installation had repeated the same refused call 802 times. -
Native tool calls are no longer refused by default. Codex, Cursor, Windsurf, OpenCode, Gemini and CodeBuddy defaulted to Replace mode, whose hooks refused native Bash, Grep and Glob calls. Each refusal cost the agent a whole extra request (in 30 days of Codex sessions: 249 refusals, median 67k prompt tokens re-read per refusal) — mostly for commands like
pwd,mkdir -p,wc -lorshasumwhose native output costs next to nothing — and users found it disruptive. Every hook-capable agent now defaults to Hybrid: lean-ctx steers agents toctx_*tools and rewrites known shell reads and searches, and other native calls go through. Deny hooks check the setting on every call, so hooks installed by earlier versions stand down as soon as the binary updates. Claude Code keeps native Grep and Glob out of its tool list in the default mode: Claude Code drops a tool named inpermissions.deny, so this costs no error and no retry (0 refusals in 380 measured sessions), and native Glob returned ~12× the tokens ofctx_globfor the same patterns.hook_mode = "hybrid"gives Claude both tools back; CodeBuddy, which shares that contract, does the same and gets native Bash back (it was hidden too). OpenCode no longer sets native read, grep, glob and bash toask, which prompted on every call and refused them in headless runs; the entries an earlier version wrote are removed on the next MCP server start, also after an update through a package manager. Replace stays available on request:lean-ctx config set hook_mode replaceorlean-ctx harden --hard(which now records the choice),lean-ctx harden --undoto go back.hook_modeis now part of the config schema (auto,hybrid,replace,mcp). -
.lean-ctx.tomlfollows one rule per key class. Project keys (compression,
read/search, memory, archive, conversation, response shaping, code health,
timeouts — about 60) win wherever the project file sets them, also back to the default
(before, a value equal to the default was ignored, a key mentioned only in a comment
could count as set, and an omittedsilent_preloadreset the global value).
User- and machine-level keys (theme, shell hooks, memory profile, proxy timeout) are no
longer taken from a repository. Security:write_allow_paths,read_only_roots
andread_redirect = "off"now apply only in a trusted workspace. A project file
without profiles is used as written when a global profile is selected (it used to be
skipped as a parse error). -
Handoff ledgers are stored only if they can be read back now — the whole source
lineage re-read under one budget, as a reader does. -
.lean-ctx.tomlkeys without effect are named. A project key the merge does not
apply (global-only, one-way, or equal to the default while the global differs) is
logged as "not applied" instead of being ignored silently. -
Settings audit: every setting now does what it says, or is gone.
- Fixed: an
[autonomy]section withoutcognition_loop_enabledswitched the
background knowledge loop back on; it now stays off unless set.[conversation]
bounds (preserve_last_n_turns,compression_threshold_tokens,
min_score_to_preserve,drop_score_below) were hard-coded and are now applied; the
stub for a dropped message no longer promises a recovery that never existed.
[cache] l2_ttl_secsis applied (it was fixed at one hour), and[cache]is the one
place for the delivery-cache bounds ([ocla.delivery.cache]moves there).
[memory.gotcha] max_gotchas_per_projectis applied, as are a gotcha's own
expires_atanddecay_rate_override. - Retired (never applied):
session_token_limit,allow_auto_reroot,
shadow.auto_record,shadow.baseline_model,agents.identity_ttl_hours,
agents.max_concurrent_*,context.diet_*,cloud.last_contribute,
code_health.coupling,boundary_policy.audit_cross_access,
gateway_server.admin_bind_host/usage_retention_days,[solution.commercial],
theresponse_shapingsub-sections,proxy.reasoning_budget,
proxy.pipeline.enable_effort,conversation.summarize_score_range/
ccr_store_dropped,cache.l1_max_entries/l3_gc_threshold, and four
memory.gotchakeys. Profiles losetranslation,layout,budget,constraints,
capabilities,pipeline,read.max_tokens_per_file,read.prefer_cache,
compression.output_density/terse_mode/adaptive/entropy_threshold,
routing.max_model_tierandautonomy.auto_response/response_min_tokens; the
built-in profiles no longer suggest budgets they never enforced. - Migration: older files keep loading. A writable global
config.tomlhas retired
keys removed automatically (the comments of other keys are kept);lean-ctx doctorand
lean-ctx config applyname any that remain as "retired" instead of "unknown".
- Fixed: an
Removed
-
Personal Cloud. Cloud sync, knowledge and gotcha sync, the hosted personal index and
the cloud dashboard metrics close on the 3.12.0 release day: writes stop and the hosted
endpoints answer410with{"error":{"code":"personal_cloud_ended"}}. Stored Personal
Cloud content is deleted 30 days after release; there is no export. Local data is unaffected. The engine side goes: the cloud client and cloud sync,
lean-ctx login,register,forgot-password,account,sync,contribute,cloud
andenterprise, the knowledge vault and index bundles, and the[cloud]config
section (a retired key; the legacycloud.contribute_enabledopt-in is still migrated
totelemetry.enabled). -
Hosted index.
pro.hosted_indexis retired; the hosted index stack (upload,
pairing, egress admission, the semantic search shortcut) is removed. -
Hosted team servers. They close on the 3.12.0 release day. Removed: the
teamCLI and its completions, the dashboard's
/api/knowledge/{publish,team}, the shared-artifact store and team artifact runtime
modules,savings pushandsavings teamwith the daemon's savings auto-push, and the
team_url,team_tokenandteam_auto_pushkeys (now retired). Local savings,
savings sign,verify-batchand ROI stay. -
ctxpkg.com connection. ctxpkg.com closes on the 3.12.0 release day and its packages
are archived without migration. Removed: the hosted-registry client, the remote
dependency resolver,pack update,pack publish, remotepack install ns/name,
addon add ns/nameandctxpkg.lock. Packages and add-ons install from local files; a
scopedns/nameis refused with that hint. The.ctxpkgformat, signing and
verification stay. -
Pro gating and promotion. The leaderboard route and proxy rank header, the README
badge command, Pro conversion nudges (session dismiss-pro|show-pro), the billing CLI,
the dashboard value-gate summary and/api/billing-badge, and hosted Wrapped
publication (gain --publish|--leaderboard|--link|--rejoin|--unpublish, the publish
prompt, startup auto-publish, the weekly nudge and the recovery-phrase identity it
used).[gain]is a retired config key. Localgain --wrapped,--svg,--share,
--copyand--openstay. In the Cockpit: the Account and Cloud pages, the checkout
flow, the team memory tab, team pills, the share sheet,/api/gateway/entitlement,
/api/gateway/teasersand/api/gateway/pro/*(now/api/gateway/analysis/*). In the
engine: the licensed/api/runtime/pro.dashboard.knowledge_workflowsroute, the
dashboard exchange,core::billing(plans, signed entitlements, metering, settlement
evidence) and the savings ledger's evidence projection, and the runtime's personal
licence activation, provisioning, renewal, project sync, context sharing and
engine context-personal-sync. -
ctx_work_graph action="execute"with itsconnector,modelandmax_attempts
parameters, and the agent connector layer behind it (Claude Code/Codex/Cursor CLI
launch, process supervision, cancellation signals, retry, usage parsed from CLI
output). Callingexecutereturns the host-start path. -
lean-ctx pair: remote pairing was never implemented; the command prints a pointer. -
34 retired MCP tools are removed (30 from this release plus the four #509
aliasesctx_smart_read,ctx_multi_read,ctx_semantic_search,ctx_symbol).
A call — directly or throughctx_call— fails with a message naming the
successor (ctx_compose,ctx_graph,ctx_search,ctx_expand,ctx_read) or
the way forward. The default profile advertised none of them; every tool with real
use had a direct successor. Ledger eviction under context pressure moved to
ctx_control action="evict". List:docs/migration/focus-2026-10.md§3–4. -
The read-path autonomy drivers are removed (session-start project overview,
related-file hint, silent import preload, post-read prefetch, automatic cache dedup).
An A/B on the retrieval corpus (3 interleaved repetitions, warm index) returned
byte-identical responses and equal R@5/MRR without them, while the first call of a
session took 2–14 s longer. The overview carried the wake-up briefing but exceeded the
400-token injection cap on real projects, so the briefing never arrived: it is now
delivered on its own as--- AUTO CONTEXT ---on the first call, its project facts
fitted to the cap (most salient first). On 932 real knowledge stores every briefing
now arrives; before, the facts block alone exceeded the cap for 19 %. Retired keys:
[autonomy] auto_preload,silent_preload,auto_related,auto_dedup,
dedup_threshold(and theirLEAN_CTX_*variables; profile[autonomy]keeps
enabledandcheckpoint_interval). Breaking: the Autonomy Drivers contract
andctx_proof'sautonomy-drivers-v1export are withdrawn with their producer. -
The workflow evidence ledger is removed (
workflows/evidence-ledger-v1.json).
ctx_proof,ctx_agentsnapshot andctx_handoffexports indexed their files
there, but nothing read it; the contract still described the removedctx_workflow.
A snapshot export no longer reports an error when only that index could not be
written. Receipts stay in the execution ledger, security events in the audit trail.
Breaking: the Workflow Evidence Ledger contract and
leanctx.contract.workflow_evidence_ledger_v1.schema_versionare withdrawn. -
ctx_intentandctx_taskare removed (no call from any installation in the
30 days measured). Intent is inferred from the tool calls;ctx_compose(task=…)
selects context for a task andctx_knowledge action="remember"stores a fact (the
JSONknowledge_factintent did the same). Task assignment is host execution:
ctx_work_graphkeeps the shared coordination state, A2A peers keep/a2a, and
ctx_agentstill lists an agent's tasks. Breaking: the Intent Route contract
(v1 historical, v2ctx_intent format=json) is withdrawn with its only surface;
leanctx.contract.intent_route_v2.schema_versionis gone from the contract keys. -
Grammar-addon remnants and two OCLA execution modules without callers
(reference_adapters,regression_gate). -
CLI commands
visualize,demo,calibrate,benchmark-runand the modules
only they used (visualizer,calibrator,local_runner): calling one prints where
the measurement lives now and exits with 2. -
Domain and compliance packs left the Community engine.
healthcareand
finance-euare LeanCTX Pro;eu-ai-act-deployer,iso42001-aligned,
soc2-contextand the EU AI Act / ISO 42001 / SOC 2 mappings are LeanCTX Enterprise.
lean-ctx compliance report(signed CISO report),policy coverage --frameworkand
audit evidence --frameworkstay in the engine and take their framework assessment from
the licensed Enterprise runtime; without it they name the tier. New:
lean-ctx compliance factsprints exactly what the runtime assesses (policy facts, no
patterns, no content);lean-ctx compliance verifychecks a report offline, no license.
Breaking: a project pack withextends = "healthcare"(or another former
built-in) no longer loads; the error names the tier. Switchextendsto
strict-redactionand add your own patterns, or install the paid pack. Built-ins
are nowbaseline,strict-redaction,open-source; the Community PII filter
(IBAN, cards, e-mail, phone, SSN, AHV) is unchanged. Evidence bundles keep
manifest.framework(alwaysnull). Released versions up to 3.11.x keep their
Apache license. -
Hebbian cache-eviction bonus, FEP prefetch and Boltzmann eviction are removed. A
replay of 4,906 real reads showed the bonus lowered re-read cache hits (47.1 % → 51.5 %
without it, −11 % resent tokens); the prefetch hint only reached a debug log; Boltzmann
eviction had no caller.ctx_read/ctx_searchoutputs are otherwise unchanged. -
OCLA modules without a production caller are removed:
runtime,wire_middleware,
openapi(never mounted;/openapiis served bycore::openapi),wire_stream,
ledger_export,policy_bundle,tracing(its health component always reported zero
spans and is gone from/ocla/v1/health), the never-startedsidecarandgrpc_bridge
listeners, the scheduler cluster (reference_scheduler,scheduler_service,
policy_constraints,catalogue,OclaRegistry::discover), the experiment execution
helpers, and the RTK capability manifest whose adapter was already gone. Native
engine_interfaceplans keep byte-identical scheduler evidence, so stored plans
still validate.[ocla.sidecar]and[ocla.grpc]in a config are ignored.
Breaking for library users: the deprecatedlean_ctx::oclamanifest module
(superseded bylean_ctx_protocol::CapabilityManifestV1) is removed. -
Dead code without a production caller is removed: five source files that were never
compiled, the oldwrapmodule (superseded bylean-ctx wrap), unused copies of the read
reuse / search grouping / inference manifest / provider header logic, the proxy modules
image_compression,latency_guard,usage_azureandsensitive_transport, nine unused
coreandcontext_kernelmodules, and four unused functions in learning modules. The
proxy no longer copies every request's message list for the removedctx_live_zonetool.
Tool descriptions and the full-tier read hint no longer name removed tools.
A second pass removed the blanketallow(dead_code)on the proxy and twelve modules, so
the compiler guards dead code again, and with it what that exposed: the edit-snapshot
and read-provenance stores (every redirected read re-read and kept the file for a guard
that was never wired), the never-used stream shaper, the web-app detection middleware
and tracker (their per-request result was never read), the agent-execution capability
adapter,benchmark_spec,saliencyand two test-only kernel modules. -
Never-wired surfaces are withdrawn. The frozen protocol contracts
invocation-context-binding-v1andinvocation-evidence-manifest-v1(types, schemas,
vectors) are withdrawn — nothing produced or consumed them — solean-ctx-protocol
moves to 0.4.0. The stable contract
tokenizer-translation-driver-v1is withdrawn: its driver was never called by the
engine (no output ever used it).lean-ctx introspect qubo(QUBO selection spike) and
the deprecatedcontext_kernel::policy_enginealias are removed; two internal modules
that were never wired (a signed invocation-admission verifier and a reader for a
never-written "v2" receipt layout) are removed — Engine receipts remain the canonical v1
artifacts. The daemon no longer sends the one-way handshake to an enterprise sidecar,
and the sidecar itself is removed: it synced policies only to count them and never
recorded metering. The gateway proof register's case 5 now cites only the production
enforcement tests (policy::floor, config merge). -
Commercial leases stop carrying three unused features (
graph_analysis,
multi_agent_orchestration,quality_experiments): no runtime ever checked them.
Older leases that carry them still decode;model_routingstays (older runtimes
check it as the base-runtime right). -
cognitive_modeand its science features are retired. Measured on the retrieval
A/B corpus,full(the default of every 3.11 release) produced +74 % read output with
no retrieval gain (R@5 and MRR identical). Removed: Wasserstein chunk allocation, the
FSRS recency boost in knowledge recall, file-trajectory prediction and cache warming,
verbosity learning, anti-interruption events, intent-keyword enrichment in
ctx_compose,autochoosing thecognitiveview, the cockpit science panel and
lean-ctx cognitive.ctx_read mode="cognitive"and"mdl"render the map view.
The key is retired: older configs load, the migration removes it. -
Learned co-access ranking is retired (
[graph] traversal_edges): it wrote on every
read, changed no retrieval result in the A/B corpus, made ranking depend on history,
and as a cache bonus it lowered the hit rate (−4.4 points, −29 % tokens saved). -
Learned compression-threshold shifts are retired. Since #1910 the rendered read
ignored them, yet every entropy read still loaded the feedback and learner stores, the
cockpit showed per-extension "learned behavior" andlean-ctx learningexported it.
The bandit arm that feeds the adaptive planner's weights stays. Learning bundles move
to schema 2 (LITM calibration only); v1 bundles still import. -
<data>/evidence_ledger.jsonlis no longer written. Nothing ever read it and its
savings column was always 0; the existing file can be deleted. -
ctx_composedrops its "Related (associative)" section. Measured over 882 replies
of the retrieval A/B corpus: it appeared in ~5 % of replies, ~110 tokens each, with
~10 % precision, and never surfaced a relevant file the ranked list had missed. The
spreading-activation module andLEAN_CTX_COMPOSE_GRAPH_BUDGET_MSgo with it. -
Retired enterprise leftovers: the archived platform server, its deploy kit,
Dockerfile and installer (leanctx-cli), and the unusedengine-integrationcopies in
commercial-core. One canonical JSON helper (core::canonical) replaces eight private
byte-identical copies. -
Capability
pro.result_fusionis retired together with the two never-wired
context_kernelmodules behind it (capsule_wire,result_fusion): no tool, agent
or runtime ever called them, and the catalog entry pointed at an unrelated file. It is
no longer granted by any plan; entitlements signed with it still verify. -
Bare
lean-ctx prove(simulated decision-loop self-test) is removed; it runs in the
test suite instead.lean-ctx prove speed,ctx_proofandlean-ctx audit evidence
stay.lean-ctx evidence-exportno longer writesproof_result.jsonor the
"Decision Loop Proof" and "Semantic Model: READY FOR TRAINING" lines: they reported a
simulation (and a fixed string) as evidence. -
Role budgets, SLOs, anomaly detection and the degradation policy. Role token/shell/cost limits (
[limits]in role files), the session cost cap ([cost] max_session_cost_usd,LEAN_CTX_COST_CAP_OVERRIDE), budget warnings and nudges,slos.tomlevaluation, the anomaly detector (anomaly_detector.json), and the profile[degradation]policy with its context-pressure read-mode downgrade are gone, along withctx_session action=budget/action=slo, the dashboard/api/slosand/api/anomalyroutes and their SLO/Anomalies views, theBudgetWarning,BudgetExhausted,SloViolationandAnomalyevents, thedegradation-policy-v1contract and proof artifact, and the Prometheus serieslean_ctx_session_cost_usd,lean_ctx_session_context_tokens,lean_ctx_shell_invocations_total,lean_ctx_slo_violations_total,lean_ctx_anomalies_total(Datadogleanctx.slo.violations). Existing role, profile and config files that still contain these keys load unchanged (the keys are ignored), and older event journals with the retired event kinds stay readable. Per-agent context budgets (agent_token_budget) are unchanged.
Deprecated
quality-labandevalstill run and print a one-line notice on stderr.[shadow] baseline_modelis deprecated and ignored; existing configuration
files still load. Reports keep the note that the baseline is simulated.
Fixed
-
Claude Code requests through the proxy are no longer refused (HTTP 403). Anthropic's
safeguard metadata carries boolean flags whose key names read like classification
markings, so the egress check flagged them as restricted content for a remote destination.
On the Anthropic route a known boolean field in the rootsafeguardsarray is protocol,
not a classification banner; project policy and every other detector still apply, and
every key a caller chose is still inspected in full. -
A busy agent store no longer fails a tool call after 750 ms. The file lock of the
agent registry, the task store, the work graph and agent leases is polled and not a fair
queue, so under load a call behind other writers could time out and report
lock … timed out. It now waits up to 5 s; nothing was lost before, the call failed. A
fair lock follows in a later release. -
Claude Code: the mod no longer defers
ctx_patch,ctx_globandctx_tree. The
Claude Code mod kept only six lean-ctx tools in the prompt and deferred the rest behind
ToolSearch, overridingalwaysLoad, so models fell back to native Edit/Glob although the
rules route editing and file finding to lean-ctx. The defaultfront_loaded_toolsnow
covers every core tool the rules route to, and a test keeps the two in step. -
Two first
ctx_handoff createcalls with onerequest_idstore one ledger. Keyed
creates of one agent in one project are serialized under a bounded lock; the second
call is served the first call's ledger. -
A refused source re-check is in the decision receipt. When a search serves a
provider chunk admitted before and its source now refuses it (revoked, unavailable, …),
the call's receipt records a content-free denial with that source state
(source.revoked, …) instead of a debug log line only. -
Concurrent writers no longer lose shared memory entries (
ctx_memory): one project's
store is now locked from load to save. -
A server switching roots no longer takes over another agent's saved session, and
cross-project knowledge search no longer serves other projects' session findings. -
Installing a
.ctxpkgfile verifies before it pins. The original bytes are stored,
every check runs before anything is written, and a failed install exits non-zero and
leaves nothing installed or pinned.pack sendrefuses packages that fail admission and no
longer sends the local path or project hash; uppercase package scopes are refused. -
An interrupted legacy adoption or knowledge migration resumes cleanly instead of
duplicating facts or leaving a partial project partition. -
A governed proxy request whose every object is withheld is refused with its reasons
and a withheld receipt, like the call routes, instead of failing for want of a receipt. -
Crash logs redact secrets in the panic payload.
-
read -m signatureskeeps parameter types (fn f0(a:i32)instead ofa:n). -
ctx_agent share_knowledgeno longer crosses projects. Shared facts were kept in one
installation-wide file, so a fact shared in one project reached the agents of every other
project. Facts are now stored per project, admitted before they are stored and re-authorized
for each reader, and written atomically. The old file is moved unread into
agents/shared_knowledge/quarantine/and never served. -
A Work Graph child taken with
action="claim"could never finish: its fenced receipt
required a measured connector receipt that nothing produced. Receipts are now bound to
the fence and recorded as reported usage (usage_source: "reported"), still bounded by
the node and chain budgets. Reported figures no longer free the parent's reservation. -
A started Work Graph child that exhausted its budget kept its concurrency slot and path
claims forever; every terminal transition now ends the incarnation. A stopped child's
paths stay exclusive until the window granted at start ends. -
Projects no longer leak into each other. Archived facts,
ctx_memoryfacts and the
hint they add to tool answers, the archive search (ctx_expandsearch, list, count and id
lookup), scent and claims, diaries, handoff lists andclear, the multi-agent sync counts,
and BM25/vector index directories are now partitioned by project; another project's items
are neither served nor counted nor named. Two clones of one repository no longer share an
index. -
A request keeps its project. A slow call that finishes after the host switched roots
writes into the session it started in; tools no longer load "the latest session" of the
process directory; configuration, policy helpers and writable roots follow the request's
project; the HTTP daemon's shared session ignores client roots; a home directory with a
dotfiles.gitis never adopted as a project root; session restore requires an exact
project match. -
Concurrent writes are no longer lost in knowledge import and bridge pull/publish,
session summaries and the local package index; a received package version is immutable,
whilepack createreplaces your own local build. -
Egress: tool errors pass the release gate like results; the request URL (path and
query, percent-decoded) and relayed header values are admitted like the body, with
provider credentials exempt only for their own destination; WebSocket frames are checked
right before they are sent and observed after; a lost retry observation is stated on the
reply (x-leanctx-egress-evidence); receipts name the caller by a keyed reference. Logs no
longer print error text that may carry content. -
Provider sources: items of two sources with the same id no longer replace each other in
the index, and a classification stamp in a provider title is detected. -
Adding a git remote or renaming the package no longer empties a project. The project's
knowledge, gotchas, archives,ctx_memoryfacts, shared agent knowledge, diaries and shares
are carried into the new identity on first use, proven by the project root they record
(copied, never moved). This also repairs knowledge stores an earlier path-only migration had
copied but then refused to load. -
Background work follows its project: auto-capture, consolidation, summaries and
archives started by a request use that project's configuration; a request without a project
getsproject_unresolvedinstead of the process directory. Agent presence and messages
compare projects by path identity (symlinks, separators), and the dashboard binds a folder
exactly as an MCP session would. -
Context packages marked auto-load apply again. They were applied only by the
session-start project overview, which this release retired, soctx_pack auto_loadhad no effect over MCP. They now apply once per session on the first
call, and the--- AUTO CONTEXT ---block names them. -
SDK Agent Tools v1 keeps its contract. The engine had dropped
ctx_symbol
andctx_fillfrom the negotiated capabilities with their MCP tools, so every
published SDK (all six languages) would have refused the handshake. The v1 set
is back:ctx_symbolruns asctx_search action=symbol;ctx_fillanswers that
it has no successor. -
No hint names a removed tool any more: the
ctx_contextandctx_edit
descriptions, thecontext-focus/context-reviewMCP prompts, the semantic-index
"building" message, the LSP-missing error,lean-ctx cheatsheet, the impact
"not found" hint and the removal message forctx_analyze/ctx_compare(which
named a non-existentlean-ctx compress --diff). -
Hermes plugin: it offered
ctx_semantic_searchandctx_summaryto the
model and calledctx_summaryat session end; it now exposesctx_search
(withaction=semantic) and saves the session withctx_session action=save. -
The unused
ctx_semantic_searchentry of the default
[loop_detection] tool_total_limitsand of the lead-gen persona is gone (no
behaviour change: semantic search counts againstctx_search). -
Guides and references (
docs/guides,docs/reference, README, llms.txt,
package READMEs) name the successors. -
ctx_work_graphnames every missing field at once. 45 of 64 calls failed in the
30 days measured; the largest class was a missing argument reported one field at a
time, so agents retried field by field. An incomplete call now lists the fields the
action requires and the ones missing; concurrency and duplicate-graph errors say how
to proceed. -
The project graph is the same on every build. Orphan files got their "sibling" edge
from the first match in hash order, so two builds of an unchanged project differed in
about 40 % of their edges, and graph-based impact and
ranking changed from run to run. Files are now visited in sorted order; the
index backend's symbol lookup also caps its 100 hits in path/line order like the
property graph does (#498). -
Semantic redaction reaches the agent. The release point re-ran the advisory semantic
detector on text it had already redacted; a model is not idempotent on its own output, so
everyctx_readwith a semantic redaction was withheld asrelease.unadmitted_contentand
each read paid the model twice. The release point now re-checks with the built-in floor. -
Sessions and observations save under a semantic PII detector. Identifiers, configuration
tags and paths must stay exact; a model finding there (a user name in a project path) failed
every session save. Exact positions are decided by the built-in floor, content fields keep
the semantic stage. -
Dense texts are inspected beyond 32 findings. When the runtime stops at the findings
bound, the Engine asks for the rest (with context) within the same time budget. -
ctx_searchbatch queries acceptpath/file_path— the handler read them,
but the key check refused them (265 failures across 74 installations in 30 days).
Unambiguous near-misses (regex,query,maxResults,limit,glob, …) are
mapped to the canonical key; other unknown keys are still named. -
ctx_readis about eight to twelve times faster (release build, 2,500-file repository:
p50 1,263 ms → 158 ms on first read, ~1,210 ms → ~100 ms on re-reads). The built-incoderprofile ran a prefetch — a graph walk plus up to ten
admitted file reads under the session-cache lock — after every read, for a result only an
internal event saw; it is no longer on by default.minimal_overheadnow defaults to
truealso when a config.toml does not name it (it readfalsethere). The read path no
longer loads the code graph per call: post-read enrichment, the session-start hook and
the pre-read mode gate use only a built graph and otherwise schedule the background build. -
ctx_composeno longer refuses unchanged results with "source authority changed"
(a timed-out worker invalidated its caller's ended policy view) and reuses the resident
search index instead of loading it from disk per call. While the index of a cold project is
still building, ranked sections can still differ between sessions. -
The path jail admits the host's own session output read-only — Claude Code's
tool-results/subagents, Cursor'sagent-tools/terminals, Claude Code's private
scratch dir — and~/.pyenv/versions; credentials beside them stay jailed. -
Gateway refusals name the setting behind them; passwords in
https://…and other
URLs are redacted;ctx_work_grapherrors say what to do next. -
Provider items are found by search again. Issues, tickets and other provider results were indexed but never returned by
ctx_search(also withaction=semantic) in BM25 mode. They are now part of the search view whenever their source still returns them to the current reader; an item the reader may not see adds nothing to the ranking — no title, count, snippet or term statistic. -
Governed search is about three times faster and no longer refused by an MCP server's memory target. Admitted files are chunked in parallel (admission itself stays on the request's thread), freed memory is returned before each search, and a search is refused only at the hard memory level. On a 2,782-file tree: about 7 s per search instead of 19–21 s, and the MCP server answered all 18 searches of the measurement instead of 6 at its default 512 MB target.
-
A query in words finds
snake_caseidentifiers.admit_source_typedis also indexed asadmit,source,typed, as camelCase names already were. Only the index splits: a query forsettle_canarystill means that identifier. On 18 labelled code questions recall@5 rose from 0.50 to 0.72 and MRR from 0.32 to 0.54. -
Provider results under a symlinked project path are searchable (macOS
/var→/private/var); they were written to an index no search read. Two provider queries in quick succession no longer race on the index file, and an item queried again replaces its earlier copy. -
The Provenance view of the dashboard loads again (it called an API method that does not exist).
-
An expired team artifact's kept copy is removed at the next use, which refuses it.
-
Agents outside a project are told what is missing (OpenCode). When a host starts lean-ctx outside a project (OpenCode launched from the home directory) and reports no project directory, a search or tree without
pathsaid only "active project root is required", and a relative read failed as "file not found: ~/src/main.rs". Both now say that the session has no project yet and to pass the absolute project path, after which that project stays bound. OpenCode installations hit this four times as often per installation as Claude Code. -
Rules name only the tools the session is offered. With no profile pinned, the injected rules and MCP instructions were written for the full tool set, while
tools/listoffers the lean core (OpenCode, Cursor and other clients: 11 tools). They namedctx_knowledgeand, for native-editor clients,ctx_patchas if callable, and agents called tools their list did not contain. Guidance now describes the lean core and points toctx_callfor the rest; the skill shows non-core tools in theirctx_callform. A pinned profile keeps its full set. -
Reading a file in windows is no longer booked as a correction. A
lines:window (and thehead,tailandsed -nreads the shell hook maps onto it) counted as a compressed read, andhead/tailthroughctx_shellas a full re-read, so paging through a long file produced a correction for nearly every window — hundreds on a single long instruction file in Codex sessions. A correction is now only a lossy compressed view (map,signatures,aggressive,entropy,task,reference,cognitive,mdl,density:,autoresolved to one of them) followed by the full content (full,raw, whole-fileanchored, orcat/bat/less/morewithout a range). Windows,head,tail,sed -nranges anddiffdeltas are partial reads: they neither start nor complete a correction.anchored, which is verbatim plus line anchors, no longer starts one either. A failed edit after a window read is no longer charged to a compressed read. -
Edits made through the shell cancel a provisional correction.
sed -i,perl -i, output redirection (>,>>,>|,&>),tee [-a],cp/mv/installonto a file andapply_patchbodies — throughctx_shell, also in&&/;chains, aftercdand insidesh -c/lean-ctx -c— now count as edits of their target files, likectx_patch. Native shell commands seen by the Claude Code, Cursor and Codex Bash hooks and Codexapply_patchcalls (the Codex observer hook now also matchesapply_patch) report the edit through the edit beacon.2>/dev/null,2>&1,>&2and targets built from$VARare never edits. Shell reads are resolved against the command's working directory, so a relativecat src/x.rsnow matches the filectx_readread. -
Reading a file before editing it is no longer booked as a correction. A compressed read followed by a full read of the same file was booked as a bounce (a correction that cancels the read's savings) at once, even when the full read was the preparation for an edit — the flow lean-ctx itself recommends (map to orient, full to edit). A detected bounce is now provisional for 10 read ticks: an edit of the file inside that window —
ctx_patch,ctx_edit, or a native host edit (Claude CodeEdit/Write, CursorStrReplace, …) reported by the hook through a small edit beacon in the data directory — cancels it; otherwise it is booked when the window passes, and at shutdown at the latest. Only booked bounces reach the ledger, the per-path memory, the quality signal and the scent field. -
A file lean-ctx learned is always re-read in full is delivered in full for explicit compressing modes too. The per-path memory (#496) only steered
mode=auto, so an explicitmap,signatures,aggressive,entropy,task,reference(orcognitive,mdl,density:) read of such a file still bounced. It is now served in full with the notice[mode overridden: map -> full, reason=learned-full, pass fresh=true to keep the requested mode];lines:,diff,rawandanchoredstay untouched. -
Agent instruction files are served complete on every read path.
ctx_readalready deliveredAGENTS.md,CLAUDE.md,GEMINI.md,LEAN-CTX.md,SKILL.mdand the documents underskills/,.claude/rules/,.cursor/rules/in full; the internal read path behind CLI and helper tools did so only forauto, and a relative path that starts with the directory (skills/…/guide.md,.claude/rules/x.md) was not recognised. Both now follow the same rule, and a relayed compressed view from another agent no longer stands in for an instruction file. -
Savings-ledger events say which agent produced them. Every event carried
agent_id: "local"unlessLEAN_CTX_AGENT_IDwas set, so corrections could not be attributed per agent. A single-client MCP server now records<client>:<bus agent id>(for exampleclaude-code:mcp-1274-…), hook and CLI processes record their host (claude,codex,cursor), andLEAN_CTX_AGENT_IDstill wins. A server that sees a second, different client falls back rather than mislabel. Signing keys and the hash-chain format are unchanged; existing entries verify as before. -
The shell hook intercepts commands in non-interactive bash (#2092). Bash expands aliases only in interactive shells, and agent harnesses run their Bash tool non-interactively — OpenCode through
BASH_ENV— solean-ctx-ondefinedgit,cargo,npmand the rest as aliases that were never used, and every command ran raw without a warning. The bash hook (and the containerenv.shbuilt from it) now enablesexpand_aliases; zsh already expanded them.lean-ctx-statusnow answers on a pipe too (bash, zsh and fish), so an agent can check the hook's state: it printed nothing whenever stdout was not a terminal. -
The Claude Code plugin shapes native Bash output again (#2089). Claude Code 2.1.296 and later lets a plugin call only the tools an MCP server lists, and
ctx_shapeis deliberately unlisted, so every call was refused and large Bash output always came back unchanged (/leanctxshowed "Bash outputs shaped 0"). The plugin now reachesctx_shapethrough the listedctx_call;ctx_shapestays out of the tool list and out ofctx_discover_tools. A refusal on the way (workflow, role, policy, budget or rate limit) is now returned as an error, so the plugin keeps the native output instead of putting the block message in its place, and repeated identical commands no longer count as a lean-ctx loop. -
A hook no longer wraps its own
lean-ctx -ccall again (#2088). The allowlist wrap recognised only a barelean-ctx …, not the binary path the hook itself writes (C:/…/lean-ctx-bin/bin/lean-ctx.exe -c '…'on Windows npm installs). Every time a hook saw such a command it added another-clayer, and the nested quoting then broke in the inner shell, so the command was blocked as a mis-split fragment ('lean-ctx.exe -c '). A command that already runs lean-ctx, by bare name or by that path, now passes unchanged; the PowerShell path checks the same way. -
ctx_shellfollowscd $TMPDIRandcd $Dbefore a relative target (#2079). The redirect and download checks place a relative target in the directory its command runs in, but acdthrough any variable made that directory unknown and the target was refused — although both refusals name$TMPDIRas an allowed destination and$TMPDIR/x/fpassed. Acdthrough$TMPDIR, or through a variable the same command set to a literal path earlier (D=/tmp/x; cd $D && curl -o f …), is now followed like the literal. A command that rebindsTMPDIRto something the check cannot read (TMPDIR=$PWD,read TMPDIR,unset TMPDIR) no longer counts as the scratch directory — this also closes that spelling for download targets (TMPDIR=$PWD; curl -o $TMPDIR/f), which were judged against the environment's$TMPDIR. Any other variable still leaves the directory unknown. -
The word
cdin a quoted argument is no longer a directory change (#2081).printf '… cd /tmp …' > fwas refused because the check read the words of the string as commands. Only words the shell runs count now. A quoted command name ("cd" /x,c'd' /x) still runs and still counts, and anyevalleaves the directory unknown. -
ctx_shelldownloads may write where>may (#2080). A download (curl -o/-O/--output-dir,wget,dd of=) was allowed only into a scratch path, and the refusal claimed the>capture rule applied "as well" and that "a literal path" would do — so agents fetching a model or an asset into their project retried variable, literal and chained spellings and were refused each time with the same text. A download now follows the capture rule: the session's project,allow_paths/extra_roots,write_allow_pathsor a scratch path, judged where the target lands (relative to the directory its command runs in, through variables the command set to a literal). wget is judged by every file it writes (document,-Pdirectory,-o/-alog) instead of being refused outright. A variable that cannot be followed is still refused, and the message states the rule. -
Files with a database connection string are no longer withheld whole. The context gateway masks the credentials of a Postgres, MySQL, MongoDB or Redis URL, then re-scans its output to make sure no secret is left. The masked form still looked like a
user:passwordpair to that re-scan, so every file holding a real connection string —docker-compose.yml,.env, settings modules — was withheld entirely withsecret.redacted, redaction.incompleteinstead of being delivered with the password masked. In 3.11.4 this was 250 failedctx_readcalls on 33 installations in three days. Detector and redactor now share one rule, so masked output never matches again. The rule also masks a password that contains an unencoded@in full and covers the user-less Redis form; anAuthorization :header with a space before the colon is masked like one without. -
Agents can read their own settings and MCP configs.
ctx_readrefused~/.claude/settings.json,~/.codex/config.toml,~/.cursor/mcp.jsonand the like as a "protected location" — in 3.11.4 the refusal seen on the most installations (103 of 591 in three days), typically an agent checking its own setup. These files now open read-only for the session, file by file, like skills and rules already did; a token in them is masked by the context gateway. Credential files (~/.claude/.credentials.json,~/.codex/auth.json),~/.claude.json, sessions and transcripts stay jailed, and lean-ctx still never writes there. -
ctx_composeno longer throws away a finished result because the policy check was busy. Every source read is checked against one verified policy snapshot, once before and once after the work. Both checks go through a single shared worker with a 2-second deadline; with many parallel tool calls it answered "busy" or "deadline exceeded", and the finished compose result was discarded as "source authority changed or could not be verified" (43 times on 14 installations in three days on 3.11.4). A check the worker could not serve is now asked once more; an invalid or changed policy still fails on the first answer. The error also names which check failed. -
The daemon no longer grows with every project root it indexes (#2075). Measured with 16 copies of the lean-ctx source tree (4,541 files each) indexed one after another on Linux: 3.11.4 grew linearly to 1.3 GB (peak 1.6 GB) and released nothing when idle; it now levels off at ~550 MB after eight roots (peak 0.8 GB). Four causes, all fixed:
- Freed memory was never returned to the OS.
arena.<i>.purgetakes no value, but lean-ctx passed one, so every purge failed and the failure was logged only at debug level. In a macOS test, a dropped 900 MB parse working set stayed in the footprint; with the call fixed it falls to ~50 MB. - tree-sitter's parse trees came from the system allocator, which kept the pages: on macOS 336–404 MB stayed after the trees were dropped, and
malloc_zone_pressure_reliefreleased none of it. tree-sitter now allocates from jemalloc, so the purge reaches its memory too. On Linux, glibc's free pages (SQLite and other C code) are also trimmed. - The search index stayed resident for every root, without limit. The daemon now keeps at most eight, dropping the least recently used first, as the graph cache already did.
- The daemon's memory guard only cleared the file-content cache, even at hard pressure. It now runs the same eviction as an MCP server, dropping resident search, graph and embedding indexes too. A new
daemon_max_rss_mb(2048 MB, envLEAN_CTX_DAEMON_MAX_RSS_MB,0= percent only) caps its target on large machines, where 5 % of RAM let a daemon reach several GB first.
- Freed memory was never returned to the OS.
-
Windows: rooted reads of a relative path open the file inside the project. The read checked the path against the project root but then opened it relative to the process's working directory, which for the daemon is not the project; such reads failed or were refused as outside the root. They now open the path the check resolved, as on macOS and Linux. With the path jail off (
path_jail = false), a relative path was not resolved against the project at all on any platform; it now is. -
Self-signing after an update can no longer hang. On macOS,
securityandcodesignran without a time limit; a test with an isolated data directory reached the real signing keychain and waited for a password prompt forever. Each step is now bounded by its own budget within one shared deadline, and a tool that does not answer is ended before the fallback; a timeout falls back to the ad-hoc signature as before. -
Parallel
remembercalls on a busy machine no longer fail. Knowledge writes waited at most 2 seconds for the project lock, so seven parallel writers on a loaded machine could answer "knowledge lock unavailable" and drop a fact. The wait is now bounded at 10 seconds. -
lean-ctx doctornames hooks that run a missing program. A Codexhooks.jsonwith an extraSessionStartentry pointing at a deleted temporary binary failed every session start with exit 127, while doctor reported the hooks as healthy. Doctor now reports any Codex or Claude Code hook whose absolute program no longer exists, whoever wrote it, and names the file to remove it from; it does not delete entries lean-ctx did not write. A stale lean-ctx binary is also reported when a current one is configured next to it, since every configured hook runs. -
lean-ctx claude-mod installfinds Claude Code when PATH does not show it yet. A terminal or editor started before Claude Code was installed reported it missing. After PATH, the installers' default locations are checked (~/.local/bin, and on Windows%APPDATA%\npm\claude.cmd), under the same trusted-location check. -
Refreshing Codex hooks keeps your own hooks. Recognising lean-ctx's entries by "contains
lean-ctx" also matched user wrappers such as/custom/lean-ctx-wrapper hook rewriteor anecho lean-ctx …hook, and setup replaced or removed them. Only commands that run the lean-ctx binary itself count as lean-ctx's now; other hooks in a shared entry stay, and outdated lean-ctx commands in it are updated to the current binary. -
cargo build --no-default-featurescompiles again (#586). The featureless build that FreeBSD and other ports were told to use had decayed to 99 compile errors after CI switched to checking only feature sets that includehttp-server.http-servernow gates the servers alone: the HTTP client (reqwest),hexand the proxy's accounting (CCR archive behindctx_expand, usage meters, savings, introspection) build in every configuration, while the proxy server and its provider adapters stay behind the feature. A new CI step checks the build with no features at all. -
ctx_searchwith a filepathhonoursincludeandexclude(#2059). Pointingpathat one file and addinginclude="*.rs"scanned 0 files and suggested fixing the glob: the glob was matched against the file's path relative to itself, which is empty. A file root is now matched by its name. -
lean-ctx callalways returns the content (#2060). A one-shotlean-ctx call ctx_compose(orctx_read) could print only[cross-agent cache · compose · produced by …]when another process had delivered the same result in the same Claude Code conversation. The caller of a one-shot process never received that delivery, so such a process now never serves a stub or cache reference. Cachedctx_composeresults also expire when the embedding model changes or the dense index is rebuilt; they were ranked with the old vectors. -
lean-ctx call ctx_composewaits for its ranking (#2049). On a large project the BM25 ranking section read "local BM25 ranking deferred" because it had the 4-second budget meant to keep an agent loop responsive, and the finished ranking was then discarded. A one-shot call now gives it up to 120 seconds; MCP sessions keep 4 seconds. The note namesLEAN_CTX_COMPOSE_BUDGET_MS, which overrides both. -
lean-ctx index statusno longer reports a differing daemon root for the same directory (#2049).G:/projectandG:\project(or\\?\G:\project) were compared as text. -
Semantic search headers show Windows project roots as written (#2063).
ctx_searchwithaction:"semantic"printed the root as\\?\C:\…. -
lean-ctx claude-mod installfinds Claude Code on Windows (#2061). It reported "Claude Code not found on PATH" for npm installs (claude.cmd, previously not accepted) and for the native installer's%USERPROFILE%\.local\bin\claude.exe; multi-segment trusted roots also never matched canonical\\?\paths. Both are now recognised under the same trusted-location check, and the message names the actual reason (not on PATH, untrusted location, or failed to run). -
ctx_callgraphfinds calls written with a module path. A call such ascrate::config_io::write_atomic_with_backup(..)orcompound_lexer::split_compound(..)was invisible tocallers,callees,traceandrisk:write_atomic_with_backupshowed 3 callers instead of 83. Queries now match a call by its path segments, sowrite,config_io::writeandcrate::config_io::writeall find it, whilea::savenever matchesb::save. A path call whose module or type names exactly one defining file (config_io::write→config_io.rs,Repo::save→ the file definingRepo) is now bound to that file as[resolved]instead of[ambiguous]. Stored code graphs rebuild once on the next query. -
entropyno longer drops facts or hides what it dropped. The view used to delete a file's most predictable lines without a trace, which removed rows such asre("git", Category::Vcs)from a look-alike table and every variant of an enum, and left code that looked complete. A line that holds a string literal or code identifier found nowhere else in the view is now kept, and every omitted run reads[lean-ctx: omitted N lines]. On dense source the default therefore saves less than before: those savings came from the silent deletions. Higheraggressivenessstill sheds more. -
density:Xworks on source code. It fell back to the full file for almost every Rust file at any target: its quality guard demanded an information density that unmodified code does not reach, and a fixed identifier share only a view of 80% or more could meet. A density view now keeps definitions and imports first, then lines that add identifiers the view lacks, then the highest-entropy rest; omitted runs are marked and their markers count against the budget. The guard checks the result against the original file and the requested budget. -
Claude Code: re-reading a file with
ctx_readcosts a stub, not the whole result. The MCP server withholds its[unchanged]stub on Claude Code because sub-agents share their parent's connection (#1801), so every re-read was delivered in full. Theread-deduphook now also coversctx_read: when the identical result was already delivered to the same conversation or sub-agent for the same arguments, it is replaced by a one-line stub;fresh=truestill delivers it. The installed hook is extended automatically when the next session starts. -
Task-filtered reads are no longer steered by
git diffcounters. Without a stated task the session took thegit diff --statsummary line ("Modified: 2 files changed, 19 insertions(+) …") as its task, and its words filteredtaskandentropyreads. An inferred task now names the uncommitted files, is refreshed instead of persisting across sessions, and never steers a read. -
Semantic search and
ctx_composeranking work in a subdirectory of a large project. A search scoped withpathwalked and counted the whole project first and failed with "source file budget exceeded" once the project held more thanbm25_max_files(5000) files. The walk now starts at the requested directory and counts only sources the search can return; the error namespath,languagesandbm25_max_files. Linked git worktrees checked out inside a project are skipped by every scan like other worktree copies. -
Searches and indexes no longer read
.gitinternals. Content walks include hidden paths so tracked dotfiles such as.github/are found (#1792), which also letctx_search,ctx_compose, globbing and the BM25 corpus walk.git(.hg,.svn,.jj): a project-wide search returned.git/rr-cacheconflict images as uses in code. Version-control metadata is now skipped below the walk root; asking for.gititself still works. -
ctx_composeshows the code first. Its exact matches came from a single search capped at ten hits in directory order, so root-level docs and agent rule files filled the section. It now lists definitions, then uses in code, and prose only when code has none. -
lean-ctx read -m density:X,-m referenceand-m taskreturn the requested view instead of the whole file when the CLI renders locally. -
referenceis described as what it is: a one-line pointer (path, lines, tokens) without content. The tool schema called it "quotes". -
The Claude Code plugin no longer announces a background job the agent already read. A job that finished during a long turn was announced at once; Claude Code held that wake until the turn ended, and by then the agent had usually read the job itself, so the stale wake cost a whole extra turn. Wakes for jobs that finish mid-turn are now held and sent after the turn only for jobs the agent has not read.
-
Context Gateway: a CLI tool run stored a Decision Receipt only under
protection. In developer mode a stand-alonelean-ctx read(no daemon) admitted
its source and recorded nothing, solean-ctx inspectcould not show the
decision. The CLI now follows the MCP call's rule in every mode: a plain receipt
when a source was admitted, no sidecar and no anchor duty without protection. -
Context Gateway: the evidence store (
<data>/gateway) is packed and bounded.
Receipts are stored zstd-packed (<sha256>.json.zst; plain.jsonreceipts still
load). A background maintenance pass in the MCP server and the daemon — at startup,
hourly and soon after a write that did not fit under the ceiling
(LEAN_CTX_GATEWAY_STORE_MAX_MB, else 10 % ofmax_disk_mb, else 1024 MB) —
counts the store's files and rebuilds its usage ledger from the count, removes
receipts older than 30 days (LEAN_CTX_GATEWAY_RETENTION_DAYS), brings the store
down to 80 % of its ceiling, oldest first, each with its sidecar and observation,
and packs the plain receipts that stay; an unfinished pass is continued by the next
process. The last 24 hours (LEAN_CTX_GATEWAY_PROTECT_HOURS), receipts a project's
latest index lists and receipts of a task in progress are always kept; only when a
pass found them alone filling the store are new receipts refused (developer mode
delivers and logs the missing receipt, protected mode withholds the release). A
stale or copied ledger never refuses a write, and the write path never counts
files.lean-ctx inspect --maintainruns a pass now;lean-ctx doctoralways shows
size, ceiling and the last pass. On the first start after the
update a long-used store is brought within its ceiling in the background; see
"The store's ceiling" in the security reference. -
Shadow Mode priced the uncompressed baseline with a fixed reference model
([shadow] baseline_model, defaultgpt-4o). Whenever the host used another
model, the report labelled the taskmodel_routing, recommended "Model
routing" between the two models, and counted their price difference as a
saving. The baseline now uses the model the host chose for each task, so
only context changes count, and no model is ever recommended.
Security
- Project provider configs load only in trusted workspaces (GHSA-rrww-7924-w72f, high). A
project-local.lean-ctx/providers.toml(or.lean-ctx/providers/) is loaded only after the
workspace is trusted withlean-ctx trust; an untrusted checkout can no longer bring its own
provider definitions. Upgrade note: in an untrusted workspace its project providers are no
longer available until you runlean-ctx trustthere (see the upgrade guide). Hardening of
workspace trust continues. - Gateway-held provider keys need the lean-ctx token (GHSA-53h5-q4m8-vg3x, medium). On a
loopback proxy withproxy_require_token = false, a request carrying any provider key
header could reach a/providers/{id}route whose key the proxy injects (api_key_env,
Bedrock), also through a routing alias on/v1/chat/completions. Such routes now require
the lean-ctx proxy token before the operator's key is injected. - Proof and knowledge export paths stay inside the project (GHSA-pv78-9chr-hj3c, medium).
ctx_proofexport accepts only a plain file name, andctx_knowledgeOKF export and import
paths are kept inside the project jail. Upgrade note: a relative OKFpathnow resolves
against the project root instead of the server's working directory. - Untrusted project config cannot widen write paths (GHSA-79fg-7cj5-4xmm, low). An
untrusted project's.lean-ctx.tomlno longer setswrite_allow_paths, like the other
sensitive overrides it already could not set. - Constant-time helpers. ctutils 0.4.4 (RUSTSEC-2026-0385: mask generation and
u128
comparisons could branch on secret values), in the engine and the cloud and edge services. - TLS certificate verification. rustls-webpki 0.103.16 and webpki-roots /
webpki-root-certs 1.0.10 (RUSTSEC-2026-0381, -0382, -0383). - Agent bus handoffs.
/v1/a2a/handoffverifies the envelope HMAC when
LEAN_CTX_HANDOFF_SECRETis set (401 signature_required/invalid_signature) and
refuses signed envelopes when no secret is configured (fail closed); unsigned handoffs
without a secret behave as before. Addressed handoffs reach only their recipient, live
and after replay. The task store is read under its file lock, soctx_agentexport
pruning and concurrent task updates no longer lose writes. - Secret files. Each owner-only secret-file write uses its own random temporary file,
so concurrent writers of the same path no longer collide; on Windows a writer no longer
fails when another one already removed the old file.
Coming in 3.12.1
The Hive connector code ships in 3.12.0 but stays switched off: lean-ctx hive connect
and lean-ctx hive link refuse with "LeanCTX Hive comes with 3.12.1; this version does not
connect to a Hive.", and hive is not listed in help or completions. The items below take
effect with 3.12.1.
- What leaves for a swarm is checked on the machine. Results, proposals, verdicts (reason
and value) and report notes pass the secret and personal-data screening. For a public
swarm they also must not contain text of a repository linked to a vault on this machine
(three consecutive lines or about 200 bytes of one file; the refusal names no file, and a
check that cannot run refuses). Text fields and every string of a value refuse invisible,
direction and control characters; list items are single lines of at most 500 characters.
A team swarm of another organization is left out of listings, reported by count only, and
refused before anything is sent to it. - Engine metrics for Hive workspaces (not released yet). A connected engine can send its
workspace hourly counts of what the local cockpit shows, per vault: tokens and savings (by
trust label), read modes, tool calls by tool name, compression, protection and policy-block
counts by rule, sessions, agents used, model spend where it is measured, and redacted secrets
as per-workspace fingerprints. It never sends file content, paths, prompts, model output,
secret values or command lines: every name on the wire is a closed pattern orother. Batches
are signed with the engine's instance key, idempotent per hour (rev), buffered offline (at
most 720 hours / 8 MiB, oldest dropped and counted) and backed off on 429/5xx. Nothing is
collected or buffered unless the workspace's "Share engine metrics" rule is on (Team and
Business by default; Community and Pro afterlean-ctx hive metrics confirmin a terminal),
and turning it off drops the buffer.lean-ctx hive statusshows the line "Sharing engine
metrics with …",lean-ctx hive metrics preview [--json]prints exactly what would be sent
for the last hour,lean-ctx hive metrics deleteremoves what the engine buffered. Sending
stays switched off in this build until the privacy review is done; the guide follows with
3.12.1. lean-ctx hive connectis the one step to Hive. It signs in through the browser
(device flow), where the person chooses the workspace for this machine; then it asks once
per workspace what this machine shares with it and lists each channel that is on (captured
knowledge, daily usage totals, context receipts, agent presence and bus messages). The
answer is kept in<config_dir>/hive/sharing.json, so a later connect or session asks
nothing;--yesanswers yes without asking. A "no" turns every outbound channel off in
[hive]while the workspace's knowledge and policy are still pulled. Without a terminal
and without--yes, the[hive]settings apply unchanged. Running it again on a
connected machine only does the steps not yet answered.- Projects find their vault on their own. At connect, and in the background sync for
other projects whose sessions queued knowledge, the engine asks Hive for the vault of the current project from org-salted
digests of its identity (.lean-ctx-id, the normalized origin URL, the repository's first
commit; never a path, user or host name). A vault this machine may already read is mapped
at once. A suggested vault, a new private vault for the project, a committed link file, or a
vault that moved to another workspace waits for one confirmation by the person: at
hive connectin a terminal, or withlean-ctx hive consent approve <id>. Agents, MCP
calls and--yesnever confirm it; until then the project's knowledge stays on the machine
and sync reportsconsent_required. The same repository URL alone never gives access.
lean-ctx hive link <workspace>/<vault>stays as the manual override. A Hive without
the match route keeps the earlier resolve, after the same confirmation. - Knowledge states in delivery. Knowledge delivered from a vault replica carries one of
five states, derived on every read from the folded replica, the same way Hive derives it:
verified,provisional,outdated,conflictingorrejected. Outdated items (anchor
changed or gone) are labelled[outdated: re-verify]and conflicting ones[conflicting],
after the current ones; rejected and superseded items are not delivered. - Citing delivered knowledge. Each delivered vault item shows its
node:<id>, and each
section says once how to cite it. A claim that namesnode:<id>in
ctx_knowledge action=remember refsgets aderived_fromedge to that item, the evidence
Hive counts as verified reuse across engines. lean-ctx hive maintain <workspace>/<vault> --stalere-checks every anchored claim
against the code in this checkout and marks changed ones to verify and missing ones
gone (no model, no cost; the same check runs after each capture during sync).
--stale --confirm <node_id>re-anchors a claim the person checked at the current code.
It prints counts, never claim texts.- A task result can be a failure.
lean-ctx hive tasks submit … --failedand
ctx_tasks action=submit outcome=failedend the task as failed; the default stays
completed. Against Hive v5 a result ends the task at once, without a person's decision; an
Hive before v5 takes no--failed(release the task instead). lean-ctx hive statusnames the filter packs the org policy requires and whether each
is installed exactly as signed (policy.required_filter_packsin--json, a
Required:line in the text output); the Cockpit's organization policy view lists them.- Task claims made with
lean-ctx hive tasks claimstay alive while their agent works.
The CLI ends right after claiming, so nothing renewed the claim and an agent running a long
gate lost it before submitting. The daemon that runs the bus relay now takes over such a
claim while its agent is registered and active within 30 minutes, and renews it at
half-time; once the agent stops, the claim ends at its expiry. - How Hive helped, in the Hive metrics. For each vault and day, the metrics
upload now also carries counts and durations only: how many Hive facts agents asked for and
got, the tokens and list price the project's host sessions used while this machine held a
task's claim (per task), and the median time from a session's start to its first Hive
knowledge. They are recorded locally in a private file; sealed vaults report the same
counts, and no text, path or fact leaves with them. - Hive tasks in the engine.
ctx_tasks(MCP) andlean-ctx hive tasksread a vault's
tasks, claim one, report one-line summaries, submit the result with evidence
(commit, receipt, CI run, URL, fact, or a code anchor on a file or symbol as it is now) and
give it back;proposequeues an agent task that a person approves in Hive, sent with the
next sync and created once however often it is resent. A claim passes the engine's worker
gate (the person's opt-in for the vault, pause, today's budget) and goes out under that opt-in;
Hive checks it again, and the engine shows any refusal as it is. The claim's lease id and
fencing token stay in a private file on the machine, every write carries them, and the session
renews its claims while it runs and gives them back on stop. Summaries, proposals and release
reasons pass the outbox screening (a text holding a credential or personal data is not sent)
and go out sealed in sealed vaults. Task text from Hive reaches the agent fenced as foreign
data, never as an instruction. A session starts with the claims held in the project and its
open tasks. Every task call from a tool ends within five seconds; offline or without the
tasks.*rights the tools answer at once. - Confirmations, auto-merge and rollback for Hive knowledge. An agent confirms or objects
to a knowledge proposal through its own session (ctx_tasks action=confirm|object); this
counts toward the vault's auto-merge threshold; a session never confirms what it wrote, nor does
any session of the machine that wrote it or submitted the task result (in Pro the owner's other
machine confirms), and an objection leaves the proposal to a person (in a sealed vault its
reason stays on the machine). People confirm on the web. When an agent here judged a fact to contradict another one, the
engine objects to a proposal that adds it, once. A sealed proposal that reached its threshold
is merged by the next sync of an engine that may merge, since Hive cannot read it.
lean-ctx hive review rollback <workspace>/<vault> <revision>restores the document of an earlier
revision as a new one; in a sealed vault the engine opens it with that revision's key and seals
it again under the current key, and says so when this machine holds no key for it. - Sealed vaults (end to end). A vault marked sealed in Hive is encrypted on the machines
that hold its key; Hive stores and relays ciphertext only. A maintainer approves each
engine after comparing its fingerprint (lean-ctx hive status), andlean-ctx hive grantpasses the vault key to approved engines. Drafts from a sealed vault carry no readable
summary, title, reason or sources, and Hive refuses any that do.lean-ctx hive review
reads and merges sealed proposals on a machine that holds the key. Removing an engine, its
member or its access rotates the key. - Hive metrics and receipts. A connected engine uploads Cockpit metrics and Decision
Receipt summaries (which context went to which model, no content) to Hive for the team
statistics and proof views. Both are on by default and can be switched off per machine
([hive] metrics_upload,receipts_upload) and per organization in Hive; Hive refuses
an upload kind that is switched off. - Agents across machines.
ctx_agentleases on a file or symbol are coordinated through
Hive when the machine is connected and the repository is linked to a vault, and an agent can hand a task
to an agent on another machine of the organization. The answer always names the scope
(scope=hivewith a fencing token, orscope=localwith the reason); Hive sees only a
hash of project, kind and repo-relative path. Organization controls (hold, stop, veto,
resume) apply to that machine's agents while its lease is valid. - LeanCTX Hive connector.
lean-ctx hive connect [--url <origin>] [--label <name>] [--no-browser]enrolls this machine as an engine instance of your organization through a
device flow (approve the shown code in the browser). The instance key is generated
locally and never leaves the machine; access tokens are minted from signed assertions.
Community includes 1 connected engine, Pro 2, Team 2 per seat; Enterprise: contact us; a
further machine is refused with a message naming the limit, without retries.lean-ctx hive status [--json]shows
organization, plan, rights, lease, queued and refused drafts, the organization policy
and the filter packs from local state only (--jsonis the shape the Cockpit reads);
lean-ctx hive link <workspace>/<vault>links this git repository to a vault
(.lean-ctx-hive.json, plus.lean-ctx-idwhen the repository has no identity);
lean-ctx hive syncsends queued drafts and pulls reviewed knowledge now;
lean-ctx hive disconnectfrees the seat and removes the credentials, the lease, the
keys and the local Hive data (queued drafts, pulled bases, activity), which
--keep-localkeeps. Leases move Valid → Grace → Lapsed; offline or lapsed only pauses
Hive, local tools never depend on it. State lives in<config_dir>/hive(directories
0700, files 0600) and<data_dir>/hive. New[hive]config section (enabled,url,
root_key,auto_draft,pull_interval_minutes,metrics_upload,receipts_upload,
bus,vault_labels,runtime_consent,sealed_grants); a self-hosted Hive needs its
[hive] root_key. - Vaults. What you create in Hive is a vault, linked to exactly one git repository:
lean-ctx hive link <workspace>/<vault>. Commands, help, MCP descriptions and errors say
vault; "repository" stays where the git repository is meant. The engine calls
/v1/vaults/…and sendsHive-Names: vaulton every request and on the bus upgrade, so
Hive answers in vault names.[hive] vault_labelsreplacesproject_labels: the old key
is read as the new one (the new one wins when both are set), the config migration renames
it with its comment, andlean-ctx config validateandlean-ctx doctorname it as renamed
instead of unknown. Files on disk keep their earlier names (.lean-ctx-hive.jsonwrites
repo,<data_dir>/hive/projects.jsonand every local Hive file writeproject_id,
pulled facts keep thehive-repo:tag) and read the new ones too, so a team with mixed
engine builds shares one link file and a machine that goes back keeps its Hive state,
sealed vault keys included. - Worker mode and swarms. With worker mode on for an engine in Hive, the engine's own
agents pull work: tasks of the vaults you chose and subtasks of swarms, within a daily
budget (lean-ctx hive worker status|pause|resume|stop;[hive.worker]can only lower
the budget).lean-ctx hive swarm list|show|material|claim|renew|release|submit|propose| verifications|commit|reveal|reportandctx_tasks scope=swarmshow swarm work the way an
agent sees it, everything others wrote fenced as data. Claims and verification commits
pass the worker gate (opt-in, budget, pause); a verdict is committed as a hash and revealed
later. A public swarm is open to everyone, a team swarm stays inside its organization. - Knowledge channel: drafts out, reviewed revisions in. At session end, on
ctx_session save(debounced to 10 minutes per project) and at server shutdown, what
the agent learned is screened and queued as one draft proposal; no network call runs
inside a tool call or hook. Queued items are durable (<data_dir>/hive/outbox, retries
with backoff from 30 s to 1 h, refused items stay visible inhive status). Reviewed
revisions are pulled everypull_interval_minutes(default 15) into project knowledge
under the categoryhive/<ns>/<name>; nothing is written into the project tree. - Organization policy and filter packs from Hive.
hive syncand the daemon pull a
signed policy bundle. An organization policy is accepted only when signed by the key the
lease pins for the organization, inside its validity window and with a forward-only
version (a downgrade, the same version with other bytes, or a silently dropped policy is
refused). Filter packs (leanctx.filter-pack/v1,redactandblockrules) must be
signed by a Hive key, digest-checked and stay within 128 rules in total; the policy
runtime applies them as redaction and blocked-content rules, also when no project or
organization policy exists. The signed organization policy names the filter packs it
requires (pack, version and digest; Hive protocol 1.8): a bundle that lacks one of them
or carries another version is refused, the engine keeps the last good bundle, and
hive statusandlean-ctx doctorreport the policy as not compliant while local work
continues. A refused bundle never replaces the last good one. On Team
and Enterprise the organization policy is enforced by the optional LeanCTX Intelligence
runtime, installed only with explicit consent (lean-ctx hive runtime install [--yes],
[hive] runtime_consent) and licensed by the Hive lease; without it nothing is
written and local work is never gated. - Agent bus across machines. With
[hive] bus = "auto"the daemon relays the local
agent bus (ctx_agent post/read) to the other machines of the organization
(lean-ctx hive bus relay [--for <seconds>]runs it in the foreground). Outgoing
messages are screened like every outbound text, replays are deduplicated, and incoming
messages pass the normal admission.bus = "off"keeps the bus local. - Hive metrics upload again.
lean-ctx hive syncreported "metrics not sent: unknown
fieldproject": a metrics day named its project where the 3.12 contract names itsvault. lean-ctx hive bus relayno longer panics at start. The build enables both rustls
crypto providers (aws-lc-rs and ring), so rustls could not pick a process default, and the
bus WebSocket's TLS client aborted with "Could not automatically determine the process-level
CryptoProvider" (without a relay no agent presence reaches Hive, so no task can be claimed).
Every lean-ctx process now installs aws-lc-rs first, the provider reqwest and the update
verifier already use; the bus connect installs it as well.- An agent's registered role reaches Hive. An MCP session announces its default role at
start; a laterctx_agent registerwith another role changed it only locally, because the
relay sent a newhelloonly for a new agent or vault, so Hive refused task claims that need
that role. The relay now announces a changed role at once, and announces its agents again
every 5 minutes, which also restores presence Hive closed meanwhile. - Hive refuses older engines. Hive answers requests without a compatible
Hive-Protocolheader with426 upgrade_requiredandHive-Min-Engine, and device
enrollment requires engine 3.12.0 or later; 3.12.0 sends protocol 1.8 on every request. - Hive transport and screening. HTTPS only (loopback HTTP for local testing), no
redirects, bounded response bodies,Hive-Protocolchecked. The trust chain root key →
key set → lease is re-verified on every load and leases issued in the future are
refused. Screening is the single path into the outbox: credentials (including custom
patterns), redaction rules, personal data, card and account numbers, active egress
forbidden_patternsand home paths drop a fact instead of rewriting it, and drops are
counted. An end-to-end test asserts that no canary secret reaches any request body.
Upgrade
lean-ctx update # recommended (auto-downloads + refreshes shell hooks)
cargo install lean-ctx # or
npm update -g lean-ctx-bin # or
brew upgrade lean-ctxNote: After upgrading via cargo/npm/brew, run
lean-ctx setupto refresh shell aliases.lean-ctx updatedoes this automatically.
Full Changelog: v3.11.4...v3.12.0
