dsh-mini-utility-dock 0.1.4 → 0.1.6

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/CHANGELOG.en.md CHANGED
@@ -1,5 +1,14 @@
1
1
  # Changelog
2
2
 
3
+ ## 0.1.6 - 2026-09-20
4
+
5
+ - Fix the `allowRemoteHost` note in `dist/guard.js`: it read "stop being admitted", the opposite of what the code does — that mode skips both checks, so it admits them. The JSDoc was already right; only this inline comment was inverted.
6
+ - The fragment's bytes change, so consumers must re-run `guard:sync` and raise their pin to 0.1.6.
7
+
8
+ ## 0.1.5 - 2026-09-17
9
+
10
+ - Documentation maintenance: README and CHANGELOG cleanup. Fragments and command behavior are unchanged, so consumer pins need no update.
11
+
3
12
  ## 0.1.4 - 2026-09-16
4
13
 
5
14
  - Add a cross-repo consistency section to the READMEs, separating two different properties: **local** -- a consumer's `npm test` runs `loopback:check` / `guard:check` to compare both fragments byte-for-byte against the version of this package it pins, covering both "edited a block by hand" and "forgot to re-`sync`"; and **cross-repo** -- this package's published versions are immutable and consumers pin an exact version, so "all three pin the same version" already implies "all three hold byte-identical blocks".
package/CHANGELOG.md CHANGED
@@ -1,17 +1,26 @@
1
1
  # Changelog
2
2
 
3
+ ## 0.1.6 - 2026-09-20
4
+
5
+ - 修正 `dist/guard.js` 里 `allowRemoteHost` 的说明文字:原文写作「不再被放行」,与代码相反——开启该模式时这两项检查被跳过,即被放行。JSDoc 一直是对的,只有这处行内注释写反。
6
+ - 该片段的字节因此变化,消费仓需重新运行 `guard:sync` 并把 pin 升到 0.1.6。
7
+
8
+ ## 0.1.5 - 2026-09-17
9
+
10
+ - 文档维护:README 与 CHANGELOG 的整理,片段与命令行为不变,故无需改动消费仓的 pin。
11
+
3
12
  ## 0.1.4 - 2026-09-16
4
13
 
5
- - README 新增「跨仓一致性」一节,区分两类性质:**本地**——消费仓 `npm test` 的 `loopback:check` / `guard:check` 把本仓两个片段与它们所 pin 的本仓版本逐字节比对,覆盖「私自改块」与「忘了重新 `sync`」;**跨仓**——本仓版本发布后不可变、消费仓 pin 的是精确版本,故「三仓 pin 同一版本」已经蕴含「三仓的块逐字节相同」。
6
- - 该节同时记录:消费仓的 `scripts/guard-parity.mjs` 是**人工诊断工具而非 CI 门禁**,理由是它断言的性质在 peer 检出解析到不同分支时不成立,门禁化会误报。
7
- - LICENSE 的版权署名统一为 `xswt442-cmd`。
14
+ - README 新增「跨仓一致性」一节:本地由消费仓 `npm test` 的 `loopback:check` / `guard:check` 逐字节比对,跨仓由消费仓 pin 精确版本保证。
15
+ - 该节记录 `scripts/guard-parity.mjs` 是人工诊断工具而非 CI 门禁。
16
+ - LICENSE 版权署名统一为 `xswt442-cmd`。
8
17
 
9
18
  ## 0.1.3 - 2026-09-14
10
19
 
