@deepseek-ai/dsh-plugin-manager 0.1.6-alpha.2

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/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 DeepSeek
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,6 @@
1
+ # Bilingual-pair consistency record (docs/i18n/README.md): the git blob hash of each
2
+ # side as of the last confirmed-consistent state. Both languages carry equal authority;
3
+ # after editing either side, bring the other along and re-record with:
4
+ # pnpm run verify-translation-pairing --write packages/boot/plugin-manager/README.md
5
+ README.md: 46b5447a8b3548b548bf844e1d753296861b17da
6
+ README.zh.md: d4c285b72f8d31357a12f222d741323e9b4658e6
package/README.md ADDED
@@ -0,0 +1,133 @@
1
+ ---
2
+ description: "Enable profile plugins and install, remove or select bundles from the Web sidebar or an agent."
3
+ kind: "package-reference"
4
+ ---
5
+
6
+ # @deepseek-ai/dsh-plugin-manager
7
+
8
+ English | [中文](README.zh.md)
9
+
10
+ Application-owned profiles supply their bundled package-manager invocation through launcher facts. It takes precedence over `pnpmCommand` for package operations and registry inspection; its environment applies only to those subprocesses.
11
+
12
+ ## Summary
13
+
14
+ Manage the current profile's plugins without editing configuration by hand. Enable or disable individual plugin entries, select installed bundles, and install or remove external bundles. With HMR enabled in YAML, configuration changes apply immediately; without HMR, the running composition remains until restart. Changes affect every session using the profile.
15
+
16
+ ## Table of Contents
17
+
18
+ - [Use this package](#use-this-package)
19
+ - [Understand the implementation](#understand-the-implementation)
20
+ - [Further Exploration](#further-exploration)
21
+ - [Model Experience](#model-experience)
22
+ - [Known Limitations and Deferred Work](#known-limitations-and-deferred-work)
23
+ - [Failure behavior](#failure-behavior)
24
+ - [Dev Note](#dev-note)
25
+
26
+ -----
27
+
28
+ <a id="use-this-package"></a>
29
+ ## Use this package
30
+
31
+ Base-backed profiles provide the manager. In Web, the sidebar's **Plugins** page ([ui-plugin-manager](../../client/ui-plugin-manager/README.md)) manages the profile's bundles and their uniquely addressable rows; the Settings Plugin list stays read-only. Agent-preset rows remain read-only. The `plugin_manager` tool exposes the same operations and is enabled in Creator mode. Other presets keep it disabled by default. Every tool action requires `danger-full-access` or approval for that call. Under lower sandbox modes, `ask` requests approval; `never`, rejection, cancellation, or an unavailable approval channel prevents execution. An approval leaves the session permission mode unchanged. Profile changes persist across sessions, and installed Host code executes in-process outside the workspace sandbox. Dependency build-script approval remains separate.
32
+
33
+ For a deployment without agent presets, enable the tool in the profile patch. Preset-backed sessions use their preset’s `tool-plugin-manager` entry.
34
+
35
+ ```yaml
36
+ - id: tool-plugin-manager
37
+ disabled: false
38
+ ```
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.
41
+
42
+ `inspect(spec)` 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 registry and proxy settings apply as to the install; an absolute path has its `package.json` read; a git address or tarball answers only its form. The answer carries the name, version, description, and whether the package declares a bundle, or a `problem`: `invalid-spec`, `already-installed`, `not-found`, `not-a-package`, `not-a-bundle`, `network`, or `unknown`. A caller's `signal` or `inspectTimeoutMs` ends the lookup.
43
+
44
+ `installBundle` accepts a caller-generated `requestId`, under which `plugin-manager/install-log` streams each pnpm run's output and `plugin-manager/install-state` announces `installing`, `cancelling`, and `applying`. `cancelInstall(requestId)` stops the run and answers `cancelled` only after pnpm exited and the files are back, `too-late` once the bundle is being applied, and `not-running` for any other id; the install call then reports `application: 'cancelled'`. A run that fails, is cancelled, or adds a package without a bundle patch restores `package.json` and `pnpm-lock.yaml` as they were; `packageResult.kind` classifies a failed run from its exit and output, and `bundle` names the package a finished run added. `listBundles` carries each bundle's one-liner (the package `description`), the rows its patch declares with their live entries, and the built-in rows it overrides; it lists the profile's own bundles, the bundles the installation supplies, and a selected name without a bundle patch as a `not-bundle` problem, while an unselected plain dependency is left out. A bundle the launcher's `OPTIONAL_BUNDLES` names is `optional`: shipped switched off for the person to turn on, never removable, and selected by no shipped template ([rationale](../../../.agents/notes/implemented/process/2026-09-15-shipped-optional-bundles.md)). Every completed operation emits `plugin-manager/changed`; a patch generation applied outside the manager, by HMR's watcher after a CLI or hand edit, announces nothing, so the page learns of it on its next read.
45
+
46
+ 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`, where pnpm records them. 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.
47
+
48
+ ### Configuration
49
+
50
+ | Field | Default | Meaning |
51
+ |---|---|---|
52
+ | `pnpmCommand` | `pnpm` | The pnpm executable name or path, resolved through `PATH` like the `dsh plugin` command. |
53
+ | `inspectTimeoutMs` | `20000` | Bound on one registry lookup an inspection runs, in milliseconds. |
54
+ | `outputBytes` | `16384` | Maximum pnpm diagnostic bytes returned per operation; the full output remains in the returned log path. |
55
+ | `lockWaitMs` | `120000` | Maximum time in milliseconds to acquire the profile write lock. |
56
+
57
+ -----
58
+
59
+ <a id="understand-the-implementation"></a>
60
+ ## Understand the implementation
61
+
62
+ <details>
63
+ <summary>Implementation internals — click to expand</summary>
64
+
65
+ 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 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. Dependency-only changes do not trigger configuration reloads.
66
+
67
+ 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 installation restores the manifest and lockfile it snapshotted before pnpm ran ([rationale](../../../.agents/notes/implemented/architecture/2026-09-15-guided-plugin-installation.md)); a failed removal retains its partial changes and diagnostics. 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. No invariant companion is published because the manager reads files and Loader state directly and owns no independent state projection.
68
+
69
+ </details>
70
+
71
+ -----
72
+
73
+ <a id="further-exploration"></a>
74
+ ## Further Exploration
75
+
76
+ - [App boot](../app-boot/README.md) — profile layers and startup policy.
77
+ - [Plugin inventory](../../host/plugin-inventory/README.md) — current Loader and preset observations.
78
+ - [Plugin manager page](../../client/ui-plugin-manager/README.md) — the Web sidebar page over this service.
79
+ - [Plugin settings](../../client/ui-settings-plugin-inventory/README.md) — the read-only Web inventory.
80
+
81
+ <a id="model-experience"></a>
82
+ ## Model Experience
83
+
84
+ ### Management tool
85
+
86
+ #### What the model sees
87
+
88
+ 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.
89
+
90
+ #### Token effect
91
+
92
+ The tool declaration is present when its consumer is mounted; each invocation adds its returned inventory or change result.
93
+
94
+ #### KV Cache effect
95
+
96
+ Tool results append to the transcript. Enabling or disabling other tools can change subsequent tool declarations and their cache reuse.
97
+
98
+ ## Known Limitations and Deferred Work
99
+
100
+ <a id="known-limitations-and-deferred-work"></a>
101
+
102
+ - Web approves the entire displayed pending group; it has no per-package selection.
103
+ - Package replacements require restarting the process to load a fresh JavaScript module generation.
104
+ - Startup-only profiles cannot remove packages used to start the current process; stop it and use `dsh plugin`.
105
+ - The manager cannot disable its own management components, change another profile, or edit an agent preset's composition.
106
+ - 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.
107
+ - Management results describe Host activation. Browser synchronization failures appear separately in the Settings plugin list.
108
+ - Desktop package operations remain owned by the Desktop shell.
109
+
110
+ <a id="failure-behavior"></a>
111
+ ### Failure behavior
112
+
113
+ Failures preserve completed steps and report the actual remaining state. Profile dependencies without valid bundle metadata remain visible and removable, with enablement unavailable.
114
+
115
+ | Failed operation | Handling |
116
+ |---|---|
117
+ | Install: pnpm or bundle validation fails | Restore `package.json` and `pnpm-lock.yaml` as snapshotted before pnpm ran; files pnpm downloaded may remain. Report installation failure. |
118
+ | Enable: saving selection or loading fails | Keep the installed dependency and any saved selection. Report enablement failure; allow repair, disablement or removal. |
119
+ | 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. |
120
+
121
+ Installation finishes after pnpm and bundle validation succeed; subsequent enablement failure does not undo installation. Removal proceeds in order: remove the bundle from `dsh.profile.bundles`, unload its runtime contributions, then run `pnpm remove`. A failed step prevents subsequent steps.
122
+
123
+ 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.
124
+
125
+ <a id="dev-note"></a>
126
+ ### Dev Note
127
+
128
+ <details>
129
+ <summary>Working context for maintainers — click to expand</summary>
130
+
131
+ None.
132
+
133
+ </details>
package/README.zh.md ADDED
@@ -0,0 +1,133 @@
1
+ ---
2
+ description: "通过 Web 侧边栏或 agent 启停 profile 插件,并安装、删除或选择组合包。"
3
+ kind: "package-reference"
4
+ ---
5
+
6
+ # @deepseek-ai/dsh-plugin-manager
7
+
8
+ [English](README.md) | 中文
9
+
10
+ 应用拥有的 profile 通过启动器信息提供内置包管理器调用方式。它在包操作和 registry 检查中优先于 `pnpmCommand`;其环境仅应用于这些子进程。
11
+
12
+ ## 概述
13
+
14
+ 管理当前 profile 的插件,无需手动编辑配置。启停单个插件条目、选择已安装的组合包,以及安装或删除外部组合包。在 YAML 中启用 HMR 时,配置变化立即生效;未启用 HMR 时,运行中的组合保留到重启。改动影响使用该 profile 的全部会话。
15
+
16
+ ## 目录
17
+
18
+ - [使用本包](#use-this-package)
19
+ - [理解实现](#understand-the-implementation)
20
+ - [进一步探索](#further-exploration)
21
+ - [模型体验](#model-experience)
22
+ - [已知限制与延期工作](#known-limitations-and-deferred-work)
23
+ - [失败行为](#failure-behavior)
24
+ - [开发备注](#dev-note)
25
+
26
+ -----
27
+
28
+ <a id="use-this-package"></a>
29
+ ## 使用本包
30
+
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
+
33
+ 未使用 Agent 预设的部署在 profile patch 中启用工具;使用预设的会话由其预设中的 `tool-plugin-manager` 条目控制。
34
+
35
+ ```yaml
36
+ - id: tool-plugin-manager
37
+ disabled: false
38
+ ```
39
+
40
+ 插件开关只更新 profile 的 `cordis.patch.yml` 中最后一条匹配覆盖项的 `disabled`;没有匹配项时追加。匹配依据是条目 id,以及覆盖项声明的模块名称。组合包开关修改 `package.json` 的有序 `dsh.profile.bundles` 列表。关闭保留依赖;开启追加到列表末尾,可能改变配置优先级。安装新组合包默认启用。home 和单次启动 patch 保留更高优先级。
41
+
42
+ `inspect(spec)` 在任何东西安装之前读出 spec 指向什么:注册表包名通过 `pnpm view` 询问注册表,在 profile 目录中运行,因而与安装使用同样的注册表与代理设置;绝对路径读取其 `package.json`;git 地址或 tarball 只答复自己的形式。答复携带名称、版本、描述以及该包是否声明组合包,否则给出 `problem`:`invalid-spec`、`already-installed`、`not-found`、`not-a-package`、`not-a-bundle`、`network` 或 `unknown`。调用方的 `signal` 或 `inspectTimeoutMs` 会结束查询。
43
+
44
+ `installBundle` 接受调用方生成的 `requestId`,`plugin-manager/install-log` 在其下流式转发每次 pnpm 运行的输出,`plugin-manager/install-state` 通告 `installing`、`cancelling` 与 `applying`。`cancelInstall(requestId)` 停止运行,只在 pnpm 退出且文件恢复后答复 `cancelled`,组合包已在应用时答复 `too-late`,其他 id 答复 `not-running`;安装调用随后报告 `application: 'cancelled'`。失败、被取消或装入了没有组合包 patch 的包的运行,会把 `package.json` 与 `pnpm-lock.yaml` 恢复原样;`packageResult.kind` 按退出方式与输出对失败运行分类,`bundle` 给出完成的运行新增的包。`listBundles` 携带每个组合包的一句话简介(包的 `description`)、其 patch 声明的行及其存活条目,以及它覆盖的内置行;它列出 profile 自己的组合包、安装提供的组合包,以及被选中却没有组合包 patch 的名字(作为 `not-bundle` 问题),未选中的普通依赖不列出。启动器的 `OPTIONAL_BUNDLES` 点名的组合包是 `optional`:随安装提供、默认关闭、由用户开启,永不可卸载,也不被任何随附模板选中([理由](../../../.agents/notes/implemented/process/2026-09-15-shipped-optional-bundles.zh.md))。每个完成的操作都会发出 `plugin-manager/changed`;在管理器之外应用的一代 patch(HMR 监视到 CLI 或手工编辑后)不发通知,页面要到下一次读取才知道。
45
+
46
+ pnpm 11 拦下依赖脚本时,失败的安装在 `pendingBuilds` 里报告 profile 中所有待决定的包名,包括先前尝试留下的;失败的运行会恢复 `package.json` 与 `pnpm-lock.yaml`,但有意不恢复 pnpm 记录这些名字的 `pnpm-workspace.yaml`。Web 插件页提供**允许这些脚本并重试**;工具可以在用户于对话中批准这些脚本后,通过 `install_bundle` 的 `approvedBuilds` 代为授权。服务只校验待决定的名字,不核实对话中的批准。授权按包名保存在当前 profile,允许以宿主用户的权限执行命令,并在再次安装失败后保留。只能批准当前未决定的名字;已有的拒绝与通配规则不能通过此操作覆盖。`allowBuilds` 里出现 YAML 锚点或别名时拒绝授权。重试保留原来的启用选择。
47
+
48
+ ### 配置
49
+
50
+ | 字段 | 默认值 | 含义 |
51
+ |---|---|---|
52
+ | `pnpmCommand` | `pnpm` | pnpm 可执行文件名或路径,与 `dsh plugin` 命令一样通过 `PATH` 解析。 |
53
+ | `inspectTimeoutMs` | `20000` | 单次检查所做注册表查询的上限,单位毫秒。 |
54
+ | `outputBytes` | `16384` | 每次操作返回的 pnpm 诊断字节上限;完整输出保留在返回的日志路径中。 |
55
+ | `lockWaitMs` | `120000` | 获取 profile 写锁的最长等待毫秒数。 |
56
+
57
+ -----
58
+
59
+ <a id="understand-the-implementation"></a>
60
+ ## 理解实现
61
+
62
+ <details>
63
+ <summary>实现细节——点击展开</summary>
64
+
65
+ 服务与 `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 前取消选入并完成卸载。仅依赖字段变化不会触发配置重载。
66
+
67
+ 结果包含最后尝试的阶段、目标、磁盘变化、应用状态和错误码。Web 词典呈现管理文案;pnpm 与 Loader 的诊断保持原样。无关的已有故障作为警告返回;新出现、配置变化后的故障,以及显式启用目标未激活,都会使操作失败。失败或被取消的安装会恢复 pnpm 运行前快照的 manifest 与 lockfile([理由](../../../.agents/notes/implemented/architecture/2026-09-15-guided-plugin-installation.zh.md));失败的删除保留部分改动和诊断。安装按 request id 跟踪到调用结束,因此取消只针对一次运行,并且不取 profile 锁就能等待它结束。CLI 继承认证环境和终端描述符;service 使用清理后的环境并捕获输出。管理器直接读取文件和 Loader 状态,不维护第二份目标状态注册表,因此不发布单独的运行时不变式伴生入口。
68
+
69
+ </details>
70
+
71
+ -----
72
+
73
+ <a id="further-exploration"></a>
74
+ ## 进一步探索
75
+
76
+ - [App boot](../app-boot/README.zh.md)——profile 配置层与启动策略。
77
+ - [Plugin inventory](../../host/plugin-inventory/README.zh.md)——当前 Loader 和预设状态。
78
+ - [插件管理页](../../client/ui-plugin-manager/README.zh.md)——基于本服务的 Web 侧边栏页面。
79
+ - [Plugin settings](../../client/ui-settings-plugin-inventory/README.zh.md)——只读的 Web 清单。
80
+
81
+ <a id="model-experience"></a>
82
+ ## 模型体验
83
+
84
+ ### 管理工具
85
+
86
+ #### 模型看到什么
87
+
88
+ [`plugin_manager` 工具](../../../docs/tool-catalog.zh.md#deepseek-aidsh-plugin-manager) 列出插件条目和组合包,并执行影响整个 profile 的改动。结果包含保存状态变化、应用状态和包管理诊断。管理操作不会向 Agent 注入消息。
89
+
90
+ #### Token 影响
91
+
92
+ 装配工具消费者时提供工具声明;每次调用追加返回的清单或改动结果。
93
+
94
+ #### KV Cache 影响
95
+
96
+ 工具结果追加到对话中。启停其他工具可能改变后续工具声明及其缓存复用。
97
+
98
+ ## 已知限制与延期工作
99
+
100
+ <a id="known-limitations-and-deferred-work"></a>
101
+
102
+ - Web 一次批准显示出来的整组待决定包,没有逐包选择。
103
+ - 替换已有包后需要重启进程,以加载新的 JavaScript 模块版本。
104
+ - 仅启动时加载的 profile 不能删除当前进程启动时使用的包;停止进程后使用 `dsh plugin`。
105
+ - 管理器不能关闭自身所需的管理组件、修改其他 profile 或编辑 agent 预设组合。
106
+ - 失败的删除可能留下部分依赖改动,失败或被取消的安装可能在 `node_modules` 或 pnpm 缓存中留下已下载文件。文件缺失的未启用依赖仍可删除。诊断日志保留在 profile 的 `.plugin-manager/logs` 目录中。
107
+ - 管理结果描述 Host 激活状态。浏览器同步失败会在设置的插件列表中单独显示。
108
+ - Desktop 包管理操作仍由 Desktop shell 负责。
109
+
110
+ <a id="failure-behavior"></a>
111
+ ### 失败行为
112
+
113
+ 失败保留已完成步骤,并报告实际残留状态。没有有效组合包声明的 profile 依赖仍可见、可删除,但不能启用。
114
+
115
+ | 失败操作 | 处理方式 |
116
+ |---|---|
117
+ | 安装:pnpm 执行或组合包校验失败 | 恢复 pnpm 运行前快照的 `package.json` 与 `pnpm-lock.yaml`;pnpm 已下载的文件可能保留。报告安装失败。 |
118
+ | 启用:保存选择项或加载失败 | 保留已安装的依赖和已保存的选择项。报告启用失败,允许修正、停用或卸载。 |
119
+ | 卸载:任一步失败 | 停在失败步骤,保留已完成的改动和待重试删除的依赖,报告卸载失败。不重新启用组合包。 |
120
+
121
+ pnpm 执行和组合包校验成功即完成安装,后续启用失败不撤销安装。卸载依次执行:从 `dsh.profile.bundles` 移除组合包、卸载运行时贡献、执行 `pnpm remove`。任一步失败都不继续执行后续步骤。
122
+
123
+ 恢复只重写这两份快照文件;用户编写的 patch 配置、应用数据、诊断日志以及 pnpm 已下载的文件保持原样,没有 manifest 引用的包由下一次包操作清理。
124
+
125
+ <a id="dev-note"></a>
126
+ ### 开发备注
127
+
128
+ <details>
129
+ <summary>维护者的工作上下文——点击展开</summary>
130
+
131
+ 无。
132
+
133
+ </details>