borgmcp-shared 0.4.2 → 0.4.3

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/docs/releasing.md CHANGED
@@ -1,313 +1,126 @@
1
1
  # Publishing `borgmcp-shared`
2
2
 
3
- This repository publishes immutable public releases from a protected GitHub
4
- Actions environment. A release is built once, audited as a tarball, and then
5
- published from that exact tarball. Local publication and publication from an
6
- unreviewed branch are not supported.
7
-
8
- The active release policy is governed by the ratified
9
- `shared-package-consumption`, `borgmcp-shared-coordinator-autonomy`, and
10
- `npm-publish-sole-operator-approval` decisions. This document describes the
11
- operator procedure; it does not authorize a release.
12
-
13
- ## Permanent Repository Configuration
14
-
15
- Configure these controls before creating a release tag:
16
-
17
- 1. Keep `.github/workflows/publish.yml` as the only npm trusted-publisher
18
- workflow. The workflow uses a GitHub-hosted runner, exact Node and npm
19
- versions, no dependency cache, and only `contents: read` plus
20
- `id-token: write` in the protected publish job. npm is installed with
21
- lifecycle scripts disabled under an isolated `${RUNNER_TEMP}` prefix; only
22
- that prefix's bin directory enters `GITHUB_PATH`. Never update the active
23
- global npm installation from within npm itself.
24
- 2. Create a GitHub environment named `npm-publish`. Require an authorized
25
- approval from the sole operator `TheodorStorm`, allow self-review so that the
26
- sole-operator path remains executable, and prevent administrators from
27
- bypassing its protection rules. Store npm bootstrap credentials only in this
28
- environment. This exact shape is ratified by
29
- `npm-publish-sole-operator-approval`; adding any other reviewer or bypass
30
- actor requires a new decision.
31
- 3. Add an active tag ruleset whose only included ref is
32
- `refs/tags/v*.*.*`. Enable creation, update (without fetch-and-merge),
33
- deletion, and non-fast-forward restrictions. The sole bypass actor is the
34
- release-operator user `TheodorStorm` (GitHub user ID `12745431`), with no
35
- role, administrator, team, application, or deploy-key bypass. Require an
36
- annotated tag; the workflow rejects lightweight tags and tags whose commit is
37
- not on `main`.
38
- 4. Set the environment variable `NPM_EXPECTED_OWNER` to `byteventures`, the npm
39
- maintainer returned by `npm view borgmcp maintainers`. Do not infer this value
40
- from package metadata.
41
- 5. Keep the GitHub repository public when provenance is generated. npm cannot
42
- issue provenance for a public package built from a private GitHub repository,
43
- and the workflow stops if the repository is private.
44
- 6. Protect `refs/heads/main` with an active ruleset and no bypass actors. Require
45
- resolved review threads and the `package (20)` and `package (22)` checks from
46
- GitHub Actions application ID `15368`, with strict status checking. Set the
47
- GitHub approval count to zero and disable stale-review dismissal, code-owner
48
- review, and last-push approval: the separately recorded cube CR, Security,
49
- and Release Quality gates are the human evidence, while a GitHub approval
50
- requirement would be inoperable for the sole repository operator. Allow
51
- merge commits only and protect deletion and non-fast-forward operations. Do
52
- not add a restrictive update rule, which would block normal pull-request
53
- merges without a bypass.
54
- 7. Restrict Actions to selected GitHub-owned actions and require full commit-SHA
55
- pins. Do not allow all verified Marketplace publishers or any custom pattern.
56
- The CI and publish workflows need only `actions/checkout`,
57
- `actions/setup-node`, `actions/upload-artifact`, and
58
- `actions/download-artifact`, each pinned in source. Keep workflow tokens
59
- read-only and prohibit them from approving pull requests.
60
- 8. Enable GitHub private vulnerability reporting, secret scanning, push
61
- protection, and Dependabot security updates unconditionally. Enable secret
62
- validity checks and non-provider pattern detection whenever the organization
63
- plan licenses them. GitHub requires a paid plan with GitHub Secret Protection
64
- for [validity checks](https://docs.github.com/en/code-security/how-tos/secure-your-secrets/customize-leak-detection/enable-validity-checks)
65
- and [non-provider patterns](https://docs.github.com/en/code-security/secret-scanning/using-advanced-secret-scanning-and-push-protection-features/non-provider-patterns/enabling-secret-scanning-for-non-provider-patterns).
66
- The configuration guard accepts those two controls as disabled only while the
67
- live organization plan is exactly `free`; a plan change makes them mandatory.
68
- `SECURITY.md` directs reporters to the private reporting path, so disabled
69
- reporting is always a release-blocking documentation failure.
70
-
71
- The environment approval is the final technical control. It appears only on the
72
- `publish` job, after `validate` has verified the SR approval tuple. Approval must
73
- remain pending while Security reviews the artifact produced by the `verify` job.
74
- GitHub's ephemeral workflow token cannot read every repository-administration
75
- setting checked by `scripts/verify-release-configuration.mjs`. An authorized
76
- operator must run the guard with an administration-capable token before creating
77
- the tag and again immediately before approving the environment:
3
+ This repository publishes immutable public releases through one protected workflow job
4
+ in GitHub Actions. The active `minimal-package-release-assurance` decision replaces the
5
+ former cross-run artifact approval protocol. This runbook describes the current
6
+ operator procedure; it does not authorize a tag or publication.
7
+
8
+ ## Assurance Boundary
9
+
10
+ The release lane has one build, test, package, and publication authority:
11
+ `.github/workflows/publish.yml` on an annotated `v*.*.*` tag. The job:
12
+
13
+ 1. verifies the public repository context, exact package version, annotated tag,
14
+ tag commit, and ancestry on protected `main`;
15
+ 2. installs locked dependencies without lifecycle scripts and runs dependency
16
+ audit, type checks, the full test suite, one clean build, and generated-output
17
+ drift detection;
18
+ 3. creates one local tarball, enforces the packed-artifact policy, and installs
19
+ that tarball into a clean consumer that imports every public export;
20
+ 4. rejects an existing immutable version or a package not owned solely by the
21
+ configured npm owner before any registry mutation;
22
+ 5. publishes that exact local tarball through npm Trusted Publishing with
23
+ provenance; and
24
+ 6. uses bounded registry-propagation retries to compare the published
25
+ `dist.integrity` with the tarball, then installs the exact registry version
26
+ with scripts disabled and runs `npm audit signatures`.
27
+
28
+ npm and GitHub verify the registry signature and publish attestation. The
29
+ repository does not reconstruct DSSE or SLSA statements, transfer approval
30
+ tuples between runs, rebuild in a second job, or place checksum, SBOM, and report
31
+ bundles on the critical publication path. SBOM portability remains covered by
32
+ CI and the repository's dedicated deterministic SBOM tests.
33
+
34
+ ## Permanent Configuration
35
+
36
+ Keep these controls in place:
37
+
38
+ 1. `publish.yml` is the only npm Trusted Publisher workflow for organization
39
+ `Byte-Ventures`, repository `borg-mcp-shared`, and environment `npm-publish`.
40
+ 2. The `npm-publish` environment requires the authorized sole operator
41
+ `TheodorStorm`, permits that operator's self-review, prevents administrator
42
+ bypass, and allows only protected `v*.*.*` tags.
43
+ 3. `NPM_EXPECTED_OWNER` is `byteventures`. It comes from the live npm package
44
+ maintainer record, not package metadata.
45
+ 4. No `NPM_TOKEN`, `NODE_AUTH_TOKEN`, or committed `.npmrc` participates in an
46
+ owned-package release. Authentication is the job's short-lived OIDC exchange.
47
+ 5. The publish job uses a GitHub-hosted runner with only `contents: read` and
48
+ `id-token: write`. Actions are GitHub-owned and pinned to full commit SHAs.
49
+ 6. Protected `main`, the release-tag ruleset, private vulnerability reporting,
50
+ secret scanning, push protection, and dependency security updates remain
51
+ enabled as checked by `scripts/verify-release-configuration.mjs`. Secret
52
+ scanning validity checks and non-provider patterns remain mandatory whenever
53
+ the organization plan licenses them.
54
+
55
+ Before creating a tag and again before approving the environment, an authorized
56
+ operator runs:
78
57
 
79
58
  ```sh
80
59
  GITHUB_TOKEN="$(gh auth token)" node scripts/verify-release-configuration.mjs
81
60
  ```
82
61
 
83
- The token is read from the operator's credential store and must not be written
84
- to the repository, an artifact, or workflow output. Any guard failure blocks the
85
- tag or environment approval.
86
-
87
- Every release and verification-only run must be a first attempt. The workflow
88
- logs `GITHUB_RUN_ID` and `GITHUB_RUN_ATTEMPT`, rejects any attempt other than `1`
89
- before dependency installation, and includes the same values in the uploaded
90
- `RUN_EVIDENCE` file. Never use the Actions rerun controls to advance a failed
91
- immutable tag or proof run.
92
-
93
- All three jobs reject a repository-root `.npmrc` before their first npm command. The
94
- exact npm bootstrap uses isolated runner-temp prefix, user config, and cache
95
- paths, forces `https://registry.npmjs.org`, disables scripts, and verifies both
96
- the installed npm version and registry before adding its bin directory to
97
- `GITHUB_PATH`.
98
-
99
- ## First-Publish Bootstrap
100
-
101
- npm trusted publishing cannot be configured until the unscoped package exists.
102
- The initial `v0.2.0` bootstrap run, `29353763609`, failed during verification
103
- before producing an artifact or reaching publication. The failed `v0.2.0` tag is
104
- immutable and MUST NOT be moved, reused, or rerun. The separately authorized
105
- `v0.2.1` tag run, `29355823822`, also failed verification before dependency
106
- installation or artifact creation because the checkout action replaced its local
107
- annotated-tag ref with the peeled commit. The remote `v0.2.1` tag remains valid
108
- and immutable and MUST NOT be moved, reused, or rerun.
109
-
110
- The first protected-main verification-only proof run, `29356980492`, confirmed
111
- the repaired tag/source trust checks, then failed before artifact upload because
112
- npm 11 interpreted the bare `release/<tarball>` argument as a package/GitHub spec
113
- instead of a local file. It produced no auditable artifact and MUST NOT be rerun.
114
- The workflow now passes generated tarballs to both npm dry-run and publication as
115
- explicit `./release/<tarball>` filesystem paths.
116
-
117
- The next protected-main proof run, `29357632667`, passed every verification gate
118
- against immutable `v0.2.1`, structurally skipped the publish job, and produced an
119
- exact artifact that passed Security audit. This proved the corrected tag,
120
- protected-main, input, artifact, and npm local-file handling without reusing the
121
- tag for publication.
122
-
123
- Under the ratified `borgmcp-shared-recovery-version` decision, `0.2.2` is the
124
- selected recovery version. The source bump does not itself authorize a tag,
125
- environment approval, or publication.
126
-
127
- Run `29360398007` published `borgmcp-shared@0.2.2` from the exact approved
128
- artifact, and the registry integrity and maintainer matched that artifact. The
129
- workflow then failed during immediate postpublish verification when the package
130
- ownership read returned HTTP 404 before registry propagation completed. The run
131
- and `v0.2.2` tag are immutable and MUST NOT be rerun, moved, or reused. Consumer
132
- migration was blocked until provenance and signatures were independently verified
133
- and Security approved the recovery evidence.
134
-
135
- Recover out of band without rerunning the workflow:
136
-
137
- 1. Download artifact `8321897865` from run `29360398007` and recheck its recorded
138
- ZIP digest, `RUN_EVIDENCE`, tarball SHA-512, and artifact verifier report.
139
- 2. With `GITHUB_SHA=508f2dc88658d8e00ff036b7ce6913fcfbef239b` and
140
- `NPM_EXPECTED_OWNER=byteventures`, run
141
- `node scripts/verify-registry-release.mjs postpublish <audited-tarball>`. The
142
- verifier retries only transient HTTP 404 propagation responses. Its production
143
- envelope performs at most 18 reads over approximately three and a half minutes
144
- (1, 2, 4, and 8 second waits, then a 15 second cap). Non-404 failures and
145
- integrity, owner, or provenance mismatches remain immediate terminal failures.
146
- 3. Install exact `borgmcp-shared@0.2.2` from the registry into a clean temporary
147
- prefix with scripts disabled and run `npm audit signatures` against that
148
- prefix.
149
- 4. Record the independent integrity, ownership, signed-provenance, and signature
150
- evidence for a fresh Security verdict before changing any consumer dependency.
151
-
152
- That recovery completed successfully: the registry tarball is byte-identical to
153
- the audited artifact, its sole maintainer is `byteventures`, the signed in-toto
154
- SLSA provenance binds the protected workflow/tag/commit/run, and npm verified one
155
- registry signature plus one publish attestation. Security approved the recovery
156
- evidence. Complete the bootstrap credential and Trusted Publisher cleanup below
157
- before migrating consumers.
158
-
159
- The eventual first publication will use one temporary credential while still
160
- generating provenance from GitHub Actions.
161
-
162
- Before creating the tag, the release operator must verify all of the following:
163
-
164
- - The npm account is the account that owns `borgmcp`, uses authentication-and-
165
- writes 2FA, and has tested, protected recovery methods.
166
- - `borgmcp-shared` is still unclaimed. An `E404` is expected. Any package or
167
- ownership result that differs from the reviewed state is a stop condition.
168
- - Code Review, load-bearing Security Review, and Release Quality approved the
169
- exact commit on `main`.
170
- - The Queen explicitly authorized generating the final release artifact. This
171
- authorization does not by itself approve the later environment deployment.
172
-
173
- Create a short-lived, least-privilege npm publish token under the verified owner
174
- account. Store it as the `NPM_TOKEN` secret in the `npm-publish` environment;
175
- never place it in repository variables, workflow files, shell history,
176
- `package.json`, a committed `.npmrc`, or an issue. Set the protected environment
177
- variable `ALLOW_UNCLAIMED_FIRST_PUBLISH` to `true` only for this bootstrap.
178
-
179
- The `0.2.2` package, lockfile, runbook, and version assertions must pass fresh CR,
180
- Security, and Release Quality gates and merge to protected `main` before the
181
- Coordinator creates its matching annotated tag under
182
- `borgmcp-shared-first-publish-autonomy`. The tag starts the workflow but does not
183
- immediately publish. The unprivileged `verify` job performs the following gates
184
- first:
185
-
186
- - verifies the public repository, annotated tag, exact package version, and
187
- ancestry on `main`;
188
- - installs the lockfile without lifecycle scripts and runs audit, type checks,
189
- all tests, a clean build, and the tracked-`dist` drift check;
190
- - creates one tarball with lifecycle scripts disabled;
191
- - enforces the explicit public file allowlist, legal files, dependency and
192
- lifecycle policy, size limits, and resolvable source maps;
193
- - exercises npm's publish metadata in dry-run mode; and
194
- - installs the exact tarball with scripts disabled in a clean consumer, verifies
195
- its production tree, and imports every reviewed public export; and
196
- - uploads the tarball, verifier report, SHA-512 checksum, SBOM, and
197
- `RUN_EVIDENCE` for seven days.
198
-
199
- Security must download and audit that exact workflow artifact. After Security
200
- approves the tarball, Release Quality confirms the operator procedure, and the
201
- Queen explicitly authorizes the public flip, the Coordinator writes the SR
202
- approval tuple (`ARTIFACT_SR_SHA512`, `ARTIFACT_SR_RUN_ID`,
203
- `ARTIFACT_SR_RUN_ATTEMPT`) to environment variables and dispatches the
204
- `publish.yml` workflow with the tag. The `validate` job runs first (outside
205
- the `npm-publish` environment): it re-verifies the source, queries the source
206
- run's workflow path, tag, conclusion, and attempt via the GitHub API, downloads
207
- the artifact, binds the SR tuple to the exact tarball, and confirms run identity.
208
- Only after `validate` succeeds does the `publish` job run, which surfaces the
209
- `npm-publish` environment approval dialog. The `publish` job re-downloads and
210
- checksum-verifies the same artifact, re-binds the SR tuple, repeats the artifact
211
- verifier, checks that `0.2.2` is absent and the name is unclaimed as expected,
212
- and publishes only the downloaded tarball with `--access public --provenance`.
213
-
214
- Immediately after a successful first publish:
215
-
216
- 1. Confirm the workflow's registry-integrity, owner, and SLSA provenance checks
217
- passed before changing any consumer dependency.
218
- 2. Configure npm's trusted publisher for organization `Byte-Ventures`, repository
219
- `borg-mcp-shared`, workflow filename `publish.yml`, environment
220
- `npm-publish`, and the `npm publish` action.
221
- 3. Remove the `NPM_TOKEN` environment secret, revoke the bootstrap token at npm,
222
- and set `ALLOW_UNCLAIMED_FIRST_PUBLISH` to `false`.
223
- 4. Configure npm publishing access to require 2FA and disallow traditional
224
- tokens. Future releases authenticate through short-lived OIDC credentials.
225
- 5. Only then replace consumers' exact Git SHA dependencies with
226
- `borgmcp-shared@^0.2.0` and commit their registry lockfiles.
227
-
228
- ## Later Releases
229
-
230
- ### 0.4.2 Cross-Platform SBOM Recovery
231
-
232
- `borgmcp-shared@0.4.0` is the published, immutable clean-slate v2 contract, but
233
- its registry artifact was built before the public package's local/self-hosted
234
- topology cleanup. The immutable `v0.4.1` run `29701429995` built the cleaned
235
- artifact, but independent macOS verification proved that the SBOM verifier used
236
- the auditor's installed optional-dependency tree instead of a deterministic
237
- release graph. The `v0.4.1` tag, run, and artifact are failed evidence: never
238
- publish, move, reuse, rerun, or substitute them.
239
-
240
- Version `0.4.2` carries the reviewed cleanup with a lockfile-derived SBOM graph
241
- for the fixed release target `{os: linux, cpu: x64, libc: glibc}`. It does not
242
- change the protocol tag or runtime behavior. This source now identifies `0.4.2`.
243
- The reviewed recovery bump does not authorize creating `v0.4.2` or publishing
244
- the package.
245
-
246
- Before a separately authorized `v0.4.2` tag is created:
247
-
248
- 1. The exact `0.4.2` source commit must be merged to protected `main` after Code
249
- Review, Security, and Release Quality approve the package identity, public
250
- API, generated output, and release documentation.
251
- 2. The package and root lockfile, `SHARED_PACKAGE_VERSION`, packed-artifact and
252
- SBOM verifiers, generated declarations, and version assertions must all
253
- identify `0.4.2`. The protocol tag remains unchanged.
254
- 3. The protected workflow must build one exact tarball and pass its full source,
255
- test, audit, public-export, source-map, install/import, dry-run, lock-derived
256
- CycloneDX SBOM, integrity, and provenance gates. Security must approve that
257
- exact workflow artifact.
258
- 4. The `0.4.2` workflow must generate a CycloneDX SBOM, canonicalize npm's
259
- checkout-derived root display name to the already-verified manifest name,
260
- and validate every component's exact canonical registry tarball URL, single
261
- matching CycloneDX distribution reference, purl, and lock SHA-512 plus the
262
- exact lockfile-derived release-target graph and zero package runtime
263
- dependencies. The graph starts from root development dependencies, follows
264
- required dependencies and peers, includes only target-compatible optional
265
- dependencies, and includes optional peers only when another reachable edge
266
- installs them. Root manifest and lock selectors must match and permit the
267
- fixed target. Verification must not inspect the auditor's operating system,
268
- installed dependency tree, or `node_modules`. The tarball, SBOM, and SBOM
269
- validation report must be checksummed and uploaded together for Security
270
- audit.
271
- 5. The tag and publication each require their own explicit authorization. A
272
- source-version approval, merge, or successful verification run grants neither.
273
-
274
- After registry publication and independent integrity/provenance verification,
275
- the first borgmcp client and borgmcp-server releases must pin exact
276
- `borgmcp-shared@0.4.2` and commit their registry lockfiles. They must not ship a
277
- Git dependency, a version range that can resolve to the pre-cleanup artifact, or
278
- a fallback to the incompatible `0.3.0` v1 enrollment response.
279
-
280
- Later releases follow the same source gates, annotated protected tag, exact
281
- tarball audit, Coordinator authorization under the ratified shared release
282
- autonomy, and environment approval. The registry
283
- preflight requires the package to be owned by `NPM_EXPECTED_OWNER` and rejects
284
- an existing target version. It also fails if
285
- `ALLOW_UNCLAIMED_FIRST_PUBLISH` is not `false` or any `NPM_TOKEN` remains;
286
- npm must exchange the workflow's OIDC identity through the configured trusted
287
- publisher.
288
-
289
- ## Stop and Recovery Conditions
290
-
291
- Stop without approving the environment when any of these conditions occurs:
292
-
293
- - the repository is private, the tag is lightweight or unprotected, the tag
294
- does not exactly match `v<package version>`, or its commit is not on `main`;
295
- - the approved commit, tag target, tarball checksum, or audit artifact differs;
296
- - `GITHUB_RUN_ATTEMPT` is not `1`, or run/attempt evidence is missing;
297
- - tests, audit, build, tracked output, artifact policy, legal metadata, or dry
298
- run fails;
299
- - the npm name, expected owner, account 2FA, recovery methods, credential scope,
300
- trusted-publisher configuration, or environment protection cannot be verified;
301
- - the target version already exists, npm returns anything other than the
302
- expected ownership/availability response, or npm/GitHub is degraded; or
303
- - final CR, Security, Release Quality, exact-tarball Security approval, or Queen
304
- authorization is missing.
305
-
306
- npm versions are immutable. Never retry by overwriting any published version,
307
- moving a release tag, force-pushing a branch, or publishing from a local rebuild.
308
- A failed verification before publication requires fixing the source and
309
- beginning again with a new reviewed version/tag plan. If npm accepted the version
310
- but integrity or provenance verification failed, block every consumer migration,
311
- preserve the workflow logs and artifact, and escalate as a release incident. Do not unpublish,
312
- deprecate, or publish a replacement version without a separately reviewed and
313
- authorized recovery decision.
62
+ The token must remain in the operator credential store. Never write it to the
63
+ repository, workflow output, artifact, issue, or shell history.
64
+
65
+ ## Release Procedure
66
+
67
+ 1. Merge the exact version, lockfile, generated output, and release documentation
68
+ to protected `main` after the required exact-SHA Code Review, Security Review,
69
+ and Release Quality gates.
70
+ 2. Verify repository controls with the configuration guard above. Confirm the
71
+ target version does not already exist and `borgmcp-shared` is owned solely by
72
+ `byteventures`.
73
+ 3. Obtain the separately required exact-commit tag authorization. Create and push
74
+ one annotated `v<package-version>` tag at that protected-main commit.
75
+ 4. The tag starts the single publish job and leaves it pending at the protected
76
+ `npm-publish` environment. Do not use workflow rerun controls; every immutable
77
+ tag gets one first attempt.
78
+ 5. Obtain the separately required environment approval, then approve that exact
79
+ pending job. Approval does not permit a local rebuild or alternate artifact.
80
+ 6. Require every job step to pass, including exact registry integrity and
81
+ `npm audit signatures`, before announcing the version or updating consumers.
82
+
83
+ The workflow publishes only `./release/<tarball>`. It never publishes from the
84
+ repository directory, a package name, a URL, a prior workflow artifact, or a
85
+ locally rebuilt replacement.
86
+
87
+ ## Stop And Recovery
88
+
89
+ Stop before publication when source identity, tag ancestry, repository
90
+ visibility, environment protection, expected owner, target-version absence,
91
+ tests, build output, tarball policy, clean-consumer imports, or Trusted Publishing
92
+ configuration cannot be verified.
93
+
94
+ If a first-attempt tag run fails before npm accepts the version, preserve the tag
95
+ and run as immutable evidence. Fix the source and begin a separately reviewed and
96
+ authorized version/tag plan. Never move, reuse, rerun, or force-update the failed
97
+ tag.
98
+
99
+ If npm accepts the version but a bounded integrity or signature check fails, do
100
+ not rerun or republish. Preserve the run, inspect the live registry integrity and
101
+ `npm audit signatures` result, and require an explicit recovery decision before
102
+ consumer adoption. npm versions are immutable; never overwrite, unpublish, or
103
+ silently substitute a replacement.
104
+
105
+ ## Immutable Historical Evidence
106
+
107
+ These records remain evidence, not reusable release inputs:
108
+
109
+ - `v0.2.0` run `29353763609` and `v0.2.1` run `29355823822` failed before
110
+ artifact creation or publication.
111
+ - Protected-main proof runs `29356980492` and `29357632667` diagnosed and then
112
+ verified the earlier tag/source and local-file handling. They are not publish
113
+ artifacts.
114
+ - Run `29360398007` published `borgmcp-shared@0.2.2`; its initial ownership
115
+ readback hit registry propagation. Independent integrity, ownership,
116
+ provenance, and npm signature verification completed before consumer adoption.
117
+ - `v0.4.1` run `29701429995` exposed a non-deterministic cross-platform SBOM
118
+ audit path and was never published.
119
+ - `borgmcp-shared@0.4.2` is accepted as published and verified. Its registry
120
+ integrity matches the audited tarball and npm verifies its signature and
121
+ attestation. Publish run `29729515410` must not be rerun; the failed custom
122
+ postpublish check reconstructed the wrong workflow identity and is the reason
123
+ that machinery was removed.
124
+
125
+ This source now identifies `0.4.3`. Its release requires reviewed source and
126
+ artifact gates plus explicit publication authorization.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "borgmcp-shared",
3
- "version": "0.4.2",
3
+ "version": "0.4.3",
4
4
  "description": "Shared protocol, domain, templates, and conformance contracts for Borg MCP implementations.",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -1543,9 +1543,9 @@ export async function runAdapterConformance(
1543
1543
  const expiredCredential = await environment.admin.issueManagedDroneSession(expiredDrone);
1544
1544
  await environment.admin.revokeManagedDroneSession(revokedDrone);
1545
1545
  await environment.admin.expireManagedDroneSession(expiredDrone);
1546
- for (const [label, credential] of [
1547
- ['revoked', revokedCredential],
1548
- ['expired', expiredCredential],
1546
+ for (const [label, credential, code] of [
1547
+ ['revoked', revokedCredential, ErrorCode.SESSION_REVOKED],
1548
+ ['expired', expiredCredential, ErrorCode.AUTH_EXPIRED],
1549
1549
  ] as const) {
1550
1550
  expectError(
1551
1551
  await environment.operations.read(
@@ -1554,14 +1554,15 @@ export async function runAdapterConformance(
1554
1554
  createProtocolEnvelope(`${label}-seat-probe`, { cursor: null, limit: 1 }),
1555
1555
  ),
1556
1556
  401,
1557
- ErrorCode.SESSION_REVOKED,
1557
+ code,
1558
1558
  `${label} seat probe`,
1559
1559
  );
1560
1560
  }
1561
1561
  return {
1562
1562
  revoked_status: 401,
1563
1563
  expired_status: 401,
1564
- code: ErrorCode.SESSION_REVOKED,
1564
+ revoked_code: ErrorCode.SESSION_REVOKED,
1565
+ expired_code: ErrorCode.AUTH_EXPIRED,
1565
1566
  };
1566
1567
  });
1567
1568
 
@@ -2,7 +2,7 @@ import { ErrorCode } from './errors.js';
2
2
  import { PROTOCOL_VERSION, type ProtocolVersion } from './version.js';
3
3
 
4
4
  export const SHARED_PACKAGE_NAME = 'borgmcp-shared' as const;
5
- export const SHARED_PACKAGE_VERSION = '0.4.2' as const;
5
+ export const SHARED_PACKAGE_VERSION = '0.4.3' as const;
6
6
 
7
7
  export const HEALTH_PATH = '/healthz' as const;
8
8
  export const PROTOCOL_INFO_PATH = '/api/protocol' as const;
@@ -28,6 +28,9 @@ export const PROTOCOL_HTTP_CONTRACT = {
28
28
  },
29
29
  auth_missing_status: 401,
30
30
  auth_invalid_status: 401,
31
+ auth_expired_status: 401,
32
+ session_revoked_status: 401,
33
+ session_rejected_status: 401,
31
34
  cursor_expired_status: 410,
32
35
  drone_evicted_status: 410,
33
36
  content_too_large_status: 413,
@@ -24,8 +24,9 @@ export enum ErrorCode {
24
24
  /**
25
25
  * The presented session bearer does not match the seat it targets: a fresh or
26
26
  * non-matching bearer against an already-bound active seat. Distinct from
27
- * SESSION_REVOKED (a formerly valid credential that was explicitly revoked or
28
- * expired). Carried by the server's typed 401 takeover rejection.
27
+ * SESSION_REVOKED (a formerly valid credential that was explicitly revoked).
28
+ * AUTH_EXPIRED is the only recoverable expired-session outcome. Carried by the
29
+ * server's typed 401 takeover rejection.
29
30
  */
30
31
  SESSION_REJECTED = 'SESSION_REJECTED',
31
32
  }