11
- - 新增两个 host 侧片段:`dist/loopback.js`(`dsh-loopback-helpers`)导出 `LOOPBACK_HOSTNAMES`、`normalizeHostValue`、`hostHostname`、`isLoopbackName`、`isLoopbackAddress`;`dist/guard.js`(`dsh-host-guard`)导出 `portOf`、`GUARD_REASONS`、`DEFAULT_GUARD_POLICY` 与内部的 `bindGuard()` 工厂。调用方以 `policy` 传入自己的错误码与文案,判定逻辑不随之分叉。
12
- - `sync` / `check` 改为处理目标文件中**所有**已标记的片段,按 `FRAGMENTS` 顺序自下而上应用,不再要求恰好一个块。单块调用方的行为不变。
13
- - 修正 README 与包描述:说明 host 侧两个片段各自的职责、固定顺序,以及 `bindGuard` 不导出的原因。
14
- - 新增测试:多块同步与幂等 `check`、块顺序、两个片段均不引入 `import`/`require`、`bindGuard` 不导出且判据不被重复声明。
20
+ - 新增两个 host 侧片段:`dist/loopback.js`(`dsh-loopback-helpers`)导出回环判定谓词;`dist/guard.js`(`dsh-host-guard`)导出 `portOf`、`GUARD_REASONS`、`DEFAULT_GUARD_POLICY` 与内部的 `bindGuard()` 工厂,调用方以 `policy` 传入自己的错误码与文案。
21
+ - `sync` / `check` 处理目标文件中所有已标记的片段,按 `FRAGMENTS` 顺序自下而上应用。
22
+ - 修正 README 与包描述:说明两个 host 侧片段的职责、固定顺序与 `bindGuard` 不导出的原因。
23
+ - 新增测试:多块同步与幂等 `check`、块顺序、片段不引入 `import`/`require`、判据不被重复声明。
15
24
 
16
25
  ## 0.1.2 - 2026-09-06
17
26
 
package/README.en.md CHANGED
@@ -1,64 +1,45 @@
1
1
  # dsh-mini-utility-dock
2
2
 
3
- Source fragments and an embedding CLI shared by the DSH plugins. Fragments are written into a consumer at build time, so a plugin publishes standalone with no dependency on this package.
3
+ Source fragments and an embedding CLI shared by the DSH plugins.
4
4
 
5
5
  ## Fragments
6
6
 
7
- Three fragments, each delimited by markers.
8
-
9
7
  | Fragment | Marker | Target file | Exports |
10
8
  | --- | --- | --- | --- |
11
9
  | dock bootstrap | `dsh-mini-utility-dock` | `lib/client.js` | — |
12
10
  | loopback predicates | `dsh-loopback-helpers` | `lib/shared.js` | `LOOPBACK_HOSTNAMES`, `normalizeHostValue`, `hostHostname`, `isLoopbackName`, `isLoopbackAddress` |
13
11
  | host request guard | `dsh-host-guard` | `lib/shared.js` | `portOf`, `GUARD_REASONS`, `DEFAULT_GUARD_POLICY` |
14
12
 
15
- `dsh-loopback-helpers` decides address locality; the Host-header path and the TCP-peer path share one decision. `dsh-host-guard` decides admission, and provides a `bindGuard()` factory internally.
16
-
17
13
  ## Usage
18
14
 
19
15
  Write the markers into the target file, then run the CLI.
20
16
 
21
17
  ```sh
22
- npx dsh-mini-utility-dock sync path/to/client.js
23
- npx dsh-mini-utility-dock check path/to/client.js
18
+ npx dsh-mini-utility-dock sync path/to/shared.js
19
+ npx dsh-mini-utility-dock check path/to/shared.js
24
20
  ```
25
21
 
26
- `sync` preserves the markers and their indentation and writes the fragment; `check` exits non-zero when the content no longer matches it. The CLI maintains every marked fragment in the target file, applied bottom-up in `FRAGMENTS` order. A file containing a single fragment is unaffected.
22
+ The CLI maintains every marked fragment in the file, applied bottom-up in `FRAGMENTS` order. `sync` preserves marker indentation; `check` exits non-zero on drift.
27
23
 
28
- This repository also exposes an equivalent entry point, with the target path passed by the caller:
24
+ Equivalent entry point from this repository (target passed by the caller):
29
25
 
30
26
  ```sh
31
- npm run dock:embed -- check path/to/client.js # verify only, non-zero on drift
32
- npm run dock:embed -- sync path/to/client.js # write between the markers
27
+ npm run dock:embed -- check path/to/client.js
28
+ npm run dock:embed -- sync path/to/client.js
33
29
  ```
34
30
 
35
- Consumers invoke the same CLI as `loopback:sync` / `guard:sync`, with the target fixed to their own `lib/shared.js`; either command maintains both fragments in that file.
36
-
37
- ## The two host-side fragments
31
+ Consumers invoke the same CLI as `loopback:sync` / `guard:sync`, with the target fixed to their own `lib/shared.js`.
38
32
 
