* feat(release): publish package source, declaration maps, and documentation Every release member publishes its TypeScript source and the declaration maps that resolve into it, and @deepseek-ai/dsh publishes the repository Markdown documentation staged from docs/ at prepack time. The ./src/* export most members already declared now resolves for an installed consumer, and a consumer editor follows a declaration to the implementation. Bundled JavaScript maps stay unpublished; the vendored family and the Desktop runtime file policy are unchanged. Rationale: .agents/notes/implemented/process/2026-10-08-published-source-and-docs.md * feat(release): publish JavaScript maps and compress bundles Every emitted JavaScript map ships beside the bundle it describes, and the workspace build and the client preset compress bundles without mangling identifiers. The documentation payload now mirrors the website publication manifest and is removed again by `postpack`; Desktop and the Python executable exclude the published source, documentation, and maps; `clean` removes a staged copy. Typert's publication contract gains the Remote declaration map. * fix(release): keep node bundles readable for the worker image The browser worker image lowers `yield*` only as a whole statement and rewrites `for await` loops by their source layout, so compressed node-side entries either fail that lowering or lower to unparseable code. Only the browser bundles keep compression, which removes about a third of their text. The bundle-purity assertion now matches the module-loader call regardless of the quote style compression picks, and the release-pack fixture exercises the installed package's new documentation requirement. * feat(release): publish the whole documentation tree `@deepseek-ai/dsh` copies `docs/` in full instead of the website's page set: the maintainer documents, the generated migration records, the translation guidelines, and the `*.i18n.yaml` consistency records ship with the installed package, so the documentation's own links resolve without a checkout. * feat(release): publish the upgrade guides with the documentation The staged documentation keeps the website's page set and adds every `docs/upgrade-guide/` document, which is what an installed reader consults when a released change breaks something. The rest of the maintainer tree stays out. * test(release): expect source and maps in master's new payload cases * feat(release): keep installed docs and source readable in Desktop Desktop keeps the published src/ and docs/ trees inside app.asar, and every model shell call receives DSH_INSTALL_DIR and DSH_NODE_EXECUTABLE so an agent can read them through Electron's Node mode. Staging also generates docs/upgrade-guide/README.md, an index of the upgrade guides grouped by the release they upgrade from. Minified client bundles print string literals with backticks: the worker image packer now recognizes those chunk requests, client license banners are prepended after minification so their text survives, and the affected artifact tests accept either quote. * test(desktop): read archived docs through the Windows PowerShell form Regenerate the config catalog for the shifted shell-env source line. * test(desktop): wait for the GUI-subsystem Electron process from PowerShell * build(release): publish source and maps from the message-quotes package * build(release): publish source and maps from packages new on master * build(release): publish source and maps from the tool-office package
description, kind
| description | kind |
|---|---|
| Settings domain base plugin: shared configuration forms, schema service, and the canonical settings slot-type contract for the dsh web client. | package-reference |
@deepseek-ai/dsh-client-ui-settings
English | 中文
Summary
This package lets web-client features expose editable preferences backed by the Host settings document without implementing their own transport or schema handling. Each feature gets namespace-scoped reads and writes, atomic multi-field updates, schema validation, and protection against silently overwriting concurrent changes. It also provides the standard extension points for settings chrome, pages, header actions, plugin tabs, and onboarding while rendering no interface itself. Any preference-owning feature can use it without depending on a presentation package; a separate package provides the settings shell.
Table of Contents
- Use this package
- Understand the implementation
- Further Exploration
- Model Experience
- Known Limitations and Deferred Work
- Dev Note
Use this package
Feature plugins use this package to store and edit their preferences without re-implementing transport or schema handling. Mount it once per composition; it injects the remote service with its settings namespace and owns the single settings.describe reader in the browser.
Configuration forms
ctx.configForms.developerTools owns the Coding Tools switch and the shared Web and desktop preference ui-settings.enabled, defaulting to true. Its enabled observable publishes accepted choices and setEnabled uses the same ordered settings writes. Desktop and every authenticated Web browser persist to the Host document. This controls presentation and HTML preview permissions, not Host authorization or Session recording. Host-backed clients keep developer features disabled until the first accepted schema-resolved value arrives; missing or failed initial responses do not enable them. Later refreshes retain the last accepted choice.
Feature adapters use ctx.configForms.get(entryId) to obtain accepted values and a write queue shared by every editor of that Host entry. Snapshots contain resolved value, inherited base, raw user, revision, and writability. set and unset submit one operation; mutate submits one atomic operation list. Staged editors pass the revision read before editing; conflicts preserve their drafts. Unsetting removes the override and restores inheritance.
A configuration form persists through the Host settings service for every authenticated browser; the authenticated-browser Host preferences note owns that policy. settings.describe.writable is the authority on whether a write is accepted.
Following served namespaces
A page that edits a namespace another plugin owns registers through ctx.configForms.whileServed(namespaces, register): register runs once any listed namespace is in the shared mirror, receives the set of namespaces the Host serves, and returns the registration's disposer, which runs when none of them is served any more or when the disposer whileServed returns runs. The caller owns that returned disposer and wraps it in ctx.effect; unlike get, the service registers nothing on the caller's context. A deployment that never composed the owner therefore shows no trace of the page, and a namespace the Host stops serving withdraws it. The four official pages on the Plugins page ride it, one companion package each.
Filling the settings slots
A settings surface registers into the slot types this package declares. The shell (sidebar.settings occupant, navigation, chrome) lives in ui-settings-general; feature pages register settings.section contributions; the Plugins section hosts settings.plugins.tab pages; onboarding steps register settings.onboarding. Cross-namespace surfaces (schema introspection, the served-namespace directory, hasDocument) read the same mirror through ctx.configForms.describe().
To customize a page's navigation icon, use ctx.slots.inject('settings.section.icon', ...) and register an icon component with the same id as its settings.section contribution. Unmatched ids never render, and the icon's label option is not displayed. The component receives size in pixels and active; the shell owns the button, label, and decorative icon wrapper. Without a matching icon registration, the shell renders its default glyph. Disposing the icon contribution restores that glyph.
Observable success and failures
A committed write folds its answer into the shared mirror. Refused writes refresh the latest Host values. Browser validation uses the serialized Config schema; the Host validates complete configuration, including checks that cannot be serialized.
Understand the implementation
The optional settings.launcher contribution receives sidebar geometry, whether the open Settings panel covers the sidebar, the settings navigation callbacks, and the effective Settings key labels and accessible combination. The shell omits shortcut presentation for an unbound command and retains its plain Settings trigger when no launcher is registered.
Implementation internals — click to expand
The package realizes one ownership rule: the browser keeps one shared mirror of the settings document, and every derived surface reads that single source, so any moment in time shows the same document revision.
The describe mirror
The Host Config of the ui-settings entry declares the default-on enabled preference. The Client plugin injects remote with its settings namespace and owns the one settings.describe reader in the browser: a shared mirror refreshed on every forwarded settings/document-updated event and on connection/reset (the first connection included, closing the window where a commit lands between the eager read and the SSE subscription). Cross-namespace surfaces read it through ctx.configForms.describe(), a read/fold face (getSnapshot/subscribe/ensure, plus acceptView folding a write answer in).
Shared entry writes
The provider owns one controller per Host entry, including its subscription and write queue; repeated get(entryId) calls return the same form. Consumers release their own view subscriptions. No caller-scoped configuration binding is created. The startup RPC budget covers the shared describe reader.
Schema service
ctx.settingsSchema rehydrates schemas, validates drafts, and edits nested values. Invalid wire values do not replace accepted values.
Further Exploration
These pages cover the settings surface family and the durable seam behind it.
- ui-settings-general — the settings shell: trigger chrome, navigation, General section, onboarding projection.
- ui-settings-plugins — the Built-in plugins section shell around the inventory tab.
- ui-settings-shell, ui-settings-agent-loop, ui-settings-subagent, ui-settings-web-search — the official configuration pages on the Plugins page, each following its namespaces through
whileServed. - ui-settings-models — the Models page and DeepSeek onboarding over this base.
- settings — the durable user-settings seam and its file provider.
- ui-sidebar — the sidebar shell whose bottom seat hosts the settings trigger.
Model Experience
None, as the package is a browser-side UI plugin layer that registers nothing model-facing.
KV Cache effect
None; this package neither assembles nor sends a provider request.
Known Limitations and Deferred Work
These limits define the settings transport's reach and who shares a settings document; they are current package constraints.
- Host preferences are shared across authenticated entries — browsers accessing the same settings document share its persisted preferences, rather than retaining per-browser choices.
Dev Note
Working context for maintainers — click to expand
None.