n-dx 0.8.0 — Find your way
All six packages move 0.7.2 → 0.8.0.
Status: the release lane is complete; two gate items remain — see Release gate.
What changed
One container for project state
State lived in three root dot-directories (.rex/, .hench/, .sourcevision/) and five loose .n-dx* files. 0.8.0 introduces a single .ndx/ container and one resolver, resolveLayout in @n-dx/llm-client, that decides which layout a project is on: a .ndx/ directory selects the new one, its absence the legacy one. An un-migrated project is not misconfigured and nothing warns.
ndx initwrites the.ndx/layout for new projects.ndx migrate-layoutmoves an existing project when the operator chooses: snapshot,git mvthe tracked paths so history follows, move the untracked state, rewrite the.gitignore/.gitattributesblocks, verify — or restore.- The per-user directory becomes
~/.ndx/withNDX_HOMEas the override;~/.n-dx/andN_DX_HOMEare still read as fallbacks. .mcp.jsonstays at the repository root (the vendor CLIs read it there) and task claims stay in the git common directory.
A reorganised dashboard
Views are now stages. Analysis opens on the isometric codebase map, with stat tiles and a collapsible Next Steps panel beneath it; Plan opens on a one-row Smart Add bar; Terrain and Architecture are tabbed sections; Home leads with a next-step panel. Stage pages fit any viewport, phones included.
Scattered settings views were consolidated onto a shared frame with an explicit Save, an unsaved-changes indicator and a leave prompt:
| Page | Replaces |
|---|---|
Robot Wrangler (/robot-wrangler) | LLM Provider |
Workflow (/workflow) | work settings, CLI timeouts, templates |
Project (/project) | analyze/plan settings, feature flags, Notion, integrations |
Robot Wrangler reports what ndx work will actually run — vendor, provider, model, and which setting supplied it — and says why when that combination would be refused. Model fields are dropdowns over a live catalog read from the vendor's models API when a key resolves, with a built-in fallback otherwise.
The breadcrumb links back to the hub and, with two or more projects registered, switches between them. The hub chooser has a stable address at /hub.
Live
A new Live tab watches every running hench run and long job across all worktrees of a repository, including runs started from a terminal. /live/task/:taskId gives a running task its own page: elapsed time, turn, tokens and tokens per second, model and heartbeat, each progress event as it is written, and Copy link, Mark stuck and Stop. A machine strip shows agent slots, free memory against the hub floor, worktree count and spend. The 5-minute stuck-run rule now lives in one place, so the bottom bar, runs health, audit and Live agree.
Security
Loopback is shared by every account on a machine, and a checkout can carry execution config of its own. 0.8.0 addresses both:
- Per-user token.
ndx startcreates<ndx home>/auth.token(owner-only) and the hub, dashboard and preview servers require it on every request and WebSocket handshake — asAuthorization: Bearer,X-Ndx-Token, or thendx_tokencookie the printed URL sets once. HTTP MCP registrations need the header.--no-authorweb.auth: falseturns it off. - Repository trust. Until you accept a checkout's execution config (
ndx trust accept), runs use the default guard — the repository can tighten it but not widen it — andbypassPermissionsis lowered toacceptEdits.ndx initends with a review of what the checkout shipped; unattended inits never trust automatically. The dashboard shows a strip until it is accepted. - Credential redaction. Run records and logs are redacted before they are persisted or shown, and child processes the agent starts get an environment stripped of credential-shaped variables (
guard.env.allow/guard.env.denyadjust it). - The
Hostheader is validated on every hub, dashboard and preview request.
Models
Claude defaults have changed. The standard tier — and the default when no model is configured — is now claude-sonnet-5-5; the heavy tier and the review model are claude-opus-5-5. The opus alias resolves to claude-opus-5-5 and fable to claude-fable-5-1. All three have 1M context and list pricing, so budget preflight, ndx usage and the spend views price them as known.
llm.effort is now actually sent on Claude API requests as output_config.effort; it was parsed but never sent. claude-opus-5-5 defaults to high so the move from Opus 5 keeps its reasoning depth. Effort is never sent to a model that rejects it.
If an older Claude Code release rejects the new model ids on CLI-provider runs, upgrade it or pin the previous model with ndx config llm.claude.model claude-sonnet-5 . (and llm.tiers.claude.heavy / llm.claude.reviewModel for the heavy tier and review).
Per-vendor agent models
hench.model is deprecated and ignored. ndx work resolves its model from --model, then hench.models.<vendor>, then the llm.* fields.
Claude settings resolve per field
The legacy top-level claude.* keys now resolve against llm.claude.* one field at a time, through a single implementation shared by the CLI, the dashboard and the footer. The fallback used to be block-level, so a modern llm.claude block holding one field discarded every legacy field beside it — a project that set claude.api_key once and later pinned llm.claude.model silently lost the key. Writes go to llm.claude.* only; existing claude.* values stay where they are and are still read until 1.0.0.
Command transparency
Every ndx command declares its effects — what it reads and writes, which phases call a model and how often, what network it touches, how long it takes. ndx help --effects --format=json prints the declarations and GET /api/commands/manifest serves them.
Interactive analyze, plan and recommend print a preflight banner from those declarations before the command starts — with a pause the operator can shorten (NDX_PREFLIGHT_PAUSE_MS) or skip (--yes) — and a run summary afterwards: files written, calls, tokens, cost. Cost appears only when it is known; an unpriced model or a provider that reported no usage shows "not recorded" rather than $0.00.
PRD storage
rex tree-diff --json diffs two PRD trees; rex ready marks items ready when they have an automated or metric requirement and no open blocker; items carry an assignee and ndx work --mine respects it. Whole-tree PRD rewrites are refused off the default branch without --allow-on-branch.
New configuration keys
Seven keys are new — absent from the 0.7.2 schema, not merely unlisted:
| Key | What it does |
|---|---|
web.auth | Require the per-user dashboard token on the hub, dashboard and preview servers. On unless set to false. |
hench.models.<vendor> | Agent-only model for claude, codex, google or local. Set in .n-dx.json (.ndx/config.json on the new layout) or from Robot Wrangler, not through hench config. |
hench.guard.env.allow | Credential-shaped environment variables to pass through to child processes anyway. |
hench.guard.env.deny | Additional environment variables to strip from child processes. |
hench.batchMaxAgeHours | How old a batch session may get before it is retired. |
hench.batchMaxIdleHours | How long a batch session may sit idle before it is retired. |
hench.guard.memoryMonitor.spawnThreshold | Memory headroom below which the guard stops spawning. |
hench.model still parses, so existing configs keep loading, but it is ignored.
A further 32 keys became visible without becoming new: hench config listed 21 at 0.7.2 and lists 56 now. The schema already accepted them — they worked if you hand-edited the config file, and were invisible if you did not.
Redirects
Every path merged into a stage stays a registered view and redirects to it. The table lives in packages/web/src/shared/view-routing.ts as VIEW_ALIASES.
| Old path | Redirects to |
|---|---|
overview | analyze |
rex-dashboard | work |
llm-provider | robot-wrangler |
hench-config, cli-timeouts, hench-templates | workflow |
project-settings, feature-toggles, notion-config, integrations | project |
An alias fires only when its target is valid for that viewer: a rex-scoped standalone viewer has no work stage, so rex-dashboard keeps rendering as its own page there rather than redirecting nowhere.
Dependencies
The dependency audit is clean on the release tree — zero findings at every severity. Transitive packages are held at safe floors through pnpm.overrides in the root package.json.
Release gate
- [x] Lane A — A1 through A8 and A6b merged.
- [x] Dashboard navigation and settings — B4 (#456), B5 (#458), B6a (#469), B6b (#482), the breadcrumb work (#471) and the icons (#506) merged.
- [x] Documents, navigation contract and wireframe comparison — B7 (#508).
- [ ] The flaky
cichild-cleanup e2e test, deferred until all A and B PRs are in. - [ ] After publish: confirm one git tag and one GitHub release per package.
Verified for this note
Measured on the merged tree at #508, not carried forward from an earlier draft:
- 120 changesets, 0 problems — every one scoped, every one with a real body; 177
patchentries and 6minor. changeset statuscomputes to minor for all six packages.- The redirect table is read from
VIEW_ALIASES, and the new-key list is a schema diff against the@n-dx/core@0.7.2tag — neither from changeset prose.