39
- The two fragments in `lib/shared.js` have a fixed order, `dsh-loopback-helpers` first.
33
+ ## Constraints
40
34
 
41
- The order is a functional requirement, not a style choice. Both fragments occupy one file, and `dsh-host-guard` uses the module-scope names the preceding fragment exports. It therefore neither redeclares those predicates nor imports a sibling module: redeclaring collides with the declaration in the same file, and importing would break the standalone-publication constraint. `guard-parity` and every consumer's `check` fail when the order is reversed.
42
-
43
- `bindGuard` is not exported from the fragment. A consumer declares its own guard export in the same file (typically reusing an existing name such as `createGuard`), and exporting the same identifier would collide. Each plugin calls `bindGuard()` and passes its own error codes and wording through `policy`: the enforcement is shared, the error vocabulary stays with each plugin.
35
+ - `dist/` is the single source. Run `npm test` after a change, and re-`sync` consumers.
36
+ - The two fragments in `lib/shared.js` have a fixed order, `dsh-loopback-helpers` first: `dsh-host-guard` uses the module-scope names the preceding fragment exports, and neither redeclares nor imports them.
37
+ - A fragment must not contain `import` or `require`; a consumer must publish standalone.
38
+ - `bindGuard` is not exported — a consumer declares its own guard export in the same file. Each plugin passes its own error codes and wording through `policy`; the enforcement is shared.
39
+ - A missing, blank, or non-string `label` falls back to `id`.
44
40
 
45
41
  ## Cross-repo consistency
46
42
 
47
- The three hand-maintained copies drifted three times: all three rejected IPv6 loopback; the three disagreed on which Host spellings count as loopback; and an unbracketed IPv6 Host silently skipped the allowlist in one plugin while the others denied it. Two checks of different kinds now cover this.
48
-
49
- - **Local.** Each consumer's `npm test` runs `loopback:check` / `guard:check`, comparing its two blocks byte for byte against the `dist/` of **the dock version it pins**. This covers a hand edit to a block and a missing re-`sync`.
50
- - **Cross-repo.** A published dock version is immutable, and consumers pin an exact version, so "all three pin one version" is equivalent to "all three hold byte-identical blocks". The cross-repo property follows from pin agreement, without comparing three source trees. The one real risk is omitting a peer from a synchronized bump.
51
-
52
- A consumer's `scripts/guard-parity.mjs` checks that cross-repo property directly, including pin agreement, and asserts that all three reach the same answer for every decision.
53
-
54
- It is a **manual diagnostic, not a CI gate**: the property it asserts cannot hold while peers sit on a different branch — on a `dev` push the peer checkouts resolve to their default branch. Run it when all three checkouts share a branch (before or after a release), where a failure is a real signal.
55
-
56
- ## Development
57
-
58
- `dist/` is the single source for each fragment. Run `npm test` after a change; consumers that have already embedded a fragment must re-run the matching `sync` command.
59
-
60
- A fragment must not contain `import` or `require`: it shares a file with the consumer's own code, and the consumer must publish standalone. Tests assert this constraint.
61
-
62
- ## Registration
43
+ A consumer's `npm test` runs `loopback:check` / `guard:check`, comparing its two fragments byte for byte against the dock version it pins. A published version is immutable and consumers pin an exact version, so pin agreement implies fragment agreement.
63
44
 
64
- A missing, blank, or non-string `label` falls back to `id`, so no item renders `aria-label="undefined"`.
45
+ `scripts/guard-parity.mjs` (in each consumer) checks that cross-repo property directly, including pin agreement. It is a manual diagnostic and **does not run in CI**: the property cannot hold while peers sit on a different branch. Run it when all three checkouts share a branch.
package/README.md CHANGED
@@ -1,64 +1,45 @@
1
1
  # dsh-mini-utility-dock
2
2
 
3
- DSH 插件共享的源码片段与嵌入 CLI。片段在构建时写入消费插件,使插件无需依赖本包即可独立发布。
3
+ DSH 插件共享的源码片段与嵌入 CLI
4
4
 
5
5
  ## 片段
6
6
 
7
- 三个片段,均由标记界定。
8
-
9
7
  | 片段 | 标记 | 目标文件 | 导出 |
