2026-07-22 10:55:17 +08:00
|
|
|
{
|
|
|
|
|
"name": "@deepseek-ai/dsh",
|
2026-08-06 04:40:32 +08:00
|
|
|
"description": "dsh CLI: profile boot, plugin management, and the browser UI alias",
|
2026-07-22 10:55:17 +08:00
|
|
|
"version": "0.0.1",
|
|
|
|
|
"private": true,
|
|
|
|
|
"type": "module",
|
|
|
|
|
"bin": {
|
|
|
|
|
"dsh": "lib/bin.js"
|
|
|
|
|
},
|
|
|
|
|
"files": [
|
2026-08-03 23:04:56 +08:00
|
|
|
"lib/*.js",
|
2026-08-04 22:06:32 +08:00
|
|
|
"config"
|
2026-07-22 10:55:17 +08:00
|
|
|
],
|
|
|
|
|
"license": "BSD-3-Clause",
|
|
|
|
|
"dependencies": {
|
2026-07-29 14:05:58 +08:00
|
|
|
"@cordisjs/plugin-hmr": "workspace:*",
|
2026-07-25 01:19:47 +08:00
|
|
|
"@cordisjs/plugin-include": "workspace:*",
|
|
|
|
|
"@cordisjs/plugin-loader": "workspace:*",
|
|
|
|
|
"@cordisjs/plugin-timer": "workspace:*",
|
2026-07-22 10:55:20 +08:00
|
|
|
"@deepseek-ai/dsh-app-boot": "workspace:^",
|
2026-08-06 04:40:32 +08:00
|
|
|
"@deepseek-ai/dsh-base": "workspace:^",
|
|
|
|
|
"@deepseek-ai/dsh-headless": "workspace:^",
|
2026-07-31 01:57:19 -07:00
|
|
|
"@deepseek-ai/dsh-mcp-client": "workspace:^",
|
2026-07-22 20:45:24 +08:00
|
|
|
"@deepseek-ai/dsh-paths": "workspace:^",
|
2026-07-31 14:28:52 +08:00
|
|
|
"@deepseek-ai/dsh-pty": "workspace:^",
|
|
|
|
|
"@deepseek-ai/dsh-pty-local": "workspace:^",
|
2026-08-06 09:27:44 +08:00
|
|
|
"@deepseek-ai/dsh-session-reference": "workspace:^",
|
|
|
|
|
"@deepseek-ai/dsh-tmux-context": "workspace:^",
|
|
|
|
|
"@deepseek-ai/dsh-tool-ask-user": "workspace:^",
|
2026-07-31 14:28:52 +08:00
|
|
|
"@deepseek-ai/dsh-tool-bash-persistent": "workspace:^",
|
2026-07-30 20:25:13 +08:00
|
|
|
"@deepseek-ai/dsh-tool-cordis": "workspace:^",
|
2026-08-06 04:40:32 +08:00
|
|
|
"@deepseek-ai/dsh-web-app": "workspace:^",
|
2026-07-25 12:02:28 +08:00
|
|
|
"commander": "^15.0.0",
|
2026-07-25 01:19:47 +08:00
|
|
|
"cordis": "^4.0.0-rc.7",
|
2026-08-03 23:04:45 +08:00
|
|
|
"js-yaml": "^4.2.0",
|
|
|
|
|
"node-addon-require-builtin": "^0.1.4"
|
2026-07-25 01:19:47 +08:00
|
|
|
},
|
|
|
|
|
"devDependencies": {
|
2026-08-06 04:40:32 +08:00
|
|
|
"@deepseek-ai/dsh-frontend-static": "workspace:^",
|
|
|
|
|
"@deepseek-ai/dsh-host-apiproxy": "workspace:^",
|
|
|
|
|
"@deepseek-ai/dsh-host-webserver": "workspace:^",
|
|
|
|
|
"@deepseek-ai/dsh-loader-smoke": "workspace:^",
|
feat(agent-presets): make the default preset a user setting
`config.default` becomes the composition base of an `agent-presets` settings
namespace, so the user document layers over the deployment's engineering
default and a person can change which preset new sessions get without a
restart.
The value is read per resolution rather than snapshotted: a hot-reloaded
document takes effect on the next session created, and every running session
stays on the preset it was composed from — which is the same rule the
session-header guard enforces from the other side.
`resolve()` read `config.default` directly, which would have made the whole
setting inert; it now goes through `defaultId` like every other caller.
The write-protection test is rewritten against a temp profile root. It was
passing vacuously: the un-overridden Loader REWRITES the composition it read —
stamping `disabled: true` onto the self-disposing row — so the committed
fixture had been mutated by the very run that proved the bug, and every later
run compared against the damaged file and passed. Building the preset in a
temp directory makes the assertion immune to its own failure mode, and it now
fails with a visible `+ disabled: true` when the override is removed.
Review follow-ups on this layer. The exported schema is
`AgentPresetSettingsSchema`, symmetric with the `AgentPresetSettings`
interface it resolves and self-describing at an import site. The `session.create`
JSDoc promised "the deployment's default preset" for an omitted `agentPreset`,
which this layer makes false — it now names the effective default. The
constructor records why it does not use `installSettingsSection`: that helper
re-judges what a consumer DERIVED across attach and detach, and nothing here is
derived. The provider-unload test disposes the fiber `ctx.plugin()` handed back
instead of reaching into `ctx.reflect.store`, and the write-protection wait says
why slack is the right shape for an absence assertion.
The real composition covers the layering too. `apps/cli` boots the shipped
`cordis.yml`, stores `agent-presets.default`, and asserts an unnamed session
composes from it — the package suite proves the layering against a hand-built
context, this proves the roster and the settings provider are wired to each
other. That test also pins the settings row at a temp file: it defaulted to
`$DSH_HOME/settings.yaml`, so a developer's own stored default decided the
outcome of a file whose whole point is that only the shipped root does.
The Agent Note records the per-resolution read and its correspondence with the
session header, and the vacuous-test finding above.
2026-08-04 00:07:11 +08:00
|
|
|
"@deepseek-ai/dsh-settings": "workspace:^",
|
2026-08-06 04:40:32 +08:00
|
|
|
"@deepseek-ai/dsh-system-prompt": "workspace:^",
|
|
|
|
|
"@deepseek-ai/dsh-tools": "workspace:^",
|
refactor(cli)!: one shared base config with per-surface overlays
`dsh` shipped two config trees that were 43 rows the same: apps/cli/cordis.yml
composed web as 74 flat rows, while the TUI booted examples/tui-agent/cordis.yml
whose single `@deepseek-ai/dsh-tui-demo` row mounted twelve plugins behind a
twenty-key pass-through Config. Neither file was what its location claimed —
apps/cli hardcoded the "example" as the product default and the "demo" bundle
was the application — and every capability change had to be made twice.
- apps/cli/base.cordis.yml holds the 43 shared rows; tui.cordis.yml and
web.cordis.yml are patch lists stating only what differs per surface
- overlays apply as SIBLING patch lists at one include level, because include
patches never cross an include boundary. Precedence: base < surface <
(--config | personal ~/.dsh/config.yaml) < launcher flag/profile patches
- `--config` now applies an overlay INSTEAD OF the personal one, so a demo or
test tree never inherits the user's route; new `--config-replace` boots a file
as the entire tree (the old `--config` behaviour). Both survive /resume
- vendor/include: index each `insert`ed row as it is added so a later patch can
configure or disable it. Upstream built the id index once before the patch
loop, leaving every surface-only row — the whole TUI front door — silently
unpatchable from user config. Logged as local modification 8
- session identity moves to dsh-agent-loop's CONFIGURED_AGENT_IDENTITIES_KEY;
dsh-tui's MAIN_SESSION_ID_KEY is deleted (only the bundle read it)
- delete examples/tui-agent, examples/cordis-agent, packages/examples/tui-demo;
TUI tests → apps/cli/tests, cordis e2e → packages/cordis/tool-cordis/tests,
examples/code-mode survives as an overlay leaf
- `dsh web` gains --config, threaded into AppCLIEntry as an extra overlay
Three latent defects surfaced and are fixed here: the TUI captured the optional
sessionQuery service once at construction and could permanently disable /resume
when it won the mount race; the session-store root silently reverted to a
project-local ./.sessions; --config-replace was dropped by the resume handoff.
Verified by booting each tree through the real Loader (TUI 55 entries, web 75,
zero unsettled) rather than reading YAML. All eight terminal snapshots replay
byte-identically; 14/14 PTY smoke, 112/112 snapshots, 25/25 doc-sync, hygiene
and lint clean.
2026-07-29 13:58:21 +08:00
|
|
|
"@types/js-yaml": "^4.0.9",
|
2026-08-04 10:07:17 +08:00
|
|
|
"execa": "^10.0.0"
|
2026-07-22 10:55:17 +08:00
|
|
|
}
|
|
|
|
|
}
|