@deepseek-ai/dsh-plugin-manager 0.2.1-alpha.1 → 0.2.1-alpha.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.i18n.yaml +10 -10
- package/README.md +14 -7
- package/README.zh.md +15 -8
- package/lib/index.js +585 -292
- package/lib/typert.host.js +407 -242
- package/lib/typert.remote-client.d.ts +16 -2
- package/lib/typert.remote-client.js +390 -234
- package/lib/types/build-approval.d.ts +14 -2
- package/lib/types/build-approval.js +35 -5
- package/lib/types/index.d.ts +22 -2
- package/lib/types/index.js +172 -62
- package/lib/types/official-install-target.d.ts +15 -0
- package/lib/types/official-install-target.js +54 -0
- package/lib/types/operations.d.ts +1 -0
- package/lib/types/operations.js +320 -255
- package/lib/types/patch.d.ts +12 -3
- package/lib/types/patch.js +47 -9
- package/lib/types/tools.js +70 -8
- package/lib/types/types.d.ts +24 -3
- package/locale/en.json +5 -0
- package/locale/tools/en.json +5 -0
- package/locale/tools/zh.json +5 -0
- package/locale/zh.json +6 -0
- package/package.json +40 -36
package/README.i18n.yaml
CHANGED
|
@@ -15,8 +15,8 @@
|
|
|
15
15
|
en: 87679c51aa3693f5
|
|
16
16
|
zh: 11684a48a5806afb
|
|
17
17
|
/deepseek-ai-dsh-plugin-manager/use-this-package:
|
|
18
|
-
en:
|
|
19
|
-
zh:
|
|
18
|
+
en: 95c1b18f8432090a
|
|
19
|
+
zh: 213e54a1547a1da1
|
|
20
20
|
/deepseek-ai-dsh-plugin-manager/use-this-package/version-compatibility-and-exemptions:
|
|
21
21
|
en: 920c0acb3b9feaf3
|
|
22
22
|
zh: ba6e832a256880a7
|
|
@@ -24,8 +24,8 @@
|
|
|
24
24
|
en: d5643a06f300c30a
|
|
25
25
|
zh: 9348b6a7676a2849
|
|
26
26
|
/deepseek-ai-dsh-plugin-manager/understand-the-implementation:
|
|
27
|
-
en:
|
|
28
|
-
zh:
|
|
27
|
+
en: 495dadf79c48c43c
|
|
28
|
+
zh: 9884dd04a5bb49dc
|
|
29
29
|
/deepseek-ai-dsh-plugin-manager/further-exploration:
|
|
30
30
|
en: c6538243d8702a0d
|
|
31
31
|
zh: 04a82d923353c75f
|
|
@@ -36,8 +36,8 @@
|
|
|
36
36
|
en: 1815ec6ce56c80d4
|
|
37
37
|
zh: 2d7ac75d3b25eb6b
|
|
38
38
|
/deepseek-ai-dsh-plugin-manager/model-experience/management-tool/what-the-model-sees:
|
|
39
|
-
en:
|
|
40
|
-
zh:
|
|
39
|
+
en: b1dae91f98350290
|
|
40
|
+
zh: 802ae86d923ac6ce
|
|
41
41
|
/deepseek-ai-dsh-plugin-manager/model-experience/management-tool/token-effect:
|
|
42
42
|
en: bc70208bd361dbcd
|
|
43
43
|
zh: bb651d6066066c6c
|
|
@@ -45,11 +45,11 @@
|
|
|
45
45
|
en: c29f60be7f3edc1a
|
|
46
46
|
zh: d9b9388b96ef95cc
|
|
47
47
|
/deepseek-ai-dsh-plugin-manager/known-limitations-and-deferred-work:
|
|
48
|
-
en:
|
|
49
|
-
zh:
|
|
48
|
+
en: 6b93fd9851b79a0e
|
|
49
|
+
zh: d2cf1982e8cfc718
|
|
50
50
|
/deepseek-ai-dsh-plugin-manager/known-limitations-and-deferred-work/failure-behavior:
|
|
51
|
-
en:
|
|
52
|
-
zh:
|
|
51
|
+
en: c670eb2330b441e8
|
|
52
|
+
zh: 2c8223e03e1e3ef0
|
|
53
53
|
/deepseek-ai-dsh-plugin-manager/known-limitations-and-deferred-work/dev-note:
|
|
54
54
|
en: e67f633dc6fe7773
|
|
55
55
|
zh: 3bb0c20c93f16f98
|
package/README.md
CHANGED
|
@@ -37,14 +37,20 @@ For a deployment without agent presets, enable the tool in the profile patch. Pr
|
|
|
37
37
|
disabled: false
|
|
38
38
|
```
|
|
39
39
|
|
|
40
|
-
A plugin toggle updates only `disabled` in the last matching override in the profile's `cordis.patch.yml`, or appends an override when none matches. Matching uses the entry id and any module-name assertion. A bundle toggle changes `package.json`'s ordered `dsh.profile.bundles` list. Disabling retains the dependency; enabling appends the bundle at the end, which can change configuration precedence. Installation enables a new bundle by default. Home and invocation patches retain their higher priority.
|
|
40
|
+
A plugin toggle updates only `disabled` in the last matching override in the profile's `cordis.patch.yml`, or appends an override when none matches. Matching uses the entry id and any module-name assertion. An override holding only `id` and `disabled` is removed, and none is appended, when the bundle layers and the remaining profile patches already give the entry the requested state, so the profile patch records only departures from the bundles. Home and invocation patches are left out of that comparison; they apply after the profile patch and do not decide what it records. A bundle toggle changes `package.json`'s ordered `dsh.profile.bundles` list. Disabling retains the dependency; enabling appends the bundle at the end, which can change configuration precedence. Installation enables a new bundle by default. Home and invocation patches retain their higher priority.
|
|
41
41
|
|
|
42
42
|
A selected bundle that cannot load remains in `listBundles` with an `error`; `enabled` records the saved selection, not successful loading. The plugin page shows the error and allows deselection. A broken bundle cannot be enabled. Management bundles remain protected if their files become unreadable.
|
|
43
43
|
|
|
44
44
|
`listBundles` includes optional display `meta` for each bundle and its declared plugin rows, including disabled bundles. The Client selects a language from these values. The separate `description` field is the bundle's raw `package.json.description`; a metadata diagnostic does not block management. `source` gives a profile dependency as a spec `pnpm add` accepts: a git address or URL as recorded without the user information of an http(s) URL (a query string stays as recorded), a `file:` or `link:` path made absolute against the profile or the home directory for `~`, and a registry range, tag, or alias after the package name, as is any spec of a package installed under another name; a bundle the installation supplies has none, even when the profile also depends on it, because the installation's copy is the one that loads. The `plugin_manager` tool omits UI display metadata from list results.
|
|
45
45
|
|
|
46
|
+
`listBundles` marks shipped optional bundles and on-demand catalog entries as `official`, independently of package installation. `availability` identifies a readable installation-provided or profile package, or `missing`; on-demand catalog entries exclude undeclared transitive copies. `installed` only records whether the profile declares the dependency. An absent on-demand entry carries embedded localized metadata and a host-derived `installTarget` containing the running DSH version and install spec, without registry access. Profile-declared packages with unreadable files retain their declaration and expose the normal error.
|
|
47
|
+
|
|
46
48
|
`inspect(spec, options)` reads what a spec names before anything installs: a registry name is asked of the registry through `pnpm view`, run in the profile directory so the same proxy and authentication settings apply as to the install; an absolute path has its `package.json` read; a git address or tarball answers only its form and the `host` it is fetched from. The answer carries the name, version, description, whether the package declares a bundle, and the `registry` that answered, or a `problem`: `invalid-spec`, `already-installed`, `not-found`, `not-a-package`, `not-a-bundle`, `network`, or `unknown`, with the `registries` asked. A caller's `signal` or `inspectTimeoutMs` ends the lookup.
|
|
47
49
|
|
|
50
|
+
Published installations offer `package@<running DSH version>`. Source Web and development Desktop offer `link:<absolute workspace package directory>` from the running CLI installation, including its development symlink. Package names resolve through workspace manifests; current working directory and prerelease suffixes do not select a checkout. Missing packages, bundle patches, or built entry points produce a diagnostic without registry fallback. Prepare the checkout with `pnpm install` and `pnpm run build`. Linked packages use that checkout’s dependencies and peers; rebuilding and restarting remain necessary after code changes. A registry copy or another checkout’s link can need replacement even when its version matches.
|
|
51
|
+
|
|
52
|
+
Official on-demand installs call the same `installBundle` operation as other bundles. Registry targets use `saveExact: true`; development targets retain the ordinary `link:` dependency. An explicit update removes the installed package and installs the target with the current `enabled` selection; without HMR, a bundle that runs since startup cannot be removed, so the installation goes over it and reports `restart-required`. A failed or cancelled installation after the removal leaves the package uninstalled, and the reinstalled bundle joins the end of the selection. Turning Off only deselects the layer, and Remove uses the existing removal checks. Installation failure restores the profile manifest and lockfile; activation failure after installation can retain the saved dependency and selection. The existing peer-compatibility check still applies, without an additional Official-only version admission rule.
|
|
53
|
+
|
|
48
54
|
`installBundle` checks GitHub repositories with `git ls-remote` before starting pnpm, using the profile directory and the installer's Git and proxy configuration. `githubConnectionTimeoutMs` defaults to 5000 ms and limits only this check, not package download or builds. The check disables credential helpers and prompts; only network failures and timeouts stop installation, reporting `failedAt: 'spec-host'` with the existing failure kind and diagnostic log. Authentication, repository lookup and other failures are left to pnpm, including its HTTPS-to-SSH fallback. Cancellation and manager disposal stop the check and its descendants. Registry packages, paths, tarballs and other Git hosts skip this check. A reachable repository can still fail during download or bundle validation.
|
|
49
55
|
|
|
50
56
|
Registries are asked in turn. The plan starts at `options.registry`, else the configured `registry` (`null` is the one pnpm's own configuration names), and continues through `fallbackRegistries` while a registry is unreachable, times out, or answers that it has no such package or version, which a mirror not yet synced does. A registry outside the configured set is asked alone, so a private registry never falls through to a public one; pnpm's own registry counts as part of the set only while what it names, read through `pnpm config get registry` before each plan, is npm's own registry or one of the fallbacks, and is otherwise asked alone as a private one. A registry pnpm's own configuration already names is asked once. The lookup runs `pnpm view` with `--registry` and without pnpm's own retries, so a dead registry is reported within `inspectTimeoutMs` and the next one is asked; pnpm prints its refusal as JSON on stdout, which is read like stderr. The install keeps pnpm's retry settings. `registries()` answers the configured set and what pnpm names, for a picker. The [registry Agent Note](../../../.agents/notes/implemented/architecture/2026-09-18-plugin-install-registries.md) owns the rationale.
|
|
@@ -55,7 +61,7 @@ The browser-safe `@deepseek-ai/dsh-plugin-manager/registry` entry exports `OFFIC
|
|
|
55
61
|
|
|
56
62
|
`waitForInstall(requestId)` lets a client recover a lost response by waiting for the active installation, including its non-cancellable application phase. It returns the same outcome as the original call, or `null` if the request is not active. Completed results are not retained; `null` establishes neither success nor cancellation.
|
|
57
63
|
|
|
58
|
-
When pnpm 11 blocks dependency scripts, the failed installation reports every pending package name in the profile under `pendingBuilds`, including names left by earlier attempts; a failed run restores `package.json` and `pnpm-lock.yaml` but deliberately not `pnpm-workspace.yaml
|
|
64
|
+
When pnpm 11 blocks dependency scripts, the failed installation reports every pending package name in the profile under `pendingBuilds`, including names left by earlier attempts and names the run reported as ignored. pnpm writes those entries into `pnpm-workspace.yaml` only when it can prompt, so the manager records the reported names itself; a failed run restores `package.json` and `pnpm-lock.yaml` but deliberately not `pnpm-workspace.yaml`. The Web plugin page offers **Allow these scripts and retry**; the tool can grant permission on the user's behalf through `approvedBuilds` on `install_bundle`, after the user approves those scripts in the conversation. The service validates pending names; it does not verify conversation approval. Approval persists by package name in this profile, permits commands with the host user's permissions, and survives another installation failure. Only currently undecided names can be approved; existing denials and wildcard rules cannot be overridden through this action. Approval rejects YAML anchors or aliases inside `allowBuilds`. Retry preserves the original activation choice.
|
|
59
65
|
|
|
60
66
|
<a id="version-compatibility-and-exemptions"></a>
|
|
61
67
|
### Version compatibility and exemptions
|
|
@@ -91,9 +97,9 @@ The CLI exposes `dsh plugin --profile <profile> version-exemptions`, `allow-vers
|
|
|
91
97
|
|
|
92
98
|
The service and `dsh plugin` share the package operations in [operations.ts](src/operations.ts). The launcher supplies the current profile; [DSH HMR](../hmr/README.md) serializes module reloads, file watching and management writes. Each configuration refresh re-reads bundle selection and patch layers, updates the original root Include, and awaits removed plugin resources as well as the remaining Loader tree. CLI and service operations share the profile manifest writer lock to prevent concurrent package and manifest writes. HMR does not acquire that lock. Pnpm runs outside the HMR queue; installation selects the bundle after pnpm succeeds, while removal deselects and unloads the bundle before pnpm runs.
|
|
93
99
|
|
|
94
|
-
|
|
100
|
+
Without HMR, installing a new package, enabling a bundle and a successful removal publish the profile's runtime resolution; with HMR, every operation leaves publication to [HMR](../hmr/README.md)'s recomposition, which removes dropped mappings after their plugins stop. Shared dependencies may pass to another bundle's declaration when their normalized directory and scope stay unchanged. Without HMR, a deselected startup bundle still runs: while any such bundle is absent from the saved selection, subsequent package operations retain the entire current table and report `restart-required`. Other new installations and removals of non-running bundles can still publish without HMR; activation waits for restart. With HMR, `installBundle()` refuses a package that is already installed with `already-installed`, before pnpm runs, when the spec names it: a registry name, a local directory, or the git or tarball spec its dependency was saved with. A package that cannot be removed, such as a bundle carrying plugin management, therefore cannot be installed over with HMR. Installing another version is a removal and an installation, so the previous version's plugins stop, its modules are evicted and its mappings removed before the new one is installed; the Web page's Update for an Official plugin does both. A git or tarball spec whose package is known only after pnpm ran can still install over an installed package: without HMR it reports `restart-required`, and with HMR the recomposition replaces the running plugins whose loaded files changed. A replacement that fails to import or start reports `failed` with the activation diagnostic, which names the import error; the previous version no longer runs, and every later operation imports it again, so it starts once its files or dependencies are corrected. An unchanged import failure is a warning of later operations; a changed one fails them. A publication the runtime resolution rejects, because an installed package now resolves to another directory or a mapping of the DSH installation changed, leaves the composition as it was, after stopping and starting again the rows it would drop, and reports `restart-required` with `package-moved`. Disabling or removing a bundle evicts the modules of the packages whose mappings it drops. Every `restart-required` result carries `restartReason`: `no-hmr`, `package-moved`, or the [HMR pending reason](../hmr/README.md) of a changed module that loads only after a restart, unless the operation reports `overridden` ([decision](../../../.agents/notes/implemented/architecture/2026-09-30-profile-package-refresh-and-manifest-invalidation.md)).
|
|
95
101
|
|
|
96
|
-
A service run whose captured output stays silent for `idleTimeoutMs` is terminated, reports `timedOut` alongside its exit status, is classified `timeout` whatever status the signal left behind, and is not retried on the next registry, which bounds how long one operation can hold the profile lock; the CLI inherits the terminal, captures no output, and stays unbounded for its operator to interrupt. A run completes when its process exits, and the pipes then drain under a bounded grace period, so a descendant that inherited them cannot hold the operation open. A terminated run stops its whole process tree and waits for it, because a lifecycle script outlives the pnpm process that started it (issue #4981). Each operation records the pnpm run it starts in `.plugin-manager/run.json` and removes the record when the run ends. A lock whose holder process exited is taken over by the next writer, but that process's pnpm tree can still be running, so an operation that finds a record waits up to five seconds for the recorded run to stop and otherwise fails with a diagnostic that names the process and the record, without running pnpm. Dependency-only changes do not trigger configuration reloads.
|
|
102
|
+
A service run whose captured output stays silent for `idleTimeoutMs` is terminated, reports `timedOut` alongside its exit status, is classified `timeout` whatever status the signal left behind, and is not retried on the next registry, which bounds how long one operation can hold the profile lock; the CLI inherits the terminal, captures no output, and stays unbounded for its operator to interrupt. A run completes when its process exits, and the pipes then drain under a bounded grace period, so a descendant that inherited them cannot hold the operation open. The diagnostic file is closed before the call settles, including preparation or spawn failures. A terminated run stops its whole process tree and waits for it, because a lifecycle script outlives the pnpm process that started it (issue #4981). Each operation records the pnpm run it starts in `.plugin-manager/run.json` and removes the record when the run ends. A lock whose holder process exited is taken over by the next writer, but that process's pnpm tree can still be running, so an operation that finds a record waits up to five seconds for the recorded run to stop and otherwise fails with a diagnostic that names the process and the record, without running pnpm. Dependency-only changes do not trigger configuration reloads.
|
|
97
103
|
|
|
98
104
|
Results contain the last attempted stage, target, saved-state change, application status and error codes. Web dictionaries render management text; pnpm and Loader diagnostics remain unmodified. Unrelated pre-existing inactive entries return warnings; new or changed failures and inactive explicit enablement targets fail the operation. A failed or cancelled package run, or failed bundle validation, restores the manifest and lockfile snapshotted before pnpm ran ([rationale](../../../.agents/notes/implemented/architecture/2026-09-15-guided-plugin-installation.md)); later failures retain saved changes as described in [Failure behavior](#failure-behavior). Installations are tracked by request id until their call settles, so a cancellation names one run and joins its settlement without taking the profile lock. The CLI inherits authentication variables and terminal descriptors; service operations use a scrubbed environment and captured output.
|
|
99
105
|
|
|
@@ -116,7 +122,7 @@ Results contain the last attempted stage, target, saved-state change, applicatio
|
|
|
116
122
|
|
|
117
123
|
#### What the model sees
|
|
118
124
|
|
|
119
|
-
The [`plugin_manager` tool](../../../docs/tool-catalog.md#deepseek-aidsh-plugin-manager) lists plugin entries and bundles and performs profile-wide changes. Its results include saved-state changes, application status and package diagnostics. Management operations do not inject messages into Agents.
|
|
125
|
+
The [`plugin_manager` tool](../../../docs/tool-catalog.md#deepseek-aidsh-plugin-manager) lists plugin entries and bundles and performs profile-wide changes. Its results include saved-state changes, application status and package diagnostics. A change result that is not plainly applied adds `nextStep`, a sentence derived from its application status, refusal code, package-manager failure kind or restart reason that says what the model does next or tells the user. Management operations do not inject messages into Agents.
|
|
120
126
|
|
|
121
127
|
#### Token effect
|
|
122
128
|
|
|
@@ -131,7 +137,8 @@ Tool results append to the transcript. Enabling or disabling other tools can cha
|
|
|
131
137
|
<a id="known-limitations-and-deferred-work"></a>
|
|
132
138
|
|
|
133
139
|
- Web approves the entire displayed pending group; it has no per-package selection.
|
|
134
|
-
-
|
|
140
|
+
- pnpm verifies every lockfile tarball URL against its default registry when a command changes the lockfile. After a package was installed from another registry, installing a different package with the default registry, or removing that package after a restart, can fail with `ERR_PNPM_TARBALL_URL_MISMATCH`.
|
|
141
|
+
- Package replacements require restarting the process without HMR. A package relinked outside Plugin Manager while it is still installed waits for a restart.
|
|
135
142
|
- Startup-only profiles cannot remove packages used to start the current process; stop it and use `dsh plugin`.
|
|
136
143
|
- The manager cannot disable its own management components, change another profile, or edit an agent preset's composition.
|
|
137
144
|
- A failed removal may leave dependencies partially changed, and a failed or cancelled installation can leave downloaded files under `node_modules` or the pnpm store. Inactive dependencies with missing files remain removable. Diagnostic logs remain under the profile's `.plugin-manager/logs` directory.
|
|
@@ -150,7 +157,7 @@ Failures preserve completed steps and report the actual remaining state. Profile
|
|
|
150
157
|
| Resolution publication after a successful package operation fails | Keep completed disk changes and the previous runtime table. Report `application: 'failed'` with the publication diagnostic; pnpm's zero exit code does not mean publication succeeded. |
|
|
151
158
|
| Remove: any step fails | Stop at the failed step. Preserve completed changes, retain remaining dependencies for retry, and report removal failure. Do not re-enable the bundle. |
|
|
152
159
|
|
|
153
|
-
Installation finishes after pnpm and bundle validation succeed; subsequent publication or enablement failure does not undo installation. Removal proceeds in order: remove the bundle from `dsh.profile.bundles`, unload its runtime contributions, run `pnpm remove`, then publish runtime resolution unless a deselected startup bundle still runs without HMR. A failed step prevents subsequent steps; publication failure after removal does not restore deleted packages. A selected name that neither the profile's dependencies nor the installation holds, such as a retired bundle, is also removable; its removal stops after deselection and runs no pnpm.
|
|
160
|
+
Installation finishes after pnpm and bundle validation succeed; subsequent publication or enablement failure does not undo installation. Removal proceeds in order: remove the bundle from `dsh.profile.bundles`, unload its runtime contributions, run `pnpm remove`, then publish runtime resolution unless a deselected startup bundle still runs without HMR. `pnpm remove` runs with the registry this manager last installed the package from in the running process, because pnpm verifies lockfile tarball URLs against its default registry; a package installed before the process started is removed with the registry an installation asks first. A failed step prevents subsequent steps; publication failure after removal does not restore deleted packages. A selected name that neither the profile's dependencies nor the installation holds, such as a retired bundle, is also removable; its removal stops after deselection and runs no pnpm.
|
|
154
161
|
|
|
155
162
|
Restoration rewrites only the two snapshotted files; user-authored patch configuration, application data, diagnostic logs and files pnpm downloaded remain untouched, and the next package operation prunes packages no manifest references.
|
|
156
163
|
|
package/README.zh.md
CHANGED
|
@@ -28,7 +28,7 @@ kind: "package-reference"
|
|
|
28
28
|
<a id="use-this-package"></a>
|
|
29
29
|
## 使用本包
|
|
30
30
|
|
|
31
|
-
基于 base 的 profile 提供管理服务。在 Web 中,侧边栏的**插件**页([ui-plugin-manager](../../client/ui-plugin-manager/README.zh.md))管理 profile 的组合包及其能唯一定位的行;设置页的插件列表保持只读。Agent 预设条目保持只读。`plugin_manager` 工具提供相同操作,在 Creator
|
|
31
|
+
基于 base 的 profile 提供管理服务。在 Web 中,侧边栏的**插件**页([ui-plugin-manager](../../client/ui-plugin-manager/README.zh.md))管理 profile 的组合包及其能唯一定位的行;设置页的插件列表保持只读。Agent 预设条目保持只读。`plugin_manager` 工具提供相同操作,在 Creator 模式中启用。其他预设仍默认禁用。每个工具操作都要求 `danger-full-access` 或本次调用的批准。在较低沙箱模式下,`ask` 会请求审批;`never`、拒绝、取消或审批渠道不可用时均不执行。批准不改变会话的权限模式。profile 变更跨会话持久化,已安装的 Host 代码在宿主进程内运行,不受工作区沙箱限制。依赖构建脚本仍需单独批准。
|
|
32
32
|
|
|
33
33
|
未使用 Agent 预设的部署在 profile patch 中启用工具;使用预设的会话由其预设中的 `tool-plugin-manager` 条目控制。
|
|
34
34
|
|
|
@@ -37,14 +37,20 @@ kind: "package-reference"
|
|
|
37
37
|
disabled: false
|
|
38
38
|
```
|
|
39
39
|
|
|
40
|
-
插件开关只更新 profile 的 `cordis.patch.yml` 中最后一条匹配覆盖项的 `disabled`;没有匹配项时追加。匹配依据是条目 id
|
|
40
|
+
插件开关只更新 profile 的 `cordis.patch.yml` 中最后一条匹配覆盖项的 `disabled`;没有匹配项时追加。匹配依据是条目 id,以及覆盖项声明的模块名称。如果组合包层和其余 profile patch 已使条目处于所请求的状态,仅含 `id` 与 `disabled` 的覆盖项会被移除,也不会追加覆盖项,因此 profile patch 只记录与组合包不同的设置。该比较不计入 home 和单次启动 patch;它们在 profile patch 之后应用,不决定 profile patch 记录什么。组合包开关修改 `package.json` 的有序 `dsh.profile.bundles` 列表。关闭保留依赖;开启追加到列表末尾,可能改变配置优先级。安装新组合包默认启用。home 和单次启动 patch 保留更高优先级。
|
|
41
41
|
|
|
42
42
|
已选择但无法加载的组合包仍会出现在 `listBundles` 中,并携带 `error`;`enabled` 表示保存的选择,不代表加载成功。插件页面显示错误并允许取消选择。损坏的组合包无法启用。管理组合包的文件变得不可读后仍受保护。
|
|
43
43
|
|
|
44
44
|
`listBundles` 为各组合包及其声明的插件行提供可选的展示 `meta`,包括已禁用的组合包。Client 从这些值中选择语言。单独的 `description` 字段是该组合包原始的 `package.json.description`;元信息诊断不会阻止管理操作。`source` 以 `pnpm add` 接受的 spec 给出 profile 依赖:git 地址或 URL 按记录给出,但去掉 http(s) URL 的 user information(查询字符串保持原样);`file:` 或 `link:` 路径按 profile 目录解析为绝对路径,`~` 展开为主目录;注册表版本范围、标签或别名接在包名的 `@` 之后,以别名安装的包的 spec 也是如此。安装提供的组合包没有该字段,即使 profile 也依赖它,因为实际加载的是安装中的副本。`plugin_manager` 工具的列表结果不包含 UI 展示元信息。
|
|
45
45
|
|
|
46
|
+
`listBundles` 将随附可选组合包和按需目录项标为 `official`,与包的安装状态独立。`availability` 表示可读取的安装随附包、profile 包,或 `missing`;按需目录项不计入未声明的传递依赖副本。`installed` 仅表示 profile 是否声明该依赖。尚未安装的按需条目携带内嵌的本地化元信息,以及 Host 生成、包含当前 DSH 版本与安装 spec 的 `installTarget`,无需访问注册表。profile 已声明但文件不可读的包保留依赖声明,并展示原有错误。
|
|
47
|
+
|
|
46
48
|
`inspect(spec, options)` 在任何东西安装之前读出 spec 指向什么:注册表包名通过 `pnpm view` 询问注册表,在 profile 目录中运行,因而与安装使用同样的代理与认证设置;绝对路径读取其 `package.json`;git 地址或 tarball 只答复自己的形式和它被拉取的 `host`。答复携带名称、版本、描述、该包是否声明组合包,以及作答的 `registry`,否则给出 `problem`:`invalid-spec`、`already-installed`、`not-found`、`not-a-package`、`not-a-bundle`、`network` 或 `unknown`,并附上问过的 `registries`。调用方的 `signal` 或 `inspectTimeoutMs` 会结束查询。
|
|
47
49
|
|
|
50
|
+
已发布的安装提供 `package@<当前 DSH 版本>`。源码 Web 与开发 Desktop 提供 `link:<工作区包的绝对目录>`,目录来自当前 CLI 的安装位置,包括其开发符号链接。包名通过工作区清单解析;当前工作目录和预发布版本后缀不用于选择 checkout。包、bundle patch 或已构建入口缺失时报告诊断,不回退到注册表。使用 `pnpm install` 和 `pnpm run build` 准备 checkout。链接包使用该 checkout 的依赖与 peer;代码改变后仍需重新构建并重启。即使版本相同,注册表副本或其他 checkout 的链接也可能需要替换。
|
|
51
|
+
|
|
52
|
+
官方按需安装调用和其他组合包相同的 `installBundle` 操作。注册表目标使用 `saveExact: true`;开发目标保留普通 `link:` 依赖。显式更新先删除已安装的包,再以当前 `enabled` 选择状态安装目标;没有 HMR 时,自启动起运行的组合包无法删除,因此安装直接覆盖它并报告 `restart-required`。删除之后安装失败或被取消时,该包保持未安装,重新安装的组合包排在选择列表末尾。关闭仅取消选择配置层,移除使用原有移除检查。安装失败恢复 profile 清单和锁文件;安装成功后激活失败可能保留已保存的依赖和选择。原有 peer 兼容性检查继续生效,不增加仅针对官方条目的版本准入规则。
|
|
53
|
+
|
|
48
54
|
`installBundle` 在启动 pnpm 前通过 `git ls-remote` 检查 GitHub 仓库,使用 profile 目录及安装器的 Git 与代理配置。`githubConnectionTimeoutMs` 默认为 5000 毫秒,只限制这次检查,不限制包下载或构建。检查禁用凭据助手和认证提示;只有网络失败与超时会停止安装,通过现有失败类型与诊断日志返回,并标记 `failedAt: 'spec-host'`。认证、仓库查找及其他失败继续交给 pnpm,包括其 HTTPS 到 SSH 的回退。取消安装或销毁管理器会停止检查及其子进程。注册表包、本地路径、压缩包和其他 Git 主机跳过此检查。仓库可达后,下载或组合包验证仍可能失败。
|
|
49
55
|
|
|
50
56
|
注册表按顺序询问。计划从 `options.registry` 开始,否则从配置的 `registry`(`null` 即 pnpm 自身配置指定的那个)开始,并在一个注册表不可达、超时或答复没有这个包或版本(尚未同步的镜像会如此)时继续问 `fallbackRegistries`。配置集合之外的注册表只问它自己,因而私有源永远不会落到公共源;pnpm 自身的注册表只在它指向的地址(每次做计划前经 `pnpm config get registry` 读出)是 npm 官方源或某个备选源时才算集合成员,否则视为私有源只问它自己。pnpm 自身配置已经指向的注册表只问一次。查询以 `--registry` 运行 `pnpm view` 且不带 pnpm 自身的重试,所以死掉的注册表会在 `inspectTimeoutMs` 内报告并转问下一个;pnpm 把拒绝以 JSON 打印在 stdout,读法与 stderr 相同。安装保留 pnpm 的重试设置。`registries()` 把配置集合和 pnpm 指向的地址答复给选择器。[注册表 Agent Note](../../../.agents/notes/implemented/architecture/2026-09-18-plugin-install-registries.zh.md) 拥有理由。
|
|
@@ -55,7 +61,7 @@ kind: "package-reference"
|
|
|
55
61
|
|
|
56
62
|
`waitForInstall(requestId)` 让客户端在响应丢失后等待活动安装的结果,包括不可取消的应用阶段。它返回与原调用相同的结果,请求不在活动中时返回 `null`。已完成的结果不保留;`null` 不表示成功或已取消。
|
|
57
63
|
|
|
58
|
-
pnpm 11 拦下依赖脚本时,失败的安装在 `pendingBuilds` 里报告 profile
|
|
64
|
+
pnpm 11 拦下依赖脚本时,失败的安装在 `pendingBuilds` 里报告 profile 中所有待决定的包名,包括先前尝试留下的,以及本次运行报告为已忽略的。pnpm 只在能够交互提示时才把这些条目写入 `pnpm-workspace.yaml`,因此由管理器自行记录本次运行报告的包名;失败的运行会恢复 `package.json` 与 `pnpm-lock.yaml`,但有意不恢复 `pnpm-workspace.yaml`。Web 插件页提供**允许这些脚本并重试**;工具可以在用户于对话中批准这些脚本后,通过 `install_bundle` 的 `approvedBuilds` 代为授权。服务只校验待决定的名字,不核实对话中的批准。授权按包名保存在当前 profile,允许以宿主用户的权限执行命令,并在再次安装失败后保留。只能批准当前未决定的名字;已有的拒绝与通配规则不能通过此操作覆盖。`allowBuilds` 里出现 YAML 锚点或别名时拒绝授权。重试保留原来的启用选择。
|
|
59
65
|
|
|
60
66
|
<a id="version-compatibility-and-exemptions"></a>
|
|
61
67
|
### 版本兼容性与豁免
|
|
@@ -91,9 +97,9 @@ CLI 提供 `dsh plugin --profile <profile> version-exemptions`、`allow-version
|
|
|
91
97
|
|
|
92
98
|
服务与 `dsh plugin` 共用 [operations.ts](src/operations.ts) 中的包管理操作。启动器提供当前 profile;[DSH HMR](../hmr/README.zh.md) 串行执行模块重载、文件监听和管理写入。每次配置刷新重新读取组合包选择与 patch 层,更新原有根 Include,并等待已移除插件释放资源及剩余 Loader 树稳定。CLI 与 service 操作共用 profile manifest 写锁,防止并发包操作和 manifest 写入。HMR 不获取该锁。pnpm 在 HMR 队列之外执行;安装在 pnpm 成功后选入组合包,删除则在执行 pnpm 前取消选入并完成卸载。
|
|
93
99
|
|
|
94
|
-
|
|
100
|
+
没有 HMR 时,安装新包、启用组合包以及删除成功后,都会发布 profile 的 runtime resolution;有 HMR 时,每个操作都把发布交给 [HMR](../hmr/README.zh.md) 的重新组合,该重新组合在相关插件停止后移除被丢弃的映射。共享依赖的规范化目录和作用域不变时,可以改由另一个组合包声明。没有 HMR 时,已取消选入的启动组合包仍在运行:只要保存的选择列表中缺少任何这样的组合包,后续包操作就保留整张当前表,并报告 `restart-required`。其他新安装和未运行组合包的删除仍可在没有 HMR 时发布;激活等待重启。有 HMR 时,spec 指明已安装的包,`installBundle()` 在运行 pnpm 之前以 `already-installed` 拒绝安装;spec 可以是 registry 包名、本地目录,或保存依赖时使用的 git 或 tarball spec。因此,有 HMR 时无法在不能删除的包(例如带有插件管理的组合包)上安装。安装另一个版本需要先卸载再安装,因此在安装新版本之前,旧版本的插件停止,其模块被逐出,其映射被移除;Web 页面中官方插件的更新会依次执行这两步。运行 pnpm 之后才能确定包名的 git 或 tarball spec 仍可能安装到已安装的包上:没有 HMR 时报告 `restart-required`;有 HMR 时,重新组合替换已加载文件发生变化的运行中插件。替换版本导入或启动失败时报告 `failed` 及激活诊断,该诊断给出导入错误;旧版本不再运行,此后每次操作都会再次导入它,因此其文件或依赖被修正后它即启动。未变化的导入失败在后续操作中作为警告报告;已变化的导入失败使后续操作失败。已安装的包现在解析到其他目录,或 DSH 安装的映射发生变化,使 runtime resolution 拒绝发布时,它停止并重新启动该发布将丢弃的行,组合保持不变,并报告带 `package-moved` 的 `restart-required`。停用或删除组合包时,会逐出因此被删除映射的那些包的模块。每个 `restart-required` 结果都带有 `restartReason`:`no-hmr`、`package-moved`,或只有重启后才能加载的已变化模块的 [HMR 待处理原因](../hmr/README.zh.md),除非操作报告 `overridden`([决策](../../../.agents/notes/implemented/architecture/2026-09-30-profile-package-refresh-and-manifest-invalidation.zh.md))。
|
|
95
101
|
|
|
96
|
-
service 运行若在 `idleTimeoutMs` 内没有任何捕获输出即被终止,与退出状态一并报告 `timedOut`,不论信号留下什么退出状态都归类为 `timeout`,且不再转问下一个注册表,因此单次操作占用 profile 锁的时长有上界;CLI
|
|
102
|
+
service 运行若在 `idleTimeoutMs` 内没有任何捕获输出即被终止,与退出状态一并报告 `timedOut`,不论信号留下什么退出状态都归类为 `timeout`,且不再转问下一个注册表,因此单次操作占用 profile 锁的时长有上界;CLI 继承终端、不捕获输出,因此不受此上界约束,由操作者中断。运行以进程退出为完成点,随后只在一个有界的宽限窗口内排空管道,因此继承管道的孙进程无法让操作挂起。诊断文件会在调用结束前关闭,包括准备或创建进程失败的情况。被终止的运行会停止整棵进程树并等待其消失,因为生命周期脚本的存活时间超过启动它的 pnpm 进程(issue #4981)。每个操作把它启动的 pnpm 运行记录在 `.plugin-manager/run.json` 中,并在运行结束时删除该记录。持有者进程已退出的锁会被下一个写入方接管,但该进程的 pnpm 进程树可能仍在运行,因此发现记录的操作最多等待五秒让记录中的运行停止,否则不运行 pnpm,并以指明该进程与记录文件的诊断失败。仅依赖字段变化不会触发配置重载。
|
|
97
103
|
|
|
98
104
|
结果包含最后尝试的阶段、目标、磁盘变化、应用状态和错误码。Web 词典呈现管理文案;pnpm 与 Loader 的诊断保持原样。无关的已有故障作为警告返回;新出现、配置变化后的故障,以及显式启用目标未激活,都会使操作失败。包管理运行失败或被取消,或组合包校验失败时,会恢复 pnpm 运行前快照的 manifest 与 lockfile([理由](../../../.agents/notes/implemented/architecture/2026-09-15-guided-plugin-installation.zh.md));后续失败按[失败行为](#failure-behavior)所述保留已保存的改动。安装按 request id 跟踪到调用结束,因此取消只针对一次运行,并且不取 profile 锁就能等待它结束。CLI 继承认证环境和终端描述符;service 使用清理后的环境并捕获输出。管理器直接读取文件和 Loader 状态,不维护第二份目标状态注册表,因此不发布单独的运行时不变式伴生入口。
|
|
99
105
|
|
|
@@ -116,7 +122,7 @@ service 运行若在 `idleTimeoutMs` 内没有任何捕获输出即被终止,
|
|
|
116
122
|
|
|
117
123
|
#### 模型看到什么
|
|
118
124
|
|
|
119
|
-
[`plugin_manager` 工具](../../../docs/tool-catalog.zh.md#deepseek-aidsh-plugin-manager) 列出插件条目和组合包,并执行影响整个 profile
|
|
125
|
+
[`plugin_manager` 工具](../../../docs/tool-catalog.zh.md#deepseek-aidsh-plugin-manager) 列出插件条目和组合包,并执行影响整个 profile 的改动。结果包含保存状态变化、应用状态和包管理诊断。未直接应用的变更结果会增加 `nextStep`,这是一句根据应用状态、拒绝代码、包管理器失败类型或重启原因生成的说明,指出模型下一步做什么或告诉用户什么。管理操作不会向 Agent 注入消息。
|
|
120
126
|
|
|
121
127
|
#### Token 影响
|
|
122
128
|
|
|
@@ -131,7 +137,8 @@ service 运行若在 `idleTimeoutMs` 内没有任何捕获输出即被终止,
|
|
|
131
137
|
<a id="known-limitations-and-deferred-work"></a>
|
|
132
138
|
|
|
133
139
|
- Web 一次批准显示出来的整组待决定包,没有逐包选择。
|
|
134
|
-
-
|
|
140
|
+
- 命令改动锁文件时,pnpm 按默认注册表校验锁文件中的每个 tarball URL。某个包从其他注册表安装后,使用默认注册表安装另一个包,或在重启后删除该包,可能以 `ERR_PNPM_TARBALL_URL_MISMATCH` 失败。
|
|
141
|
+
- 没有 HMR 时,替换包需要重启进程。在 Plugin Manager 之外重新链接仍处于安装状态的包,需要等待重启。
|
|
135
142
|
- 仅启动时加载的 profile 不能删除当前进程启动时使用的包;停止进程后使用 `dsh plugin`。
|
|
136
143
|
- 管理器不能关闭自身所需的管理组件、修改其他 profile 或编辑 agent 预设组合。
|
|
137
144
|
- 失败的删除可能留下部分依赖改动,失败或被取消的安装可能在 `node_modules` 或 pnpm 缓存中留下已下载文件。文件缺失的未启用依赖仍可删除。诊断日志保留在 profile 的 `.plugin-manager/logs` 目录中。
|
|
@@ -150,7 +157,7 @@ service 运行若在 `idleTimeoutMs` 内没有任何捕获输出即被终止,
|
|
|
150
157
|
| 包操作成功后解析表发布失败 | 保留已完成的磁盘改动和上一张运行时表。报告 `application: 'failed'` 及发布诊断;pnpm 的零退出码不代表发布成功。 |
|
|
151
158
|
| 卸载:任一步失败 | 停在失败步骤,保留已完成的改动和待重试删除的依赖,报告卸载失败。不重新启用组合包。 |
|
|
152
159
|
|
|
153
|
-
pnpm 执行和组合包校验成功即完成安装,后续发布或启用失败不撤销安装。卸载依次执行:从 `dsh.profile.bundles` 移除组合包、卸载运行时贡献、执行 `pnpm remove`,然后发布 runtime resolution,除非没有 HMR
|
|
160
|
+
pnpm 执行和组合包校验成功即完成安装,后续发布或启用失败不撤销安装。卸载依次执行:从 `dsh.profile.bundles` 移除组合包、卸载运行时贡献、执行 `pnpm remove`,然后发布 runtime resolution,除非没有 HMR 且已取消选入的启动组合包仍在运行。`pnpm remove` 使用本管理器在当前进程中最近一次安装该包时所用的注册表,因为 pnpm 按默认注册表校验锁文件中的 tarball URL;进程启动前安装的包使用安装时首先询问的注册表删除。任一步失败都不继续执行后续步骤;删除后的发布失败不会恢复已删除的包。 profile 依赖和安装都不持有的已选名称(例如已下线的组合包)同样可卸载;其卸载在取消选择后结束,不运行 pnpm。
|
|
154
161
|
|
|
155
162
|
恢复只重写这两份快照文件;用户编写的 patch 配置、应用数据、诊断日志以及 pnpm 已下载的文件保持原样,没有 manifest 引用的包由下一次包操作清理。
|
|
156
163
|
|