fix(extension): 收紧插件密钥与命令清单边界
This commit is contained in:
@@ -1,6 +1,6 @@
|
||||
# Plugin Command 与 Settings 开发说明
|
||||
|
||||
> 更新日期:2026-09-02。本文记录第二阶段阶段 D 已实现的 Plugin Command Contribution、Plugin Settings Contribution、Secret 边界和前端 Service Contract。当前回归基线为后端 103 项测试、前端 29 项测试,TypeScript 类型检查和生产构建通过。
|
||||
> 更新日期:2026-09-02。本文记录第二阶段阶段 D 已实现的 Plugin Command Contribution、Plugin Settings Contribution、Secret 边界和前端 Service Contract。当前回归基线为后端 107 项测试、前端 29 项测试,TypeScript 类型检查和生产构建通过。
|
||||
|
||||
## 1. 阶段目标
|
||||
|
||||
@@ -22,6 +22,7 @@ Plugin 在 `plugin.yaml` 的 `contributes.commands` 与 `contributes.settings_se
|
||||
- `locations`:`command_palette`、`context_menu` 或 `toolbar`;
|
||||
- `when` 与允许传入执行器的 Context 字段;
|
||||
- 参数 JSON Schema、可选权限、受控 handler 和超时。
|
||||
- 可选 `secrets` 字段:只声明当前 Command 允许按需读取的 Secret Setting Key,不暴露给前端 DTO。
|
||||
|
||||
`settings.yaml` 采用递增 `schema_version`,首批字段类型固定为 `string`、`number`、`boolean`、`select`、`secret`。宿主会校验默认值、必填项、数值边界、Select 选项,以及 Secret 不得携带默认明文。
|
||||
|
||||
@@ -43,7 +44,7 @@ Plugin 在 `plugin.yaml` 的 `contributes.commands` 与 `contributes.settings_se
|
||||
|
||||
首批 effect 为 `none`、`notification`、`navigate`、`refresh` 和 `job`。前端不得把 effect 当作任意代码执行。
|
||||
|
||||
Command 审计使用 500 条有界内存队列,仅保留 `command_id`、`plugin_id`、成功/失败状态、耗时、错误码和时间。arguments、正文选区、文件路径、effect 与 Secret 均不进入审计事件。
|
||||
Command 执行器通过受控 Resolver 按需读取 `commands.yaml` 已声明且确实属于当前 Plugin Schema 的 Secret;使用 Secret 的 Plugin 还必须声明并获授 `secrets.use` 权限,读取未声明字段返回 `PLUGIN_SECRET_ACCESS_DENIED`。Secret 不会并入普通 Settings 字典。Command 审计使用 500 条有界内存队列,仅保留 `command_id`、`plugin_id`、成功/失败状态、耗时、错误码和时间。arguments、正文选区、文件路径、effect 与 Secret 均不进入审计事件。
|
||||
|
||||
当前声明式宿主提供安全白名单 handler,后续如允许 MCP Server 承担 Command 逻辑,应增加独立的 MCP Command Target Contract,不能把插件给出的模块路径或 Shell 字符串直接执行。
|
||||
|
||||
@@ -61,7 +62,7 @@ APP_DATA_DIR/plugins/settings.json
|
||||
- 非敏感字段值;
|
||||
- Secret 的确定性引用,例如 `plugin.text-tools.api_key`。
|
||||
|
||||
Secret 写入必须调用专用端点。后端通过 `SecretStr` 接收明文,再交给现有 `EncryptedCredentialStore`;普通 Settings API 只返回 `{ configured: true|false }`,不会返回 Secret 值。卸载 Plugin 时同时删除普通设置命名空间和对应加密凭据。
|
||||
Secret 写入必须调用专用端点。后端通过 `SecretStr` 接收明文,再交给现有 `EncryptedCredentialStore`;普通 Settings API 只返回 `{ configured: true|false }`,不会返回 Secret 值。`plugin.*` 是保留命名空间,通用凭据 API、Provider 配置、Provider 临时测试凭据和 Provider Resolver 均不得访问,防止覆盖、删除或外发 Plugin Secret。卸载 Plugin 时同时删除普通设置命名空间和对应加密凭据。
|
||||
|
||||
开发阶段凭据文件由本机 Fernet Key 加密。桌面端落地后,应由 Tauri Host 将同一引用语义迁移到 Stronghold 或系统 Keychain,HTTP Contract 无需因此改变。
|
||||
|
||||
@@ -102,6 +103,6 @@ pnpm type-check
|
||||
pnpm build
|
||||
```
|
||||
|
||||
阶段 D 测试覆盖注册/注销生命周期、位置过滤、参数与 Context 校验、上下文裁剪、设置影响命令执行、五类设置字段、Schema 版本冲突、Secret 密文与清理、损坏存储、无效贡献文件、OpenAPI 路径和前端 Service 请求格式。
|
||||
阶段 D 测试覆盖注册/注销生命周期、位置过滤、参数与 Context 校验、上下文裁剪、设置影响命令执行、声明式 Secret Resolver 与越权拒绝、Provider/通用凭据命名空间隔离、五类设置字段、Schema 版本冲突、Secret 密文与清理、损坏存储、空 Command 列表等无效贡献文件、OpenAPI 路径和前端 Service 请求格式。
|
||||
|
||||
生产构建仍会报告现有大 Chunk 警告,不影响构建成功;该问题属于前端按路由和 Markdown 依赖拆包的后续性能任务。
|
||||
|
||||
Reference in New Issue
Block a user