10
8
  | --- | --- | --- | --- |
11
9
  | dock 引导 | `dsh-mini-utility-dock` | `lib/client.js` | — |
12
10
  | loopback 判定 | `dsh-loopback-helpers` | `lib/shared.js` | `LOOPBACK_HOSTNAMES`、`normalizeHostValue`、`hostHostname`、`isLoopbackName`、`isLoopbackAddress` |
13
11
  | host 请求守卫 | `dsh-host-guard` | `lib/shared.js` | `portOf`、`GUARD_REASONS`、`DEFAULT_GUARD_POLICY` |
14
12
 
15
- `dsh-loopback-helpers` 定义地址的归属:Host 头与 TCP 对端两条路径共用同一判定。`dsh-host-guard` 定义准入策略,并在内部提供 `bindGuard()` 工厂。
16
-
17
13
  ## 使用
18
14
 
19
15
  在目标文件中写入标记,然后运行 CLI。
20
16
 
21
17
  ```sh
22
- npx dsh-mini-utility-dock sync path/to/client.js
23
- npx dsh-mini-utility-dock check path/to/client.js
18
+ npx dsh-mini-utility-dock sync path/to/shared.js
19
+ npx dsh-mini-utility-dock check path/to/shared.js
24
20
  ```
25
21
 
26
- `sync` 保留标记及其缩进并写入片段;`check` 在内容与片段不一致时以非零状态退出。CLI 处理目标文件中所有已标记的片段,按 `FRAGMENTS` 顺序自下而上应用。仅含单个片段的文件行为不变。
22
+ CLI 处理文件中所有已标记的片段,按 `FRAGMENTS` 顺序自下而上应用;`sync` 保留标记缩进,`check` 在漂移时非零退出。
27
23
 
28
- 本仓库另提供等价入口,目标路径由调用方传入:
24
+ 本仓库等价入口(目标由调用方传入):
29
25
 
30
26
  ```sh
31
- npm run dock:embed -- check path/to/client.js # 仅校验,漂移时非零退出
32
- npm run dock:embed -- sync path/to/client.js # 写入标记之间
27
+ npm run dock:embed -- check path/to/client.js
28
+ npm run dock:embed -- sync path/to/client.js
33
29
  ```
34
30
 
35
- 消费插件以 `loopback:sync` / `guard:sync` 调用同一 CLI,目标固定为自身的 `lib/shared.js`;任一命令都会同步该文件中的两个片段。
36
-
37
- ## host 侧两个片段的约定
31
+ 消费插件以 `loopback:sync` / `guard:sync` 调用同一 CLI,目标固定为自身 `lib/shared.js`。
38
32
 
39
- `lib/shared.js` 中的两个片段顺序固定,`dsh-loopback-helpers` 在前。
33
+ ## 约束
40
34
 
41
- 顺序是功能要求,不是风格约定。两者位于同一文件,`dsh-host-guard` 直接使用前一片段导出的模块级名字,因此它既不重新声明这些判据,也不 import 兄弟模块:重新声明与 import 都会与同文件内的声明冲突,且 import 会破坏插件独立发布的约束。`guard-parity` 与消费仓的 `check` 都会在该顺序被颠倒时失败。
42
-
43
- `bindGuard` 不从片段导出。消费插件在同一文件中声明自己的 guard 导出(通常沿用 `createGuard` 等既有名字),导出同名标识符会冲突。每个插件调用 `bindGuard()`,通过 `policy` 传入自身的错误码与文案;判定逻辑共用,错误词汇由各插件持有。
35
+ - `dist/` 是唯一来源。改片段后运行 `npm test`,并让消费插件重新 `sync`。
36
+ - `lib/shared.js` 中两个片段顺序固定,`dsh-loopback-helpers` 在前:`dsh-host-guard` 直接使用前一片段导出的模块级名字,既不重新声明也不 import。
37
+ - 片段不得包含 `import` `require`;消费插件必须能独立发布。
38
+ - `bindGuard` 不从片段导出——消费插件在同一文件中声明自己的 guard 导出。各插件通过 `policy` 传入自身错误码与文案,判定逻辑共用。
39
+ - `label` 缺省、空白或非字符串时回退为 `id`。
44
40
 
