docs(plugin-market): clarify enforcement and npm installation identities
This commit is contained in:
1 parent
cecb029374
commit
5fab7d08d4
6 files changed
+42
-30
No files matched your search
@@ -9,8 +9,8 @@
|
||||
en: 549330d38e58af03
|
||||
zh: be91a1cc6d5d5004
|
||||
/agent-note-reuse-ecosystem-declarations/decision:
|
||||
en: b86e80cdb73058b8
|
||||
zh: 8a1143246b38a1d5
|
||||
en: 1d782e8be314bf79
|
||||
zh: 6bfd9e0dcee767a2
|
||||
/agent-note-reuse-ecosystem-declarations/alternatives-considered:
|
||||
en: e323031a81d83039
|
||||
zh: c5bce4f4257b01da
|
||||
|
||||
@@ -10,7 +10,7 @@ Custom declarations can duplicate information that package ecosystems already de
|
||||
|
||||
## Decision
|
||||
|
||||
DSH reuses established ecosystem declarations, formats, and meanings when they satisfy its requirements. Readers use maintained parsers and validators. Catalogs and user interfaces derive their data from the original declarations. A generated projection may omit unused fields or normalize display data, but it preserves the source meaning. The owning package README or generator JSDoc documents the projection rules.
|
||||
Contributors must reuse established ecosystem declarations, formats, and meanings when they satisfy DSH requirements. Reader implementations must use maintained parsers and validators. Catalogs and user interfaces must derive their data from the original declarations. A generated projection may omit unused fields or normalize display data, but it must preserve the source meaning. The owning package README or generator JSDoc documents the projection rules.
|
||||
|
||||
A new field or changed meaning requires a specific unmet requirement and a documented difference from the ecosystem rule. When authors define npm package metadata, they reuse npm's package identity, version and range syntax, and person fields. DSH-specific composition, localized display data, and host enforcement still require explicit DSH rules.
|
||||
|
||||
|
||||
@@ -10,7 +10,7 @@ Status: implemented
|
||||
|
||||
## 决策
|
||||
|
||||
既有生态声明、格式和含义满足需求时,DSH 复用它们。读取方使用持续维护的解析器和校验器。目录与用户界面从原始声明派生数据。生成的投影可以省略未使用的字段,或归一化显示数据,但须保留原始含义。所属包的 README 或生成器的 JSDoc 记录投影规则。
|
||||
既有生态声明、格式和含义满足 DSH 需求时,贡献者必须复用它们。读取器实现必须使用持续维护的解析器和校验器。目录与用户界面必须从原始声明派生数据。生成的投影可以省略未使用的字段,或归一化显示数据,但必须保留原始含义。所属包的 README 或生成器的 JSDoc 记录投影规则。
|
||||
|
||||
新增字段或改变含义时,必须说明尚未满足的具体需求,并记录与生态规则的差异。作者定义 npm 包元数据时,复用 npm 的包身份、版本与范围语法,以及人员字段。DSH 特有的组合、本地化显示数据和宿主约束的强制执行仍须明确的 DSH 规则。
|
||||
|
||||
|
||||
@@ -18,8 +18,8 @@
|
||||
en: 4fac5a9b8261342d
|
||||
zh: f9168a8a4209feab
|
||||
/agent-note-plugin-market-index-format/proposal/plugin-fields:
|
||||
en: f292b64bad6c59e3
|
||||
zh: 2acbeabe99ca4354
|
||||
en: cf572978bea19f5a
|
||||
zh: 80a6d9507c468958
|
||||
/agent-note-plugin-market-index-format/proposal/version-fields:
|
||||
en: 83480978017dbcf7
|
||||
zh: 9a5bb55554f90caa
|
||||
@@ -27,20 +27,20 @@
|
||||
en: c748cdc4d8ce349a
|
||||
zh: 5740fa0d6106e637
|
||||
/agent-note-plugin-market-index-format/proposal/dsh-compatibility:
|
||||
en: 0212a29fac169225
|
||||
zh: 7c0f39e7be7ff502
|
||||
en: a6ae732431422eb7
|
||||
zh: 3750ecdc33f75b79
|
||||
/agent-note-plugin-market-index-format/proposal/generator-obligations:
|
||||
en: 5b6e0defe28f4546
|
||||
zh: 5ee91013aa7d299c
|
||||
en: b7185a5fc36af7d3
|
||||
zh: a6fd69988607c324
|
||||
/agent-note-plugin-market-index-format/proposal/reader-rules:
|
||||
en: 6e569aa9aa00078a
|
||||
zh: f9db9f0063f0689d
|
||||
en: 7eb0df505ef26cde
|
||||
zh: dfe1f56554489c0f
|
||||
/agent-note-plugin-market-index-format/alternatives-considered:
|
||||
en: 001d2d67f4f725cb
|
||||
zh: 5a0adbc3d1397eed
|
||||
/agent-note-plugin-market-index-format/acceptance-criteria:
|
||||
en: 3767130fe3b88801
|
||||
zh: bdd530b7aca75206
|
||||
en: 4ffec806e7a8445e
|
||||
zh: a68fee8a99f185db
|
||||
/agent-note-plugin-market-index-format/risks:
|
||||
en: 0f60dad7891f7589
|
||||
zh: 9f0ebb72d3aafba4
|
||||
en: 19f22cc4a00b97e8
|
||||
zh: 585eea737ad6af40
|
||||
@@ -113,9 +113,9 @@ Category, label, and sort-key ids are non-empty strings. Readers look ids up as
|
||||
|---|---|---|
|
||||
| `name` | yes | Package name accepted by npm's maintained package-name validator for new packages; unique within the index. |
|
||||
| `title` | no | `LocalizedText`; a reader displays `name` when absent. |
|
||||
| `description` | no | `LocalizedText` for catalog display, derived from locale metadata and the npm description. |
|
||||
| `description` | no | `LocalizedText` for catalog display; see Generator obligations for its derivation. |
|
||||
| `icon` | no | Either `data:<type>;base64,<payload>`, where `<type>` is `image/svg+xml`, `image/png`, `image/jpeg`, or `image/webp`, `<payload>` is canonically padded base64, and the decoded payload is at most 256 KiB; or a URL reference whose resolution against the index URL is an `https:` URL or has the index URL's origin. |
|
||||
| `author` | no | Display name containing a non-whitespace character, projected from the npm author declaration; see Generator obligations. |
|
||||
| `author` | no | Display name containing a non-whitespace character; see Generator obligations for the npm author projection. |
|
||||
| `homepage` | no | Absolute `https:` or `http:` URL of a page about the plugin. |
|
||||
| `metadata` | no | Object holding the three values below. |
|
||||
| `metadata.category` | no | One declared category id. |
|
||||
@@ -153,6 +153,10 @@ A client installs one version with exactly these pnpm arguments:
|
||||
|
||||
An index carries the manifest's `peerDependencies` and `engines` as separate declarations. DSH tests every `@deepseek-ai/dsh` and `@deepseek-ai/dsh-*` peer against the running DSH version. A declared `engines.dsh` adds a host requirement; it does not replace those peers. The version is compatible only when every applicable requirement matches. Missing declarations add no requirement.
|
||||
|
||||
This preserves the existing [app-boot peer check](../../../../packages/boot/app-boot/src/plugin-compatibility.ts), which receives the running DSH version explicitly. Peer declarations do not identify that process; npm's package resolution in a profile remains separate from DSH's check against its running runtime.
|
||||
|
||||
Implementing this proposal extends that evaluator with `engines.dsh` enforcement and engine-aware exemptions. The current evaluator checks peers only. The index reader and installation must both use the extended evaluator before this format is deployed.
|
||||
|
||||
The index reader and installation use one DSH compatibility evaluator with npm's `node-semver` parser and `includePrerelease: true`. Empty or invalid DSH ranges are incompatible. The existing peer rule maps `workspace:*`, `workspace:^`, and `workspace:~` to the running DSH version; other `workspace:` peer ranges are incompatible. Engine ranges do not use that peer mapping. Exact local `name@version` exemptions apply to both kinds of DSH requirement and are not published in the index.
|
||||
|
||||
Generators preserve each requirement string. Readers evaluate the strings separately; they do not concatenate or expand their ranges. npm owns package peer resolution and its Node/npm engine checks. DSH owns enforcement of its custom `engines.dsh` key, as recorded in the [public manifest decision](../../implemented/architecture/2026-09-10-public-package-manifest.md).
|
||||
@@ -167,7 +171,7 @@ A reader cannot verify these rules; a generator that violates them publishes a m
|
||||
- `dist-tags` snapshots the registry's [distribution tags](https://docs.npmjs.com/cli/v11/commands/npm-dist-tag/). A generator includes each retained tag's target version, or omits that tag when its target is outside the listed bundle versions. For Git sources, the publisher or market supplies the same exact tag-to-version mapping.
|
||||
- Each listed version declares `dsh.bundle`. Installation independently refuses a package without a bundle patch.
|
||||
- Package-derived display fields come from the exact version named by `dist-tags.latest`. Without that tag, generators omit those display fields and readers use the package-name fallback. `title`, `description`, and `icon` follow installed-plugin display metadata rules, subject to this format's `LocalizedText` requirements. Localized text is catalog display data, not another npm manifest declaration. `homepage` copies the selected manifest's `homepage` and is absent without one.
|
||||
- npm's `author` may be a person object or shorthand string. For an object, generators copy its `name` when it contains a non-whitespace character. For a shorthand string, they use a maintained npm person normalizer and take its `name` under the same condition. They omit an absent or whitespace-only name and do not copy email or URL into this display field. They normalize only the author projection, preserving version strings and exemption identities.
|
||||
- npm's `author` may be a person object or shorthand string. For an object, generators copy its `name` when it contains a non-whitespace character. For a shorthand string, they use a maintained npm person normalizer and take its `name` under the same condition. They omit an absent or whitespace-only name and do not copy email or URL into this display field. They normalize a fresh projection, leaving the source manifest untouched.
|
||||
|
||||
### Reader rules
|
||||
|
||||
@@ -175,7 +179,9 @@ A reader rejects the whole index when the document violates any rule in Root fie
|
||||
|
||||
A reader ignores members that this note does not define, at every level; an unknown `source.type` value is rejected. Format 1 can then gain optional members without breaking existing readers; a change that existing readers would misinterpret uses a new `format` value.
|
||||
|
||||
Entries in `engines`, `peerDependencies`, and `dist-tags` are declared data, not unknown members to discard. Their values must be strings; a non-string value invalidates the index. A DSH requirement string can be empty or syntactically invalid and remains visible as incompatible. Distribution-tag names use npm's tag validation, and targets match listed version strings exactly.
|
||||
Entries in `engines`, `peerDependencies`, and `dist-tags` are declared data, not unknown members to discard. Their values must be strings; a non-string value invalidates the index. A DSH requirement string can be empty or syntactically invalid and remains visible as incompatible. A distribution-tag name must make `name@tag` a registry tag spec under npm's maintained `npm-package-arg` parser, rather than a version or range. Tag targets match listed version strings exactly.
|
||||
|
||||
npm sources use canonical published registry version identifiers: the string equals npm's `node-semver.valid()` result, without build metadata. npm's publishing normalization does not provide separately selectable build-metadata variants. Git sources can retain such variants because their commits pin the installed source independently. Readers reject non-canonical npm source versions instead of claiming an exact build selection that npm does not provide.
|
||||
|
||||
Categories, labels, and sort keys are opaque: a reader filters and sorts by them, displays their `title`, and never interprets an id. Readers display declarations in the order of their localized `title`. When sorting plugins, a plugin without a value for the selected sort key follows all plugins with a value in either direction, and equal values keep the index order. Sorting by publish time uses a plugin's greatest `publishTimestamp`.
|
||||
|
||||
@@ -226,10 +232,10 @@ Clients identify prereleases when users choose an exact version or channel, and
|
||||
- A validator accepts the example above and rejects one violation of each structural rule in Root fields, Plugin fields, Version fields, and the `source` forms, with a diagnostic naming the JSON path. Invalid DSH range strings are accepted structurally and evaluated as incompatible.
|
||||
- Install arguments built from every example version are accepted by DSH's install-spec parser and by pnpm.
|
||||
- A validator ignores unknown members at every level.
|
||||
- Index and installation compatibility match for the same manifest, runtime version, and local exemptions. Cases cover hyphen ranges, `||` alternatives, workspace shorthands, invalid ranges, and a broad engine range with an incompatible DSH peer.
|
||||
- Index and installation compatibility match for the same manifest, runtime version, and local exemptions. Cases cover hyphen ranges, `||` alternatives, workspace shorthands, invalid ranges, a broad engine range with an incompatible DSH peer, and compatible peers with an unsatisfied or empty `engines.dsh`.
|
||||
- Exact `dist-tags` targets select the same source when equally ranked build-metadata versions are reordered. Missing tag targets are rejected; absent or incompatible `latest` never causes an implicit version or channel switch.
|
||||
- Author objects and shorthand strings produce the declared display name without contact fields or version normalization.
|
||||
- A parser validates `1.0.0+one` and preserves that complete string for tag lookup, installation identity, and local exemption keys.
|
||||
- A Git version parser validates `1.0.0+one` and preserves that complete string for tag lookup, installation identity, and local exemption keys. Its commit selects the exact source; npm source versions with build metadata are rejected.
|
||||
- Installation confirmation identifies the selected version, channel when selected, prerelease status, index URL, and source. Market labels and scores remain attributed claims.
|
||||
|
||||
## Risks
|
||||
@@ -240,5 +246,5 @@ Clients identify prereleases when users choose an exact version or channel, and
|
||||
- URL icons disclose the user's IP address to image hosts.
|
||||
- Pinned versions and distribution tags stay stale until the index is regenerated.
|
||||
- Version pinning does not authenticate a market's identity or guarantee the bytes an arbitrary registry returns. Installed package checks remain independent of the catalog.
|
||||
- Readers and generators must adopt this revised proposal together before deployment; mixing the original and revised format-1 rules can change compatibility results and version selection.
|
||||
- Readers, generators, and installation must adopt this revised proposal together before deployment; mixing the original and revised format-1 rules can change compatibility results and version selection.
|
||||
- Market text reaches users, and models through any client tool that lists plugins, without review by DSH.
|
||||
@@ -113,9 +113,9 @@ DSH 只能从用户已知的 spec 安装第三方组合包(bundle):npm 包
|
||||
|---|---|---|
|
||||
| `name` | 是 | npm 持续维护的包名校验器接受的新包名称;在索引内唯一。 |
|
||||
| `title` | 否 | `LocalizedText`;缺省时读取器显示 `name`。 |
|
||||
| `description` | 否 | 用于市场列表显示的 `LocalizedText`,由语言元数据和 npm 描述派生。 |
|
||||
| `description` | 否 | 用于市场列表显示的 `LocalizedText`;派生规则见生成器义务。 |
|
||||
| `icon` | 否 | 以下两种形式之一:`data:<type>;base64,<payload>`,其中 `<type>` 为 `image/svg+xml`、`image/png`、`image/jpeg` 或 `image/webp`,`<payload>` 是按规范填充的 base64,解码后的载荷不超过 256 KiB;或者 URL 引用,它相对于索引 URL 解析的结果是 `https:` URL,或与索引 URL 同源。 |
|
||||
| `author` | 否 | 从 npm 作者声明投影得到的显示名称,至少包含一个非空白字符;见生成器义务。 |
|
||||
| `author` | 否 | 至少包含一个非空白字符的显示名称;npm 作者投影规则见生成器义务。 |
|
||||
| `homepage` | 否 | 介绍该插件的页面的绝对 `https:` 或 `http:` URL。 |
|
||||
| `metadata` | 否 | 包含下列三个值的对象。 |
|
||||
| `metadata.category` | 否 | 一个已声明的分类 id。 |
|
||||
@@ -153,6 +153,10 @@ DSH 只能从用户已知的 spec 安装第三方组合包(bundle):npm 包
|
||||
|
||||
索引将 manifest 的 `peerDependencies` 和 `engines` 作为两份独立声明保留。DSH 用当前运行的 DSH 版本检验每个 `@deepseek-ai/dsh` 与 `@deepseek-ai/dsh-*` 对等依赖。声明的 `engines.dsh` 增加一条宿主要求,不替代这些对等依赖。只有满足每条适用要求时,该版本才兼容。缺少声明不增加要求。
|
||||
|
||||
这保留了既有的 [app-boot 对等依赖检查](../../../../packages/boot/app-boot/src/plugin-compatibility.ts),该检查显式接收当前运行的 DSH 版本。对等依赖声明不标识该进程;profile 中 npm 的包解析与 DSH 针对当前运行时的检查相互独立。
|
||||
|
||||
实现本提案时,须为该求值器增加 `engines.dsh` 强制检查及对应的引擎豁免处理。当前求值器只检查对等依赖。部署本格式前,索引读取器与安装检查都必须使用扩展后的求值器。
|
||||
|
||||
索引读取器和安装检查使用同一个 DSH 兼容性求值器,采用 npm 的 `node-semver` 解析器和 `includePrerelease: true`。空的或无效的 DSH 范围不兼容。既有对等依赖规则将 `workspace:*`、`workspace:^` 和 `workspace:~` 映射为当前运行的 DSH 版本;其他 `workspace:` 对等依赖范围不兼容。引擎范围不采用这种对等依赖映射。精确的本地 `name@version` 豁免适用于两种 DSH 要求,但不发布到索引中。
|
||||
|
||||
生成器保留每条要求字符串。读取器分别求值,不拼接或展开范围。npm 负责包的对等依赖解析及其 Node/npm 引擎检查。DSH 负责强制检查自定义 `engines.dsh` 键,规则记录在[公共 manifest 决策](../../implemented/architecture/2026-09-10-public-package-manifest.zh.md)中。
|
||||
@@ -167,7 +171,7 @@ DSH 只能从用户已知的 spec 安装第三方组合包(bundle):npm 包
|
||||
- `dist-tags` 保存 registry [分发标签](https://docs.npmjs.com/cli/v11/commands/npm-dist-tag/)的快照。生成器包含每个保留标签的目标版本;目标不在列出的组合包版本中时,省略该标签。对于 Git 来源,发布者或市场提供同样的精确标签到版本的映射。
|
||||
- 列出的每个版本都声明了 `dsh.bundle`。安装时也会独立拒绝没有组合包 patch 的包。
|
||||
- 来自包的显示字段取自 `dist-tags.latest` 指向的精确版本。没有该标签时,生成器省略这些显示字段,读取器回退到包名。`title`、`description` 和 `icon` 遵循已安装插件的显示元数据规则,同时满足本格式的 `LocalizedText` 要求。本地化文本是市场列表显示数据,不是另一份 npm manifest 声明。`homepage` 复制所选 manifest 的 `homepage`,manifest 没有该字段时省略。
|
||||
- npm 的 `author` 可以是人员对象或简写字符串。对于对象,生成器复制其包含非空白字符的 `name`。对于简写字符串,生成器使用持续维护的 npm 人员归一化工具,在相同条件下取结果中的 `name`。名称不存在或只有空白时省略,不将 email 或 URL 复制到该显示字段。生成器只归一化作者投影,保留版本字符串与豁免身份。
|
||||
- npm 的 `author` 可以是人员对象或简写字符串。对于对象,生成器复制其包含非空白字符的 `name`。对于简写字符串,生成器使用持续维护的 npm 人员归一化工具,在相同条件下取结果中的 `name`。名称不存在或只有空白时省略,不将 email 或 URL 复制到该显示字段。生成器归一化一份新建的投影,不改动来源 manifest。
|
||||
|
||||
### 读取器规则
|
||||
|
||||
@@ -175,7 +179,9 @@ DSH 只能从用户已知的 spec 安装第三方组合包(bundle):npm 包
|
||||
|
||||
读取器在每一层都忽略本 Agent Note 未定义的成员;未知的 `source.type` 值会被拒绝。这样格式 1 可以增加可选成员而不破坏现有读取器;现有读取器会误解的变更使用新的 `format` 值。
|
||||
|
||||
`engines`、`peerDependencies` 和 `dist-tags` 中的条目是声明的数据,不是应当丢弃的未知成员。其值必须为字符串;非字符串值使索引无效。DSH 要求字符串可以为空或语法无效,但仍作为不兼容要求保留。分发标签名使用 npm 的标签校验规则,目标与所列版本字符串精确匹配。
|
||||
`engines`、`peerDependencies` 和 `dist-tags` 中的条目是声明的数据,不是应当丢弃的未知成员。其值必须为字符串;非字符串值使索引无效。DSH 要求字符串可以为空或语法无效,但仍作为不兼容要求保留。分发标签名必须使 `name@tag` 在 npm 持续维护的 `npm-package-arg` 解析器中成为 registry 标签 spec,而非版本或范围。标签目标与所列版本字符串精确匹配。
|
||||
|
||||
npm 来源使用规范的已发布 registry 版本标识:字符串等于 npm 的 `node-semver.valid()` 结果,不含版本编译信息。npm 发布时的归一化不提供仅版本编译信息不同的可独立选择版本。Git 来源可以保留此类版本,因为提交独立固定了所安装的来源。读取器拒绝不规范的 npm 来源版本,避免声称 npm 并不提供的精确构建选择。
|
||||
|
||||
分类、标签和排序键对读取器不透明:读取器按它们筛选和排序,显示其 `title`,从不解释 id 的含义。读取器按本地化 `title` 对声明排序后显示。对插件排序时,无论排序方向如何,没有所选排序键值的插件都排在所有有值的插件之后,值相同的插件保持索引顺序。按发布时间排序时使用插件最大的 `publishTimestamp`。
|
||||
|
||||
@@ -226,10 +232,10 @@ DSH 只能从用户已知的 spec 安装第三方组合包(bundle):npm 包
|
||||
- 校验器接受上面的示例,并对根字段、插件字段、版本字段和 `source` 形式中的每条结构规则各拒绝一个违例,诊断信息给出对应的 JSON 路径。无效的 DSH 范围字符串通过结构校验,但求值结果为不兼容。
|
||||
- 根据每个示例版本构建的安装参数可被 DSH 的安装 spec 解析器和 pnpm 接受。
|
||||
- 校验器在每一层都忽略未知成员。
|
||||
- 对相同的 manifest、运行时版本和本地豁免,索引与安装检查的兼容性结果一致。用例覆盖连字符范围、`||` 分支、workspace 简写、无效范围,以及宽泛的引擎范围与不兼容的 DSH 对等依赖同时存在的情况。
|
||||
- 对相同的 manifest、运行时版本和本地豁免,索引与安装检查的兼容性结果一致。用例覆盖连字符范围、`||` 分支、workspace 简写、无效范围、宽泛的引擎范围与不兼容的 DSH 对等依赖同时存在,以及对等依赖兼容而 `engines.dsh` 不满足或为空的情况。
|
||||
- 调整优先级相同的版本编译信息条目的顺序后,精确的 `dist-tags` 目标仍选择同一来源。读取器拒绝未列出的标签目标;`latest` 缺失或不兼容时,不隐式切换版本或渠道。
|
||||
- 作者对象与简写字符串产生声明的显示名称,不携带联系字段,也不归一化版本。
|
||||
- 解析器校验 `1.0.0+one`,并保留完整字符串供标签查找、安装身份和本地豁免键使用。
|
||||
- Git 版本解析器校验 `1.0.0+one`,并保留完整字符串供标签查找、安装身份和本地豁免键使用。提交选择精确来源;带有版本编译信息的 npm 来源版本被拒绝。
|
||||
- 安装确认标识所选版本、所选渠道(如有)、先行版本状态、索引 URL 和来源。市场标签与评分继续标明归属。
|
||||
|
||||
## 风险
|
||||
@@ -240,5 +246,5 @@ DSH 只能从用户已知的 spec 安装第三方组合包(bundle):npm 包
|
||||
- URL 图标会向图片主机暴露用户的 IP 地址。
|
||||
- 固定版本与分发标签在索引重新生成之前一直保持陈旧。
|
||||
- 版本固定不验证市场身份,也不保证任意 registry 返回的字节。已安装包的检查与市场列表保持独立。
|
||||
- 读取器和生成器必须在部署前一同采用这份修订提案;混用原始与修订后的格式 1 规则,可能改变兼容性结果和版本选择。
|
||||
- 读取器、生成器和安装检查必须在部署前一同采用这份修订提案;混用原始与修订后的格式 1 规则,可能改变兼容性结果和版本选择。
|
||||
- 市场文本未经 DSH 审核即到达用户,并通过任何列出插件的客户端工具到达模型。
|
||||
Reference in new issue
Block a user