@dzhechkov/harness-cli 0.8.19 → 0.8.21
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/.dz-manifest.json +7 -7
- package/README.md +39 -19
- package/dist/cli.d.ts.map +1 -1
- package/dist/cli.js +167 -12
- package/dist/cli.js.map +1 -1
- package/package.json +9 -9
- package/sbom.json +6 -6
- package/src/cli.ts +162 -13
package/.dz-manifest.json
CHANGED
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
},
|
|
10
10
|
{
|
|
11
11
|
"path": "README.md",
|
|
12
|
-
"sha256": "
|
|
12
|
+
"sha256": "2a3c1e1f9f922913c45df3482f2055ac2efc726108e1d4377195739e026a4034"
|
|
13
13
|
},
|
|
14
14
|
{
|
|
15
15
|
"path": "dist/bin.d.ts",
|
|
@@ -49,15 +49,15 @@
|
|
|
49
49
|
},
|
|
50
50
|
{
|
|
51
51
|
"path": "dist/cli.d.ts.map",
|
|
52
|
-
"sha256": "
|
|
52
|
+
"sha256": "ef3852bb748f37d4e78a9a973505c3993eae2b996cc0cdd0659f531aa76621f4"
|
|
53
53
|
},
|
|
54
54
|
{
|
|
55
55
|
"path": "dist/cli.js",
|
|
56
|
-
"sha256": "
|
|
56
|
+
"sha256": "9d0a6cc044810b31d261b36913e3f63445f5e96550176fedd0faf606d8cbcd75"
|
|
57
57
|
},
|
|
58
58
|
{
|
|
59
59
|
"path": "dist/cli.js.map",
|
|
60
|
-
"sha256": "
|
|
60
|
+
"sha256": "3049258ffd0972b6a748eda703221911dd33e3450486c1dec0f598a431faa038"
|
|
61
61
|
},
|
|
62
62
|
{
|
|
63
63
|
"path": "dist/command-inventory.d.ts",
|
|
@@ -149,7 +149,7 @@
|
|
|
149
149
|
},
|
|
150
150
|
{
|
|
151
151
|
"path": "package.json",
|
|
152
|
-
"sha256": "
|
|
152
|
+
"sha256": "52e0e71990b14cf8dc5b07046c30d6d9807f7cec1cdef4463ac6bd155b0312d4"
|
|
153
153
|
},
|
|
154
154
|
{
|
|
155
155
|
"path": "src/bin.ts",
|
|
@@ -161,7 +161,7 @@
|
|
|
161
161
|
},
|
|
162
162
|
{
|
|
163
163
|
"path": "src/cli.ts",
|
|
164
|
-
"sha256": "
|
|
164
|
+
"sha256": "f34208b28b53697118db5370f82c6aaab883bb7be10d99789a96a39a06acfac7"
|
|
165
165
|
},
|
|
166
166
|
{
|
|
167
167
|
"path": "src/command-inventory.ts",
|
|
@@ -185,5 +185,5 @@
|
|
|
185
185
|
}
|
|
186
186
|
]
|
|
187
187
|
},
|
|
188
|
-
"signature": "
|
|
188
|
+
"signature": "xGTyQNnFIlVTZIRDcbaTCfyuQL3fbW3qReGYhLbjlFQ9k9wsYflwDXPDq/Ukge4VHEirdmE10W2RV1XQZEhUDA=="
|
|
189
189
|
}
|
package/README.md
CHANGED
|
@@ -2,6 +2,14 @@
|
|
|
2
2
|
|
|
3
3
|
The **`dz`** CLI — the main entry point to the DZ Harness Hub. Install AI skills for **Claude Code, Codex, OpenCode, Hermes, OpenClaude, GitHub Copilot** from a single command.
|
|
4
4
|
|
|
5
|
+
## Test execution
|
|
6
|
+
|
|
7
|
+
`npx vitest run` uses two projects and returns one combined verdict: `parallel` runs the ordinary
|
|
8
|
+
suites concurrently, while `serial` runs process-spawning and real-time suites one file at a time.
|
|
9
|
+
The serial paths in `test/serial-suites.txt` are regenerated from
|
|
10
|
+
`test/serial-suites-census.test.ts`, which scans test sources for synchronous and asynchronous
|
|
11
|
+
process markers, including `execSync(` and `execFile(`, and fails when the list and census differ.
|
|
12
|
+
|
|
5
13
|
## Why dz?
|
|
6
14
|
|
|
7
15
|
> **`dz` is a package manager + cross-compiler for your AI agent harness.** Write a skill once in one canonical form; `dz` installs it into any agent's harness, holds it to a quality bar, and lets the harness learn over time.
|
|
@@ -3082,14 +3090,17 @@ dz mcp-scan . --reconcile --fail-on-undergrant # CI: exit 1 if a skill declare
|
|
|
3082
3090
|
|
|
3083
3091
|
For a live publish, the CLI prints `published` only after npm answers with the exact new package
|
|
3084
3092
|
version, followed by the receipt text `confirmed by registry after N probes`. A zero exit from
|
|
3085
|
-
`pnpm publish` alone is not success. The publisher
|
|
3086
|
-
|
|
3093
|
+
`pnpm publish` alone is not success. The publisher uses 90 probes × 10 s (15 min); measured registry
|
|
3094
|
+
visibility lag was 3 to >5 min on 2026-09-10. An unconfirmed version is an error and its local bump is
|
|
3095
|
+
restored.
|
|
3087
3096
|
`--dry-run` and `--bump-only` do not probe for this receipt because neither performs a live publish.
|
|
3088
3097
|
When the receipt never arrives, the CLI adds one line telling you what to check: `npm view <pkg>@<version>` —
|
|
3089
3098
|
if the registry answers, the publish DID land and only the local bump was rolled back; re-apply it by hand.
|
|
3090
3099
|
Registry probes run `npm view … --prefer-online`, because the publisher itself warms the packument cache before publishing (measured 2026-09-10: 30 misses on a landed package).
|
|
3091
3100
|
On an error, `dz publish` prints the last three probe records (attempt, exit code, elapsed milliseconds,
|
|
3092
3101
|
and the first captured stderr/stdout line); `--json` returns the complete, untruncated `probeLog`.
|
|
3102
|
+
The text report also prints every post-publish warning and each README whose release line was synchronized;
|
|
3103
|
+
`--json` keeps those same facts in `warnings` and `releaseLineSynced` without extra human-output lines.
|
|
3093
3104
|
In a multi-package batch, a dependent is not bumped or published after one of its workspace dependencies
|
|
3094
3105
|
has failed in that batch; its error names the dependency and preserves the dependency's failure reason.
|
|
3095
3106
|
|
|
@@ -3855,7 +3866,7 @@ invariants: HARD rules **block** the operation, SOFT rules warn. Zero config nee
|
|
|
3855
3866
|
cover the known rakes; `.dz/guard.json` (via `dz guard --init`) exists only if you want to tune a severity
|
|
3856
3867
|
or disable a rule.
|
|
3857
3868
|
```bash
|
|
3858
|
-
dz guard check --op publish # no-workspace-star · no-skill-drift · no-secrets · readme-consistency · readme-first · skills-registrable · lockfile-in-sync · marketplace-parity · no-stubs · review-round · licence-hold
|
|
3869
|
+
dz guard check --op publish # no-workspace-star · no-skill-drift · no-secrets · readme-consistency · readme-first · signature-fresh · skills-registrable · lockfile-in-sync · marketplace-parity · no-stubs · review-round · licence-hold
|
|
3859
3870
|
dz guard check --op teach --text "the fix: export sk-abc..." # → BLOCK (exit 1): looks like a credential
|
|
3860
3871
|
dz guard log # append-only audit: every verdict + every forced override
|
|
3861
3872
|
```
|
|
@@ -3868,10 +3879,15 @@ dz guard (teach): ✗ BLOCK [checked: no-secrets, store-bloat-cap]
|
|
|
3868
3879
|
hatch `--no-guard "<reason>"` requires a reason and is logged to `.dz/guard-audit.jsonl` — an override is
|
|
3869
3880
|
visible, never silent. Calibrated against false gates: in a pnpm workspace, `workspace:*` in source is
|
|
3870
3881
|
*correct* (pnpm rewrites it at publish), so the rule resolves each workspace dep to the version it would
|
|
3871
|
-
ship as and blocks only a dep that would ship raw. The `
|
|
3882
|
+
ship as and blocks only a dep that would ship raw. The SOFT `signature-fresh` rule checks only signed
|
|
3883
|
+
packs with changed non-manifest files and names the `dz sign` repair before publish. The
|
|
3884
|
+
`readme-consistency` rule also holds the **docs
|
|
3872
3885
|
site** in the contour: the command count on the Starlight CLI overview and the front-page tagline must
|
|
3873
3886
|
match the cli README (the site once drifted 35→55 silently; now a mismatch is a warning here and a red
|
|
3874
3887
|
test in CI). In a repo without the docs site those pairs simply aren't gathered — no false gate.
|
|
3888
|
+
`readme-first` compares the package's `version` field with `HEAD`, so changing `repository` or other
|
|
3889
|
+
package metadata alone does not masquerade as a version bump; unreadable version evidence is reported as
|
|
3890
|
+
an `unknown` observation and never becomes a violation.
|
|
3875
3891
|
|
|
3876
3892
|
The SOFT `lockfile-in-sync` rule closes the CI break that follows a dependency bump: when a workspace
|
|
3877
3893
|
`packages/*/package.json` declares a `@dzhechkov/*` spec that differs from the specifier `pnpm-lock.yaml`
|
|
@@ -4697,21 +4713,25 @@ refusal as the honest answer.
|
|
|
4697
4713
|
|
|
4698
4714
|
## Status
|
|
4699
4715
|
|
|
4700
|
-
`harness-core v0.8.
|
|
4701
|
-
|
|
4702
|
-
|
|
4703
|
-
`
|
|
4704
|
-
|
|
4705
|
-
|
|
4706
|
-
|
|
4707
|
-
|
|
4708
|
-
|
|
4709
|
-
|
|
4710
|
-
|
|
4711
|
-
|
|
4712
|
-
|
|
4713
|
-
|
|
4714
|
-
|
|
4716
|
+
`harness-core v0.8.29` · `harness-cli v0.8.21` — **this release: the release itself is checked
|
|
4717
|
+
before it is pressed, and the repository boundary is honest.** (1) `dz guard` gains two rules:
|
|
4718
|
+
`release-line-in-sync` — the version line in the root README and the CLI README must name the
|
|
4719
|
+
versions `package.json` carries, and `dz publish` now rewrites those lines itself; `signature-fresh` —
|
|
4720
|
+
a changed pack whose Ed25519 manifest was signed over older bytes is named BEFORE publication
|
|
4721
|
+
(`workspace:` specs are rewritten before hashing, exactly as the pack is published). (2) `readme-first`
|
|
4722
|
+
compares the `version` field against HEAD instead of "package.json changed", so a repository-field
|
|
4723
|
+
edit no longer reads as a release. (3) All 56 workspace `package.json` files carry the real
|
|
4724
|
+
`repository` origin, pinned by a test. (4) Suites that spawn processes or hold real locks run in a
|
|
4725
|
+
serial vitest project (`test/serial-suites.txt`, audited by a census test); the CLI suite dropped from
|
|
4726
|
+
~6 minutes to ~2m20 once the in-process marketplace guard left the worker-RPC path. (5) `isRepoBoundary`:
|
|
4727
|
+
a `.git` directory is a repository boundary only with a real `HEAD` (or a worktree `gitdir:` file), so
|
|
4728
|
+
`dz` run from `/tmp` beside a stray empty `.git` no longer adopts it as a project and no longer creates
|
|
4729
|
+
`/tmp/.dz`. A planned fallback lock location was MEASURED unsound (two processes could hold two
|
|
4730
|
+
different locks for one root) and withdrawn before release — named locks stay `<root>/.dz/locks`, a
|
|
4731
|
+
pure function of the root. (6) `dz amendment-check` recognises the Russian challenge-panel placeholder
|
|
4732
|
+
as a stub.
|
|
4733
|
+
|
|
4734
|
+
`dz guard check --op publish` now warns when either release line disagrees with the core/CLI package versions, and a registry-confirmed live core or CLI publish synchronizes the first such line in both release READMEs: each README is rewritten atomically; the pair is not one transaction (dry-run and bump-only never write them).
|
|
4715
4735
|
|
|
4716
4736
|
**Previously (`v0.8.12`):** ONE definition of "a dz
|
|
4717
4737
|
command" (ADR-001, feature `command-count-triad`). `src/command-inventory.ts` is the single pure
|
package/dist/cli.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"cli.d.ts","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAUH,OAAO,EAAoC,KAAK,EAAa,KAAK,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAK3G,OAAO,EAAyF,KAAK,SAAS,EAAE,MAAM,yBAAyB,CAAC;AAGhJ,OAAO,EAgDL,iBAAiB,EAmBjB,KAAK,oBAAoB,
|
|
1
|
+
{"version":3,"file":"cli.d.ts","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAUH,OAAO,EAAoC,KAAK,EAAa,KAAK,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAK3G,OAAO,EAAyF,KAAK,SAAS,EAAE,MAAM,yBAAyB,CAAC;AAGhJ,OAAO,EAgDL,iBAAiB,EAmBjB,KAAK,oBAAoB,EA+ZzB,KAAK,YAAY,EA6ElB,MAAM,yBAAyB,CAAC;AAcjC,OAAO,KAAK,EAAgE,qBAAqB,EAAE,gBAAgB,EAAc,kBAAkB,EAA0J,MAAM,yBAAyB,CAAC;AA6B7U,4FAA4F;AAC5F,eAAO,MAAM,WAAW,EAAE,SAAS,MAAM,EAexC,CAAC;AA2JF,MAAM,WAAW,6BAA6B;IAC5C,QAAQ,CAAC,QAAQ,EAAE,MAAM,GAAG,IAAI,CAAC;IACjC,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,aAAa,CAAC,EAAE,MAAM,CAAC;CACjC;AAED,MAAM,MAAM,kBAAkB,GAAG,CAC/B,OAAO,EAAE,MAAM,EACf,OAAO,EAAE;IAAE,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAA;CAAE,KAC1D,6BAA6B,CAAC;AAEnC,2EAA2E;AAC3E,MAAM,WAAW,KAAK;IACpB,QAAQ,CAAC,GAAG,CAAC,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,KAAK,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;IACxC;;;;;;;;;;OAUG;IACH,QAAQ,CAAC,QAAQ,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;IAC3C;;;;OAIG;IACH,QAAQ,CAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IACxB,kFAAkF;IAClF,QAAQ,CAAC,WAAW,CAAC,EAAE,OAAO,CAAC;IAC/B,mGAAmG;IACnG,QAAQ,CAAC,YAAY,CAAC,EAAE,qBAAqB,CAAC,cAAc,CAAC,CAAC;IAC9D,sFAAsF;IACtF,QAAQ,CAAC,gBAAgB,CAAC,EAAE,CAAC,WAAW,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE;QAAE,QAAQ,CAAC,MAAM,CAAC,EAAE,MAAM,CAAA;KAAE,KAAK,OAAO,CAAC,gBAAgB,CAAC,CAAC;IACjI,uGAAuG;IACvG,QAAQ,CAAC,oBAAoB,CAAC,EAAE,CAAC,WAAW,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,KAAK,OAAO,CAAC;QAAE,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;IAC7H;;;;;OAKG;IACH,QAAQ,CAAC,aAAa,CAAC,EAAE,iBAAiB,CAAC;IAC3C;;;;;OAKG;IACH,QAAQ,CAAC,aAAa,CAAC,EAAE,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,KAAK,IAAI,CAAC;IAChE,wFAAwF;IACxF,QAAQ,CAAC,kBAAkB,CAAC,EAAE,kBAAkB,CAAC;IACjD,iEAAiE;IACjE,QAAQ,CAAC,SAAS,CAAC,EAAE,SAAS,CAAC;CAChC;AAED,yFAAyF;AACzF,MAAM,MAAM,iBAAiB,GAAG,CAC9B,GAAG,EAAE,MAAM,EACX,IAAI,EAAE;IAAE,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAA;CAAE,KACvD;IAAE,QAAQ,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,EAAE,OAAO,CAAA;CAAE,CAAC;AAyD9E,KAAK,KAAK,GAAG,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;AA41CpC;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,gBAAgB,CAAC,OAAO,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,GAAG,SAAS,MAAM,EAAE,CAExF;AAED;;;;;;;;;;;GAWG;AACH,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,GAAG,MAAM,CAMhF;AAusED;;;;;;;GAOG;AACH,wBAAsB,yBAAyB,CAAC,CAAC,EAAE,EAAE,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,GAAG,OAAO,CAAC,CAAC,CAAC,CA0BnF;AA8+HD,MAAM,WAAW,mBAAmB;IAClC,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IACxC,QAAQ,CAAC,OAAO,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IACtC,QAAQ,CAAC,KAAK,CAAC,EAAE,OAAO,CAAC;IACzB,QAAQ,CAAC,MAAM,CAAC,EAAE,OAAO,CAAC;IAC1B,6EAA6E;IAC7E,QAAQ,CAAC,MAAM,CAAC,EAAE,OAAO,CAAC;CAC3B;AAED;;;;;;;;GAQG;AACH,wBAAgB,qBAAqB,CAAC,KAAK,EAAE,mBAAmB,GAAG,UAAU,CAAC,OAAO,iBAAiB,CAAC,CAAC,CAAC,CAAC,CAQzG;AAED,MAAM,WAAW,iBAAiB;IAChC,QAAQ,CAAC,EAAE,EAAE,OAAO,CAAC;IACrB,QAAQ,CAAC,MAAM,EAAE,SAAS,MAAM,EAAE,CAAC;IACnC,QAAQ,CAAC,MAAM,EAAE,SAAS,MAAM,EAAE,CAAC;CACpC;AAED,kGAAkG;AAClG,wBAAgB,yBAAyB,CACvC,IAAI,EAAE,kBAAkB,EACxB,QAAQ,EAAE,iBAAiB,GAAG;IAAE,QAAQ,CAAC,MAAM,EAAE,oBAAoB,CAAA;CAAE,EACvE,QAAQ,UAAQ,GACf,kBAAkB,CAkBpB;AAED;;;;;;GAMG;AACH,wBAAgB,iBAAiB,CAAC,MAAM,EAAE,oBAAoB,EAAE,KAAK,SAAkB,GAAG,iBAAiB,CAoB1G;AAwGD,wBAAgB,iBAAiB,CAC/B,KAAK,EAAE,mBAAmB,EAC1B,IAAI,GAAE,CAAC,OAAO,EAAE,UAAU,CAAC,OAAO,iBAAiB,CAAC,CAAC,CAAC,CAAC,KAAK,oBAA+C,EAC3G,KAAK,SAAa,GACjB,iBAAiB,GAAG;IAAE,QAAQ,CAAC,MAAM,EAAE,oBAAoB,CAAA;CAAE,CAK/D;AAqvGD,wFAAwF;AACxF,wBAAgB,uBAAuB,CAAC,KAAK,EAAE,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,QAAQ,EAAE,OAAO,GAAG,OAAO,CAElG;AA4BD,gFAAgF;AAChF,wBAAgB,qBAAqB,IAAI;IAAE,QAAQ,EAAE,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,YAAY,KAAK,IAAI,CAAC;IAAC,OAAO,EAAE,MAAM,MAAM,EAAE,CAAC;IAAC,IAAI,EAAE,MAAM,MAAM,CAAA;CAAE,CAM7I;AAiqDD,2FAA2F;AAC3F,wBAAgB,YAAY,CAAC,OAAO,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,EAAE,KAAK,EAAE,GAAG,CAAC,MAAM,CAAC,EAAE,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,KAAK,EACtG,IAAI,GAAE,CAAC,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,QAAQ,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,CAAC,CAAA;CAAE,KAAK,MAAM,GAAG,MAAiB,GAAG,MAAM,CAkG9I;AA0xBD,MAAM,WAAW,eAAe;IAC9B,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,GAAG,IAAI,CAAC;IACxB,QAAQ,EAAE,OAAO,CAAC;IAClB,UAAU,EAAE,MAAM,GAAG,IAAI,CAAC;CAC3B;AAED;;;;;;;;;GASG;AACH,wBAAsB,eAAe,CACnC,GAAG,EAAE,MAAM,EACX,IAAI,EAAE,MAAM,EAAE,EACd,WAAW,EAAE,MAAM,EACnB,SAAS,EAAE,MAAM,EACjB,GAAG,GAAE,MAAsB,EAC3B,SAAS,GAAE,OAAO,KAAa,GAC9B,OAAO,CAAC,eAAe,CAAC,CAI1B;AA8CD,gFAAgF;AAChF,wBAAgB,oBAAoB,CAAC,MAAM,EAAE,YAAY,EAAE,MAAM,EAAE,MAAM,CAAC,UAAU,GAAG,MAAM,CAAC,UAAU,CAEvG;AAED;;;;;;;;;;;;;;;GAeG;AACH,wBAAsB,cAAc,CAClC,GAAG,EAAE,MAAM,EACX,IAAI,EAAE,MAAM,EAAE,EACd,IAAI,EAAE;IACJ,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;IACzB,SAAS,EAAE,MAAM,CAAC;IAClB,GAAG,EAAE,MAAM,CAAC;IACZ,QAAQ,EAAE,OAAO,CAAC;IAClB,SAAS,CAAC,EAAE,OAAO,KAAK,CAAC;IACzB,OAAO,CAAC,EAAE,CAAC,KAAK,EAAE,YAAY,KAAK,IAAI,CAAC;IACxC;;;;;;OAMG;IACH,OAAO,CAAC,EAAE,OAAO,GAAG,WAAW,CAAC;IAChC,kGAAkG;IAClG,QAAQ,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;CAC9B,GACA,OAAO,CAAC,eAAe,CAAC,CA8D1B;AA8/FD,wBAAsB,MAAM,CAAC,IAAI,EAAE,MAAM,EAAE,EAAE,EAAE,GAAE,KAAU,GAAG,OAAO,CAAC,MAAM,CAAC,CAwT5E"}
|
package/dist/cli.js
CHANGED
|
@@ -22,7 +22,7 @@ import { createSkill, getSkillInfo, listSkillsDetailed, formatSkillLoadFailures,
|
|
|
22
22
|
// dz workflow run (feature dz-workflow-run): the pure scheduler + the dispatch adapters.
|
|
23
23
|
TRACE_RUNID_RE, WF_RUN_OWNER_HOST, preflight, runWorkflow, makeClaudePDispatcher, makeCodexExecDispatcher, NamedLockTimeoutError, NamedLockCompromisedError, POLICY_SOURCES, detectPolicyDrift, hasPolicyFence, TARGET_NAMES, buildParityMatrix, downgradeForStaleEvidence, findStaleTranscriptEvidence, TARGET_CAPABILITIES, TARGET_SHORT_LABELS, WORKFLOW_TEMPLATES_RETIRED_MESSAGE, parsePlan, isParseErrors, validatePlan, normalizePlan, planDigest, toTraceProjection, renderPlan, mergeRender, lint, lintExitCode, LOOP_BLOBS, parseTrace, assembleTimeline, runInvariants, deriveAttestation, stampAttestation, corroborate, NOT_WITNESSED, renderTimelineHtml, importEcc, recordPattern, recordLessonForms, normalizeLessonForms, resolveLearningBackend, storeStats, consolidateSessions, pruneNoisePatterns, lessonDeltaReport, removePatternsByIds, snapshotStore, recallHybrid, teachGuard, mirrorPatternsToVector, mirrorEntriesToVector, patternVectorEntry, readMemoryLearningConfig, promotePatterns, quarantineExpiryCandidates, pruneQuarantinePatterns, clearAgentdbQuarantine, vectorMirrorEnabled, vectorTierStatus, resolveVectorEngine, reindexVectorStore, harmonizeVectorStore, importRvfCheckpoint, renderFeatureAdrPhaseLine, statuslineData, countLearningStoreRowsReadonly, readStoreMark, writeStoreMark, resetStoreMark, checkStoreHealth, storeGuardPath, storeSnapshotPath, writeFeatureAdrState, writeFeatureAdrStateDetailed, CHECKPOINT_STAGES, estimateEta, extractStageSamples, formatEta, parseCheckpointLines, segmentRun, computeUsage, deriveCostLedger, planLedgerBackfill, listCostLedgerRuns, resolveLedgerRunId, AMBIGUOUS, stampCheckpointLine, LEDGER_FILL_SOURCE, renderCostLedger, verifyCostLedgerReport, writeCostLedgerJsonl, COST_LEDGER_SCOPE, deriveUsageCalibration, normalizeClaudeUsageModelKey, readUsageLimits, parseWeeklyResetAnchor, claimCheck, summarize, BUNDLED_SLOP_REGISTRY_URL, DEFAULT_SLOP_CONFIG, parseSlopRegistry, slopLint, validateSlopLintConfig, queryBookKnowledge, loadStorePatternsSync, patternRecordId, patternIdentityOf, mergeLessonMatchedForms, SWARM_BRIEF_CONTRACT, checkSwarmBrief, visibleText, loadStoreRecords, findExactLesson, recordToPattern, bundleSkills, brainHome, listBrain, bookKbPath, promoteProjectToBrain, updateBrainSource, queryBrain, groundPrompt, expandKu, reindexBrainVectors, buildPrimer, exportBrainSlice, importBrainSlice, registerKusToBrain, RECALL_USAGE_LOG_RELATIVE, RECALL_USAGE_LOG_MAX_BYTES, parseRecallUsageLog, buildRecallUsageReport, EVENT_CHAIN_TAIL_BYTES, EMPTY_LOG_TAIL, readTailInfo, appendChainedLines, verifyEventChainText, classifyChainDefects, CHAINED_JOURNALS, buildManifest, buildSbom, resolveTrustRoot, decideVerifyPolicy, generateSigningKeypair, appendTransition, evaluateGuard, resolveRules, auditRecord, guardExitCode, DEFAULT_RULES, parsePnpmLockImporters, scannableStubPath,
|
|
24
24
|
// guard-promotion (feature guard-promotion, scout idea #1)
|
|
25
|
-
assembleCandidates, renderPromotionReport, renderPromotionAdr, normalizePromotionState, nextPromotionState, recordPromotionRunEvidence, isLessonRuleContentAnchor, isOffsetIsoTimestamp, globMatch, promotionAdrRelPath, DEFAULT_WINDOW_DAYS, DEFAULT_PERIODS, MAX_CONTENT_FETCHES, BUILTIN_COVERAGE, decideProvenance, isInsideTree, signManifest, verifyManifest, listPackFiles, listSignablePackFiles, assertKeyOutsideTree, decidePublishGate, collectPackageFacts, planReleaseGates, selectAffectedPackages, classifyGateExecutions, buildFailureIssue, buildReleaseNotes, releaseTagName, firstOutputLine, formatPublishError, MANIFEST_NAME, SBOM_NAME, buildArchitectureMap, renderMapHuman, findArchitectureDrift, renderDriftReport, scanWorkspacePackages, loadSubsystemManifest, loadProductVision, checkFeatureAgainstArchitecture, renderArchCheck, planProjectSkills, guidanceForStage, renderInjectionReport, analyzeCorpus, renderRakeReport, renderCriticSection, rakeAsLesson, rakeReward, DEFAULT_RAKE_THRESHOLDS, streamSessionEvents, findLatestTranscript, resolveScanTailTranscript, detectProcessRakes, buildRetro, renderRetro, retroLessonText, PROCESS_SIGNATURES, RETRO_DOMAIN, runRetroTailScan, scanForSetup, buildSetupPlan, scaffoldFromSpec, renderScaffoldPreview, readExistingForScaffold, assembleChallengeContext, buildChallengeBrief, planDiscriminationCheck, classifyDiscrimination, classifyExecutionEvidence, pickAdversaryModel, CHALLENGE_QUESTIONS, loadOutcomes, renderOutcomes, statsForKey, selectAutoCost, recordProvisional, finalizeOutcome, harvestStageOutcomes, recommendModels, planFeed, unfedRuns, GRADE_SUCCESS_FLOOR, COST_LADDER, splitScenarios, budgetPlan, selectWinner, proseScopeOk, renderProseDiff, readScenarioIds, DEFAULT_MAX_JUDGE_RUNS, collectDeliveryFacts, planDeliveryCheck, renderDeliveryBrief, classifyDelivery, isUsablePlaneResult, renderDeliveryReview, scanSkillsLayout, declaredPluginSurface, parseInitFacts, verifyRegistration, buildContentProbePrompt, classifyContentProbe, renderContentProbe, findNonRegistrableSkillDirs, assembleCompoundingReport, buildDeadwoodReport, compactCmdUsageIfNeeded, measureCmdUsageDepthDays, recordCommandInvocation, resolveCmdUsageRoot, renderDeadwoodReport, CMD_USAGE_LOG_RELATIVE, banditStats, narrowBanditReport, renderBanditHealth,
|
|
25
|
+
assembleCandidates, renderPromotionReport, renderPromotionAdr, normalizePromotionState, nextPromotionState, recordPromotionRunEvidence, isLessonRuleContentAnchor, isOffsetIsoTimestamp, globMatch, promotionAdrRelPath, DEFAULT_WINDOW_DAYS, DEFAULT_PERIODS, MAX_CONTENT_FETCHES, BUILTIN_COVERAGE, decideProvenance, isInsideTree, signManifest, verifyManifest, hashPackBytes, rewriteWorkspaceSpecs, listPackFiles, listSignablePackFiles, assertKeyOutsideTree, decidePublishGate, collectPackageFacts, planReleaseGates, selectAffectedPackages, classifyGateExecutions, buildFailureIssue, buildReleaseNotes, releaseTagName, firstOutputLine, formatPublishError, MANIFEST_NAME, SBOM_NAME, buildArchitectureMap, renderMapHuman, findArchitectureDrift, renderDriftReport, scanWorkspacePackages, loadSubsystemManifest, loadProductVision, checkFeatureAgainstArchitecture, renderArchCheck, planProjectSkills, guidanceForStage, renderInjectionReport, analyzeCorpus, renderRakeReport, renderCriticSection, rakeAsLesson, rakeReward, DEFAULT_RAKE_THRESHOLDS, streamSessionEvents, findLatestTranscript, resolveScanTailTranscript, detectProcessRakes, buildRetro, renderRetro, retroLessonText, PROCESS_SIGNATURES, RETRO_DOMAIN, runRetroTailScan, scanForSetup, buildSetupPlan, scaffoldFromSpec, renderScaffoldPreview, readExistingForScaffold, assembleChallengeContext, buildChallengeBrief, planDiscriminationCheck, classifyDiscrimination, classifyExecutionEvidence, pickAdversaryModel, CHALLENGE_QUESTIONS, loadOutcomes, renderOutcomes, statsForKey, selectAutoCost, recordProvisional, finalizeOutcome, harvestStageOutcomes, recommendModels, planFeed, unfedRuns, GRADE_SUCCESS_FLOOR, COST_LADDER, splitScenarios, budgetPlan, selectWinner, proseScopeOk, renderProseDiff, readScenarioIds, DEFAULT_MAX_JUDGE_RUNS, collectDeliveryFacts, planDeliveryCheck, renderDeliveryBrief, classifyDelivery, isUsablePlaneResult, renderDeliveryReview, scanSkillsLayout, declaredPluginSurface, parseInitFacts, verifyRegistration, buildContentProbePrompt, classifyContentProbe, renderContentProbe, findNonRegistrableSkillDirs, assembleCompoundingReport, buildDeadwoodReport, compactCmdUsageIfNeeded, measureCmdUsageDepthDays, recordCommandInvocation, resolveCmdUsageRoot, renderDeadwoodReport, CMD_USAGE_LOG_RELATIVE, banditStats, narrowBanditReport, renderBanditHealth,
|
|
26
26
|
// Cold-vs-warm EPOCH RUNNER (feature epoch-replay) — orchestrates + scores, never calls a model.
|
|
27
27
|
replayableInstances, buildWorkOrder, buildJudgePrompts, unblindJudgments, verifyWorkOrder, isValidMargin, DIGEST_HONEST_SCOPE, scoreEpochReplay, generateMockOutcomes, renderEpochReplayResult, renderWorkOrderSummary, renderJudgePromptsSummary, WORK_ORDER_KIND, DEFAULT_MOCK_N, DEFAULT_MOCK_SEED, scoreRun, readQeGrade, scoreReceiptToAggregateRow, readScoreAggregateRows, dedupeScoreAggregateRows, buildScoreAggregateReport, renderScoreAggregateReport, recapWindow, decideHorizon, withinWindow, buildRecap, renderRecap, parseSourceManifest, tgPostHtmlIssues, tgVisibleLength, decideTgSend, TG_TEXT_LIMIT, countRecallEventsForRun, unknownFlagNotice, mirrorWriterExplanation, appendRecallUsage, closenessLine, anyAboveFloor, decideNameCheck, renderNameCheck, exportedNamesIn, dispatchedCommandsIn, decideSourceProvenance, renderSourceProvenance, REFUSED_HORIZONS, renderScorecard, renderCompoundingReport, readReinforcementState, readQuarantineState, registrationExitCode, renderRegistrationReport,
|
|
28
28
|
// Smart Backlog (feature smart-backlog) — goal-directed idea pipeline over the Brain vector engine.
|
|
@@ -6459,6 +6459,10 @@ function cmdPublish(options, flags, cwd, writeOutput) {
|
|
|
6459
6459
|
write(` · ${item}`);
|
|
6460
6460
|
}
|
|
6461
6461
|
}
|
|
6462
|
+
for (const warning of report.warnings ?? [])
|
|
6463
|
+
write(` ⚠ warning: ${warning}`);
|
|
6464
|
+
for (const path of report.releaseLineSynced ?? [])
|
|
6465
|
+
write(` ↳ release line synced: ${path}`);
|
|
6462
6466
|
return report.errors > 0 ? 1 : 0;
|
|
6463
6467
|
}
|
|
6464
6468
|
/* ------------------------------------------------------------------ */
|
|
@@ -8936,9 +8940,10 @@ function gatherGuardFacts(op, root, text, storeCap, publishFilter) {
|
|
|
8936
8940
|
const out = volumeGitText(root, ['ls-files', 'packages/@dzhechkov/*/package.json']);
|
|
8937
8941
|
for (const rel of out.split('\n').map((s) => s.trim()).filter(Boolean)) {
|
|
8938
8942
|
try {
|
|
8939
|
-
const
|
|
8943
|
+
const packageJsonText = readFileSync(join(root, rel), 'utf8');
|
|
8944
|
+
const m = JSON.parse(packageJsonText);
|
|
8940
8945
|
manifests.push(m);
|
|
8941
|
-
located.push({ dir: rel.replace(/\/package\.json$/, ''), m });
|
|
8946
|
+
located.push({ dir: rel.replace(/\/package\.json$/, ''), m, text: packageJsonText });
|
|
8942
8947
|
}
|
|
8943
8948
|
catch { /* skip unreadable */ }
|
|
8944
8949
|
}
|
|
@@ -8948,6 +8953,45 @@ function gatherGuardFacts(op, root, text, storeCap, publishFilter) {
|
|
|
8948
8953
|
for (const m of manifests)
|
|
8949
8954
|
if (m.name && typeof m.version === 'string')
|
|
8950
8955
|
versionByName.set(m.name, m.version);
|
|
8956
|
+
// release-line-in-sync: filesystem access belongs in the CLI gatherer. The core evaluator receives
|
|
8957
|
+
// only immutable evidence, so evaluateGuard(facts) stays deterministic and independent of cwd.
|
|
8958
|
+
const coreManifestPath = join(root, 'packages', '@dzhechkov', 'harness-core', 'package.json');
|
|
8959
|
+
const cliManifestPath = join(root, 'packages', '@dzhechkov', 'harness-cli', 'package.json');
|
|
8960
|
+
if (existsSync(coreManifestPath) || existsSync(cliManifestPath)) {
|
|
8961
|
+
const readText = (path) => {
|
|
8962
|
+
try {
|
|
8963
|
+
return readFileSync(path, 'utf8');
|
|
8964
|
+
}
|
|
8965
|
+
catch {
|
|
8966
|
+
return null;
|
|
8967
|
+
}
|
|
8968
|
+
};
|
|
8969
|
+
const readVersion = (path) => {
|
|
8970
|
+
const raw = readText(path);
|
|
8971
|
+
if (raw === null)
|
|
8972
|
+
return null;
|
|
8973
|
+
try {
|
|
8974
|
+
const parsed = JSON.parse(raw);
|
|
8975
|
+
return typeof parsed.version === 'string' && /^\d+\.\d+\.\d+$/.test(parsed.version)
|
|
8976
|
+
? parsed.version
|
|
8977
|
+
: null;
|
|
8978
|
+
}
|
|
8979
|
+
catch {
|
|
8980
|
+
return null;
|
|
8981
|
+
}
|
|
8982
|
+
};
|
|
8983
|
+
facts['releaseLines'] = {
|
|
8984
|
+
coreVersion: readVersion(coreManifestPath),
|
|
8985
|
+
cliVersion: readVersion(cliManifestPath),
|
|
8986
|
+
readmes: [
|
|
8987
|
+
{ path: 'README.md', text: readText(join(root, 'README.md')) },
|
|
8988
|
+
{
|
|
8989
|
+
path: 'packages/@dzhechkov/harness-cli/README.md',
|
|
8990
|
+
text: readText(join(root, 'packages', '@dzhechkov', 'harness-cli', 'README.md')),
|
|
8991
|
+
},
|
|
8992
|
+
],
|
|
8993
|
+
};
|
|
8994
|
+
}
|
|
8951
8995
|
publishPackageRoots.push(...located
|
|
8952
8996
|
.filter(({ dir, m }) => m.private !== true && (publishFilter === undefined
|
|
8953
8997
|
|| publishFilter.length === 0
|
|
@@ -9142,25 +9186,136 @@ function gatherGuardFacts(op, root, text, storeCap, publishFilter) {
|
|
|
9142
9186
|
}
|
|
9143
9187
|
catch { /* нечитаемо — правило молчит */ }
|
|
9144
9188
|
facts['counts'] = gatherReadmeCounts(root);
|
|
9145
|
-
//
|
|
9146
|
-
//
|
|
9189
|
+
// One package-scoped WORKING-TREE diff feeds both readme-first and signature-fresh. A second
|
|
9190
|
+
// porcelain call could observe a different tree and let the two publish guards disagree.
|
|
9191
|
+
let changedPackageFiles;
|
|
9192
|
+
// readme-first: from the WORKING-TREE diff (publishes happen pre-commit here), per package: did
|
|
9193
|
+
// the version FIELD change from HEAD without its README.md changing? A package.json edit alone
|
|
9194
|
+
// says nothing about version; repository/metadata-only edits must not manufacture a bump.
|
|
9147
9195
|
try {
|
|
9148
|
-
const status = execSync('git status --porcelain -- "packages/@dzhechkov/"', { cwd: root, encoding: 'utf-8' });
|
|
9196
|
+
const status = execSync('git status --porcelain -uall -- "packages/@dzhechkov/"', { cwd: root, encoding: 'utf-8' });
|
|
9197
|
+
changedPackageFiles = status
|
|
9198
|
+
.split('\n')
|
|
9199
|
+
.map((line) => line.slice(3).trim())
|
|
9200
|
+
.map((path) => (path.includes(' -> ') ? path.split(' -> ')[1].trim() : path))
|
|
9201
|
+
.filter(Boolean);
|
|
9149
9202
|
const perPack = new Map();
|
|
9150
|
-
for (const
|
|
9151
|
-
const m =
|
|
9203
|
+
for (const rel of changedPackageFiles) {
|
|
9204
|
+
const m = rel.match(/^packages\/@dzhechkov\/([^/]+)\/(.+)$/);
|
|
9152
9205
|
if (!m || !m[1] || !m[2])
|
|
9153
9206
|
continue;
|
|
9154
|
-
const e = perPack.get(m[1]) ?? {
|
|
9155
|
-
if (m[2] === 'package.json')
|
|
9156
|
-
e.pkgJson = true;
|
|
9207
|
+
const e = perPack.get(m[1]) ?? { readme: false };
|
|
9157
9208
|
if (m[2] === 'README.md')
|
|
9158
9209
|
e.readme = true;
|
|
9159
9210
|
perPack.set(m[1], e);
|
|
9160
9211
|
}
|
|
9161
|
-
|
|
9212
|
+
const readVersion = (raw) => {
|
|
9213
|
+
const version = JSON.parse(raw).version;
|
|
9214
|
+
if (typeof version !== 'string')
|
|
9215
|
+
throw new Error('package version is unreadable');
|
|
9216
|
+
return version;
|
|
9217
|
+
};
|
|
9218
|
+
facts['readmeFirst'] = [...perPack.entries()].map(([name, e]) => {
|
|
9219
|
+
const packagePath = `packages/@dzhechkov/${name}/package.json`;
|
|
9220
|
+
let versionBumped = false;
|
|
9221
|
+
let versionUnknown = false;
|
|
9222
|
+
try {
|
|
9223
|
+
const treeVersion = readVersion(readFileSync(join(root, packagePath), 'utf8'));
|
|
9224
|
+
try {
|
|
9225
|
+
const headVersion = readVersion(execFileSync('git', ['show', `HEAD:${packagePath}`], {
|
|
9226
|
+
cwd: root, encoding: 'utf8', stdio: ['ignore', 'pipe', 'pipe'],
|
|
9227
|
+
}));
|
|
9228
|
+
versionBumped = treeVersion !== headVersion;
|
|
9229
|
+
}
|
|
9230
|
+
catch {
|
|
9231
|
+
try {
|
|
9232
|
+
const trackedAtHead = execFileSync('git', ['ls-tree', '--name-only', 'HEAD', '--', packagePath], {
|
|
9233
|
+
cwd: root, encoding: 'utf8', stdio: ['ignore', 'pipe', 'pipe'],
|
|
9234
|
+
}).trim() === packagePath;
|
|
9235
|
+
if (trackedAtHead)
|
|
9236
|
+
versionUnknown = true;
|
|
9237
|
+
else
|
|
9238
|
+
versionBumped = true;
|
|
9239
|
+
}
|
|
9240
|
+
catch {
|
|
9241
|
+
versionUnknown = true;
|
|
9242
|
+
}
|
|
9243
|
+
}
|
|
9244
|
+
}
|
|
9245
|
+
catch {
|
|
9246
|
+
versionUnknown = true;
|
|
9247
|
+
}
|
|
9248
|
+
return {
|
|
9249
|
+
name: '@dzhechkov/' + name,
|
|
9250
|
+
versionBumped,
|
|
9251
|
+
readmeChanged: e.readme,
|
|
9252
|
+
...(versionUnknown ? { versionUnknown: true } : {}),
|
|
9253
|
+
};
|
|
9254
|
+
});
|
|
9162
9255
|
}
|
|
9163
9256
|
catch { /* not a git repo — rule skips */ }
|
|
9257
|
+
// signature-fresh: verify only signed packs whose non-signature files changed in the same
|
|
9258
|
+
// porcelain listing above. Manifest/SBOM churn is the remedy, not another reason to verify.
|
|
9259
|
+
// The trust key and every byte read here stay in the CLI; the guard core receives facts only.
|
|
9260
|
+
const trustRootPath = join(root, TRUST_ROOT_REL);
|
|
9261
|
+
if (changedPackageFiles !== undefined && existsSync(trustRootPath)) {
|
|
9262
|
+
try {
|
|
9263
|
+
const trustRootPem = readFileSync(trustRootPath, 'utf8');
|
|
9264
|
+
const signedPacks = [];
|
|
9265
|
+
for (const { dir, m, text: packageJsonText } of located) {
|
|
9266
|
+
const manifestPath = join(root, dir, MANIFEST_NAME);
|
|
9267
|
+
if (!existsSync(manifestPath))
|
|
9268
|
+
continue;
|
|
9269
|
+
const prefix = dir + '/';
|
|
9270
|
+
const changedPackFiles = new Set(changedPackageFiles
|
|
9271
|
+
.filter((rel) => rel.startsWith(prefix))
|
|
9272
|
+
.map((rel) => rel.slice(prefix.length))
|
|
9273
|
+
.filter((packRel) => packRel !== MANIFEST_NAME && packRel !== SBOM_NAME));
|
|
9274
|
+
const changed = changedPackFiles.size > 0;
|
|
9275
|
+
let ok = null;
|
|
9276
|
+
let failures = [];
|
|
9277
|
+
let note;
|
|
9278
|
+
if (changed) {
|
|
9279
|
+
try {
|
|
9280
|
+
const signed = JSON.parse(readFileSync(manifestPath, 'utf8'));
|
|
9281
|
+
const verified = verifyManifest(join(root, dir), signed, trustRootPem);
|
|
9282
|
+
// A source checkout contains dev files outside package.json#files. They are absent
|
|
9283
|
+
// from the tarball by design, so an unchanged "present but not signed" source file
|
|
9284
|
+
// is not evidence about signature freshness. A changed/new unsigned file stays loud.
|
|
9285
|
+
const relevantFailures = verified.failures.filter((failure) => failure.reason !== 'present in the pack but not signed' || changedPackFiles.has(failure.path));
|
|
9286
|
+
ok = verified.ok || relevantFailures.length === 0;
|
|
9287
|
+
if (!ok && relevantFailures.length > 0 && relevantFailures.every(({ path }) => path === 'package.json')) {
|
|
9288
|
+
const signedPackageHash = signed.manifest?.files?.find(({ path }) => path === 'package.json')?.sha256;
|
|
9289
|
+
if (typeof signedPackageHash === 'string') {
|
|
9290
|
+
const rewritten = rewriteWorkspaceSpecs(packageJsonText, versionByName);
|
|
9291
|
+
// MEASURED 2026-09-10 on keysarium/skills-meta/core: pnpm also removes only
|
|
9292
|
+
// prepublishOnly from the packed scripts table. Keep that I/O-adapter concern
|
|
9293
|
+
// outside the workspace-only core helper.
|
|
9294
|
+
const packedShape = JSON.parse(rewritten);
|
|
9295
|
+
const scripts = packedShape['scripts'];
|
|
9296
|
+
if (scripts !== null && typeof scripts === 'object' && !Array.isArray(scripts)) {
|
|
9297
|
+
delete scripts['prepublishOnly'];
|
|
9298
|
+
}
|
|
9299
|
+
const rewrittenHash = hashPackBytes('package.json', Buffer.from(JSON.stringify(packedShape, null, 2) + '\n'), signed.manifest?.version);
|
|
9300
|
+
if (rewrittenHash === signedPackageHash) {
|
|
9301
|
+
ok = true;
|
|
9302
|
+
note = 'package.json matches after workspace rewrite';
|
|
9303
|
+
}
|
|
9304
|
+
}
|
|
9305
|
+
}
|
|
9306
|
+
failures = relevantFailures.slice(0, 3).map((failure) => `${failure.path}: ${failure.reason}`);
|
|
9307
|
+
}
|
|
9308
|
+
catch (error) {
|
|
9309
|
+
ok = false;
|
|
9310
|
+
failures = [`${MANIFEST_NAME}: ${error instanceof Error ? error.message : String(error)}`];
|
|
9311
|
+
}
|
|
9312
|
+
}
|
|
9313
|
+
signedPacks.push({ name: m.name ?? dir, dir, changed, ok, failures, ...(note !== undefined ? { note } : {}) });
|
|
9314
|
+
}
|
|
9315
|
+
facts['signedPacks'] = signedPacks;
|
|
9316
|
+
}
|
|
9317
|
+
catch { /* unreadable trust root — absence of evidence, so the rule is not established */ }
|
|
9318
|
+
}
|
|
9164
9319
|
// review-round: the same WORKING-TREE diff, asked a different question — does a package that
|
|
9165
9320
|
// bumps its version and changes SOURCE bring a GRADED QE report with it? Scoped to source so a
|
|
9166
9321
|
// docs-only republish is never blocked (ADR-001, features/publish-needs-a-review). A throw here
|