45
41
  ## 跨仓一致性
46
42
 
47
- 三份手写副本曾漂移三次:三家都拒绝 IPv6 loopback;三家对 Host 拼写各执一词;未加方括号的 IPv6 Host 在一家静默跳过校验、另两家拒绝。现在由两条性质不同的检查覆盖:
48
-
49
- - **本地**。每个消费仓的 `npm test` 运行 `loopback:check` / `guard:check`,把本仓的两个块与**它所 pin 的该 dock 版本**的 `dist/` 逐字节比对。这覆盖「私自改块」与「忘了重新 `sync`」。
50
- - **跨仓**。dock 版本发布后不可变,且消费仓 pin 的是精确版本,因此「三仓 pin 同一版本」等价于「三仓的块逐字节相同」。跨仓性质由 pin 的一致性推出,不需要比对三份源码树。唯一现实风险是遗漏对某个 peer 的同步 bump。
51
-
52
- 消费仓的 `scripts/guard-parity.mjs` 把上述跨仓性质直接检出来,含三仓 pin 一致性断言,也断言三仓在每一道判定上结论相同。
53
-
54
- 它是**人工诊断工具,不是 CI 门禁**:它断言的性质在 peer 处于不同分支时不成立 —— `dev` 推送时 peer 检出会解析到默认分支。请在三个检出处于同一分支时运行它(发版前或发版后),此时报错才是真信号。
55
-
56
- ## 开发
57
-
58
- 片段的唯一来源是 `dist/`。修改后运行 `npm test`;已嵌入片段的消费插件需重新运行对应的 `sync` 命令。
59
-
60
- 片段不得包含 `import` 或 `require`:它们与消费插件自身的代码位于同一文件,且消费插件必须独立发布。测试对此约束进行断言。
61
-
62
- ## 注册
43
+ 消费仓的 `npm test` 用 `loopback:check` / `guard:check` 把本仓两个片段与所 pin 的 dock 版本逐字节比对。dock 版本不可变且消费仓 pin 精确版本,故「pin 一致」即「片段一致」。
63
44
 
64
- `label` 缺省、空白或非字符串时回退为 `id`,避免渲染出 `aria-label="undefined"`。
45
+ `scripts/guard-parity.mjs`(位于各消费仓)直接检这条跨仓性质,含 pin 一致性断言。它是人工诊断工具,**不在 CI 中运行**:peer 处于不同分支时该性质本就不成立。请在三个检出同分支时运行。
package/dist/guard.js CHANGED
@@ -134,12 +134,13 @@ const bindGuard = ({ currentPort, respond, allowRemoteHost, policy } = {}) => {
134
134
  return deny(res, 'unknown_peer')
135
135
  }
136
136
  // `allowRemoteHost` buys exactly one thing: an off-loopback peer AND an
137
- // off-loopback Host stop being admitted by this guard, because the caller has
138
- // opted into verifying its own credential per request. Everything else still
139
- // applies the Origin check below rejects cross-site traffic in both modes,
140
- // so the exemption never widens the browser-facing boundary. A plugin that
141
- // does not pass the predicate never enters this mode, so for it the peer and
142
- // Host criteria are absolute.
137
+ // off-loopback Host stop being *rejected* by this guard both checks below
138
+ // are skipped because the caller has opted into verifying its own
139
+ // credential per request. Everything else still applies: the Origin check
140
+ // below rejects cross-site traffic in both modes, so the exemption never
141
+ // widens the browser-facing boundary. A plugin that does not pass the
142
+ // predicate never enters this mode, so for it the peer and Host criteria
143
+ // are absolute.
143
144
  const remote = fleetAllowed()
144
145
  if (!remote && !isLoopbackAddress(peerAddress)) {
145
146
  return deny(res, 'non_loopback_peer')
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "dsh-mini-utility-dock",
3
- "version": "0.1.4",
3
+ "version": "0.1.6",
4
4
  "description": "Canonical fragments and a build-time embedding CLI shared by DSH plugins: the Mini Utility Dock bootstrap for client halves, and the loopback predicates plus the host request guard for host halves.",
5
5
  "type": "module",
6
6
  "bin": {