machine-bridge-mcp 2.0.0 → 3.0.0-beta.9

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.
Files changed (143) hide show
  1. package/CHANGELOG.md +101 -0
  2. package/CONTRIBUTING.md +20 -25
  3. package/README.md +21 -14
  4. package/SECURITY.md +147 -123
  5. package/browser-extension/manifest.json +3 -2
  6. package/browser-extension/service-worker.js +31 -12
  7. package/docs/ARCHITECTURE.md +27 -13
  8. package/docs/AUDIT.md +85 -2
  9. package/docs/CLIENTS.md +2 -2
  10. package/docs/ENGINEERING.md +9 -3
  11. package/docs/GETTING_STARTED.md +10 -9
  12. package/docs/LOCAL_AUTHORIZATION.md +115 -72
  13. package/docs/LOGGING.md +12 -3
  14. package/docs/MANAGED_JOBS.md +24 -29
  15. package/docs/MULTI_ACCOUNT.md +98 -37
  16. package/docs/OPERATIONS.md +33 -22
  17. package/docs/OVERVIEW.md +7 -7
  18. package/docs/PROJECT_STANDARDS.md +9 -5
  19. package/docs/RELEASING.md +171 -64
  20. package/docs/TESTING.md +19 -7
  21. package/docs/THREAT_MODEL.md +138 -67
  22. package/docs/TOOL_REFERENCE.md +2 -2
  23. package/docs/UPGRADING.md +102 -18
  24. package/native/macos/MachineBridgeTrustBroker.swift +233 -0
  25. package/package.json +36 -5
  26. package/scripts/candidate-runtime-store.mjs +38 -0
  27. package/scripts/check-plan.mjs +19 -0
  28. package/scripts/check-runner.mjs +4 -1
  29. package/scripts/commit-message-check.mjs +5 -2
  30. package/scripts/coverage-check.mjs +30 -2
  31. package/scripts/github-push.mjs +11 -0
  32. package/scripts/github-release.mjs +38 -7
  33. package/scripts/install-published-prerelease.mjs +167 -0
  34. package/scripts/local-release-acceptance.mjs +23 -12
  35. package/scripts/npm-publication-policy.mjs +16 -0
  36. package/scripts/prerelease-activation.mjs +79 -0
  37. package/scripts/privacy-check.mjs +7 -5
  38. package/scripts/promotion-digest.mjs +121 -0
  39. package/scripts/publish-npm.mjs +51 -0
  40. package/scripts/published-release.mjs +80 -0
  41. package/scripts/release-acceptance.mjs +30 -1
  42. package/scripts/release-candidate-manifest.mjs +40 -0
  43. package/scripts/release-channel.mjs +106 -0
  44. package/scripts/release-impact-check.mjs +12 -22
  45. package/scripts/release-soak.mjs +237 -0
  46. package/scripts/start-release-candidate.mjs +113 -7
  47. package/src/local/account-access.mjs +6 -0
  48. package/src/local/account-admin.mjs +34 -16
  49. package/src/local/agent-context.mjs +45 -42
  50. package/src/local/app-automation.mjs +9 -4
  51. package/src/local/authority-context.mjs +106 -0
  52. package/src/local/browser-bridge-http.mjs +4 -1
  53. package/src/local/browser-bridge.mjs +14 -9
  54. package/src/local/browser-broker-routes.mjs +4 -0
  55. package/src/local/browser-broker-server.mjs +5 -4
  56. package/src/local/browser-extension-identity.mjs +50 -0
  57. package/src/local/browser-extension-protocol.mjs +9 -4
  58. package/src/local/browser-operation-service.mjs +7 -0
  59. package/src/local/browser-pairing-http.mjs +36 -0
  60. package/src/local/browser-pairing-store.mjs +56 -47
  61. package/src/local/cli-account-admin.mjs +41 -7
  62. package/src/local/cli-activate.mjs +90 -0
  63. package/src/local/cli-approval.mjs +14 -58
  64. package/src/local/cli-local-admin.mjs +5 -15
  65. package/src/local/cli-options.mjs +11 -7
  66. package/src/local/cli-service.mjs +35 -5
  67. package/src/local/cli.mjs +112 -58
  68. package/src/local/daemon-process.mjs +6 -0
  69. package/src/local/delegated-process-sandbox.mjs +147 -0
  70. package/src/local/device-identity.mjs +157 -48
  71. package/src/local/device-root-provider.mjs +87 -0
  72. package/src/local/errors.mjs +25 -3
  73. package/src/local/git-service.mjs +16 -15
  74. package/src/local/job-runner.mjs +35 -27
  75. package/src/local/log.mjs +14 -1
  76. package/src/local/macos-trust-broker.mjs +320 -0
  77. package/src/local/managed-job-lock.mjs +18 -0
  78. package/src/local/managed-job-projection.mjs +9 -1
  79. package/src/local/managed-job-runner.mjs +13 -1
  80. package/src/local/managed-job-storage.mjs +2 -1
  81. package/src/local/managed-job-terminal.mjs +138 -0
  82. package/src/local/managed-jobs.mjs +88 -32
  83. package/src/local/operation-authorization.mjs +75 -239
  84. package/src/local/operation-risk.mjs +28 -0
  85. package/src/local/operation-state-lock.mjs +7 -86
  86. package/src/local/owner-state-lock.mjs +104 -0
  87. package/src/local/policy.mjs +19 -0
  88. package/src/local/process-execution.mjs +21 -9
  89. package/src/local/process-sessions.mjs +27 -17
  90. package/src/local/process-tracker.mjs +30 -6
  91. package/src/local/process-tree-ownership.mjs +59 -0
  92. package/src/local/process-tree.mjs +22 -18
  93. package/src/local/relay-connection.mjs +47 -35
  94. package/src/local/relay-diagnostics.mjs +65 -0
  95. package/src/local/remote-configuration.mjs +48 -0
  96. package/src/local/runtime-activation.mjs +141 -0
  97. package/src/local/runtime-diagnostics.mjs +21 -0
  98. package/src/local/runtime-relay.mjs +9 -8
  99. package/src/local/runtime-reporting.mjs +8 -3
  100. package/src/local/runtime-tool-handlers.mjs +8 -8
  101. package/src/local/runtime.mjs +73 -39
  102. package/src/local/secure-file.mjs +5 -1
  103. package/src/local/security-audit-log.mjs +204 -0
  104. package/src/local/service-convergence.mjs +17 -1
  105. package/src/local/service-ownership.mjs +17 -0
  106. package/src/local/service-restart-handoff.mjs +50 -0
  107. package/src/local/service-restart-scheduler.mjs +49 -0
  108. package/src/local/service-status.mjs +47 -0
  109. package/src/local/service.mjs +142 -43
  110. package/src/local/state-inventory.mjs +21 -3
  111. package/src/local/state.mjs +155 -17
  112. package/src/local/stdio.mjs +5 -0
  113. package/src/local/tool-executor.mjs +39 -6
  114. package/src/local/tool-result-boundary.mjs +51 -0
  115. package/src/local/tools.mjs +1 -0
  116. package/src/local/trusted-executable.mjs +53 -0
  117. package/src/local/trusted-git-executable.mjs +34 -0
  118. package/src/local/trusted-github-cli.mjs +24 -0
  119. package/src/local/windows-service.mjs +20 -0
  120. package/src/local/worker-deployment.mjs +3 -4
  121. package/src/local/worker-secret-file.mjs +2 -2
  122. package/src/local/workspace-file-service.mjs +34 -31
  123. package/src/shared/admin-auth.d.mts +2 -1
  124. package/src/shared/admin-auth.mjs +3 -3
  125. package/src/shared/device-session-auth.d.mts +20 -0
  126. package/src/shared/device-session-auth.mjs +51 -0
  127. package/src/shared/server-metadata.json +1 -1
  128. package/src/shared/tool-catalog.json +2 -2
  129. package/src/worker/account-admin.ts +23 -22
  130. package/src/worker/authority.ts +9 -2
  131. package/src/worker/daemon-auth.ts +45 -67
  132. package/src/worker/daemon-sockets.ts +12 -2
  133. package/src/worker/device-session-verifier.ts +129 -0
  134. package/src/worker/dpop.ts +151 -0
  135. package/src/worker/http.ts +47 -16
  136. package/src/worker/index.ts +53 -16
  137. package/src/worker/nonce-store.ts +1 -5
  138. package/src/worker/oauth-client-admin.ts +45 -0
  139. package/src/worker/oauth-controller.ts +55 -6
  140. package/src/worker/oauth-refresh-families.ts +21 -7
  141. package/src/worker/oauth-state.ts +6 -0
  142. package/src/worker/oauth-tokens.ts +28 -8
  143. package/src/worker/websocket-protocol.ts +8 -2
package/CHANGELOG.md CHANGED
@@ -1,5 +1,106 @@
1
1
  # Changelog
2
2
 
3
+ ## 3.0.0-beta.9 - 2026-07-22
4
+
5
+ ### Cross-platform release-gate repair
6
+
7
+ - Block `3.0.0-beta.8` after owner activation and acceptance because pull-request CI found three release-blocking defects that local macOS verification could not establish: the Windows trusted-Git regression forced Linux permission semantics onto NTFS, Ubuntu coverage did not execute the macOS delegated-sandbox behavior probe, and CodeQL rejected an unused cleanup-path assignment.
8
+ - Make trusted-Git regression coverage use the actual host platform while retaining POSIX group-writable rejection on Unix. Make macOS sandbox availability accept explicit platform and executable-presence probes for deterministic cross-platform tests, and exercise the complete read/write/outside-path/Keychain behavior matrix with a synthetic process boundary.
9
+ - Remove the unused activation cleanup assignment rather than adding a CodeQL exception. These changes require a new exact candidate, live activation, acceptance, and full prerelease gate.
10
+
11
+ ## 3.0.0-beta.8 - 2026-07-22
12
+
13
+ ### Candidate repository hygiene correction
14
+
15
+ - Block `3.0.0-beta.7` after owner-machine acceptance. A full staged-tree `git diff --cached --check` exposed an extra blank line at EOF in the newly added Worker device-session verifier; the earlier working-tree-only check did not inspect that untracked file, so the reported hygiene result was incomplete.
16
+ - Remove only the extraneous EOF blank line. Runtime behavior, protocol behavior, activation logic, and the beta.7 live conclusions are unchanged.
17
+ - Assign a new prerelease version and regenerate the exact candidate because even this packaged-source change invalidates the accepted beta.7 package and promotion digests.
18
+
19
+ ## 3.0.0-beta.7 - 2026-07-22
20
+
21
+ ### Nested npm lifecycle PATH normalization
22
+
23
+ - Block `3.0.0-beta.6`. Its exact Worker and daemon activated successfully, but live launchd inspection still found repository `node_modules/.bin` entries and npm's private `node-gyp-bin`. The packaged beta.6 function was present and produced a clean PATH when called directly; the failure was caused by nested activation: the existing daemon PATH already contained one npm run-script prefix, and invoking `npm run release:candidate:activate` prepended a second. Beta.6 removed only through the first marker and therefore persisted the complete inner prefix.
24
+ - Normalize through the last npm run-script marker, removing every nested lifecycle prefix while retaining the current Node/package directories, the operator PATH after the innermost marker, and platform defaults. Inactive candidate-runtime entries remain excluded.
25
+ - Expand Unix and synthetic Windows regressions to two complete npm prefix/marker layers followed by a stale candidate and a user bin. Both layers must be removed; ordinary non-lifecycle `node_modules/.bin` entries remain supported.
26
+
27
+ ## 3.0.0-beta.6 - 2026-07-22
28
+
29
+ ### Reproducible background service environment
30
+
31
+ - Block `3.0.0-beta.5`. Its exact candidate activated successfully on the owner machine: the same-version Worker and single launchd daemon reached readiness, `project_overview` reported distinct effective and daemon-ceiling authority, fixed Git metadata succeeded, `service start` preserved the existing PID, and detached `service restart` replaced the PID and returned to readiness with no pending calls. Post-activation inspection nevertheless found that the launchd `PATH` captured npm lifecycle injection from the activation command, including project `node_modules/.bin` prefixes, npm's private `node-gyp-bin`, and the beta.4 candidate runtime that activation immediately pruned.
32
+ - Make service `PATH` construction reproducible across ordinary installation and prerelease activation. The current Node directory and current package bin are always added explicitly. When npm's `@npmcli/run-script` marker is present, the lifecycle-injected prefix is removed before inheriting the operator PATH. Any other entry below the candidate runtime store is rejected while the current candidate bin remains available. Ordinary user-supplied `node_modules/.bin` entries are retained when they were not injected by an npm lifecycle.
33
+ - Add a cross-platform regression that reproduces the exact activation topology: npm project bins before the lifecycle marker, a stale prior candidate runtime after the marker, an inherited user bin, and the current runtime entry. The service definition must retain Node/current runtime/user tools, reject npm-private and stale candidate entries, preserve absolute-only deduplication, and continue to embed the sanitized value in launchd and systemd definitions.
34
+
35
+ ## 3.0.0-beta.5 - 2026-07-22
36
+
37
+ ### Relay resilience, lifecycle correctness, and fail-closed state hardening
38
+
39
+ - Block `3.0.0-beta.4`. Live observation showed that the daemon process and launchd job could remain healthy while the authenticated WebSocket disappeared and later recovered with the same PID. The affected route was carried through the machine's system VPN/TUN; Machine Bridge cannot prove which internal VPN hop failed, but it can now distinguish application-level proxy selection from the operating-system network stack instead of reporting the misleading label `direct`.
40
+ - Cap relay reconnect backoff at 15 seconds instead of 60 seconds. Add bounded outage count/start/duration, last close category/code, transport error class, last disconnect/ready timestamps, ready duration, and next-retry timing to `server_info` and `diagnose_runtime`. Emit timestamped `relay.outage.active` and `relay.outage.recovered` events without exposing close reasons, proxy endpoints, page data, tool arguments, or results.
41
+ - Make `service start` idempotently ensure a running service and reserve explicit replacement for `service restart`. Require verified state/workspace ownership before touching the machine-global service, use detached restart handoff where behavior is verified, and fail closed on in-process Windows restart rather than risking a Task Scheduler `/End` operation that also kills the restart helper.
42
+ - Replace raw launchd/systemd status dumps with structured summaries. Service status no longer exposes the user's home path, complete PATH, SSH agent socket, environment, or provider diagnostics. Autostart log schema migration now validates both owner-only log files before mutation, rejects symbolic or multiple-hard-link paths, writes schema 4 strictly, and aborts startup on incomplete migration instead of mixing text and NDJSON.
43
+ - Treat a tool result, public error, Worker pong/welcome, browser response, and extension keepalive as explicit serialization/delivery boundaries. Circular values, BigInt, oversized structures, half-closed sockets, and send failures terminate only the affected request or transport and no longer crash or silently strand the whole relay.
44
+ - Prevent delayed process-tree escalation from signaling a reused PID or process group while still cleaning descendants that survive their parent. Snapshot process identity before graceful termination, verify it before SIGKILL, bind escalation timers to tracker/session lifecycle, and cover parent-exits-first and resistant-descendant cases.
45
+ - Pin implementation-owned Git and release-control commands to absolute, executable, non-group-writable binaries outside the workspace, state root, runtime root, and user home. Fixed metadata probes remain no-shell and minimal-environment; npm lifecycle PATH and workspace shims cannot replace `git` or `gh` in security/release decisions.
46
+ - Pin the browser broker to the repository extension ID derived from `manifest.key`, verify both WebSocket Origin and `chrome.runtime.id`, split extension and runtime credentials, and migrate legacy pairing state under the maintenance lock. The extension now cleans per-socket keepalive timers and active requests on replacement, disables stale reconnect, rejects duplicate request IDs, and closes half-dead sockets on response-delivery failure.
47
+ - Make corrupt workspace trust state persistently fail closed. Only a current-schema state envelope with matching workspace hash, canonical state-root/profile/state paths, and required policy/worker/resource objects can clear `recovery-required`; recovery markers are read once and strictly validate their bounded backup name and timestamp.
48
+ - Make managed-job terminal persistence recoverable. Result, terminal status, private runtime/plan/PID/cancel cleanup, and cleanup confirmation form an ordered protocol. Result-write, status-write, and artifact-cleanup failures remain visible; status reconstruction from a valid terminal result prevents duplicate finally execution, while leftover secret/resource copies are retried by read/list/prune.
49
+ - Give security-audit and legacy authorization state true cross-process locks. State removal also detects those locks plus managed-job transition/recovery locks, preventing uninstall from deleting a profile during an active mutation. Concurrent audit writers retain every event and a continuous hash chain.
50
+ - Reject multiple-hard-link inodes at owner-only state, autostart logs, runner diagnostics, and path-based existing-file reads. Atomic overwrite remains safe because it replaces the workspace directory entry rather than modifying a shared inode.
51
+ - Upgrade delegated macOS sandbox enablement from executable-presence testing to a behavior matrix that proves workspace access and denies outside reads/writes. Current hosts where the matrix fails remain fail closed; Keychain isolation is no longer claimed without an independently verified boundary.
52
+ - Bound detached managed-job credentials and staging lifetime. Minimal plans launch the runner with a minimal control environment, explicit full-environment plans retain that choice, and unexecuted sensitive plans expire after 24 hours instead of remaining for the seven-day result-retention period.
53
+ - Preserve both primary and cleanup failures for Secure Enclave enrollment and persistent candidate activation. Local cleanup failure is returned as an `AggregateError`; transactional rollback of an already updated Cloudflare Worker and local service definition remains an explicit operational residual rather than a false guarantee.
54
+ - Add explicit 32-call stdio admission control, refresh-family revocation before replay-marker capacity eviction, constant-memory unauthorized-request body draining before rejection, trusted Windows PowerShell literal tests, browser broker load counters, function-complexity/module-size gates, and risk-directed coverage for every new boundary.
55
+
56
+ ## 3.0.0-beta.4 - 2026-07-22
57
+
58
+ ### Explicit daemon-ceiling reporting and fixed internal metadata execution
59
+
60
+ - Mark `3.0.0-beta.3` as blocked. Its owner activation, persistent daemon handoff, relay readiness, service restart, and ordinary owner tool calls succeeded, but live verification exposed two delegated-account defects before publication: `project_overview` could report the request-effective `custom` policy as the daemon ceiling, and reviewer/editor Git metadata calls were routed through the arbitrary-process sandbox boundary.
61
+ - Return request-effective `policy`/`tools` and daemon-ceiling `daemonPolicy`/`daemonTools` as separate local fields. The Worker now consumes the explicit ceiling fields and retains a compatibility fallback for older daemon responses, preventing a second interpretation of an already-intersected policy.
62
+ - Add a fixed internal process path for bounded implementation-owned metadata probes. It uses validated argv, no shell, an isolated minimal environment, the existing timeout/output/cancellation/process-tree accounting, and never inherits the daemon full environment. Git status, diff, log, show, and project-root detection use this path; user-selected `run_process`, registered commands, and `exec_command` remain subject to the delegated sandbox and ordinary role ceilings.
63
+ - Add real `LocalRuntime` regressions for editor project snapshots and reviewer Git metadata, a process-layer regression proving the internal path is not wrapped as delegated arbitrary execution, and Worker integration coverage that supplies distinct effective and daemon fields.
64
+ - Prevent foreground startup in an unrelated workspace or isolated state root from unloading the machine-global autostart service. Platform service control now requires a live, verified `service` daemon lock for the exact state/workspace; the installed-package smoke test traps service-manager calls and proves zero-argument startup cannot stop the operator's real daemon. This fixes the repeated relay outages observed when the full verification plan reached `install:test`.
65
+ - Make `--log-format json` authoritative for the complete logger surface. Direct `debug`/`info`/`success`/`warn`/`error` calls and persistent daemon readiness now emit one timestamped, redacted JSON object per line instead of silently falling back to unstructured text. Add regressions for stream routing, normalized levels, timestamps, and sensitive/path field redaction.
66
+ - Override Wrangler/Miniflare’s transitive `sharp` dependency from vulnerable 0.34.5 to patched 0.35.3 after GHSA-f88m-g3jw-g9cj entered the audit database. Keep Wrangler itself pinned, update the npm script allowlist, and require full Worker/Miniflare integration plus zero-high-severity audit evidence for the override.
67
+
68
+ ## 3.0.0-beta.3 - 2026-07-21
69
+
70
+ ### Provisioned Secure Enclave broker boundary
71
+
72
+ - Mark `3.0.0-beta.2` as blocked. Its live activation restored version 2 device-ID compatibility, but then attempted to create a persistent Secure Enclave key from a runtime-compiled, ad-hoc-signed command-line helper. Modern macOS routes Secure Enclave keys through the data-protection Keychain and rejected that helper with `errSecMissingEntitlement` (`-34018`) before Worker deployment or daemon handoff.
73
+ - Stop treating a source-built ad-hoc helper as a production trust anchor. Without an explicitly configured provisioned broker, macOS retains or creates the owner-only portable P-256 root, performs no Keychain operation, requests no user-presence prompt, and proceeds with the coordinated version 3 upgrade.
74
+ - Add opt-in Secure Enclave enrollment through `MBM_MACOS_TRUST_BROKER`. The configured absolute path must resolve to a regular executable that is not group/other writable, has a strict valid Apple code signature, carries a stable signing identifier and Team ID, and passes an end-to-end probe that creates and deletes a temporary Secure Enclave key. The enrolled root binds the canonical broker path, signing identifier, Team ID, protocol version, key tag, and public key; every later public-key check or signature revalidates that binding.
75
+ - Keep the packaged Swift source and ad-hoc build only as a development and protocol-conformance fixture. It is intentionally rejected by the production broker validator. Add cross-platform provider-selection tests, macOS signature/binding/probe regressions, and truthful `server_info` provider metadata.
76
+
77
+ ## 3.0.0-beta.2 - 2026-07-21
78
+
79
+ ### Version 2 device-identity compatibility
80
+
81
+ - Restore the stable RFC-style P-256 JWK member order (`crv`, `kty`, `x`, `y`) used by version 2 device identifiers. The initial beta accidentally reordered those members through a new shared canonicalization helper, causing an intact version 2 portable identity to fail before Worker or daemon handoff.
82
+ - Add an explicit backward-compatibility regression that validates a persisted version 2 identifier and rejects the incorrect beta.1 ordering. Beta.1 is blocked and must not be activated or promoted.
83
+
84
+ ## 3.0.0-beta.1 - 2026-07-21
85
+
86
+ ### Request-scoped authority, trusted clients, and zero-routine-prompt security
87
+
88
+ - Replace delegated terminal approval IDs and broad capability leases with a request-scoped authority intersection. Every remote request now evaluates the daemon capability ceiling, the authenticated account role ceiling, the OAuth client and refresh-token family, automatic safety invariants, and object ownership. A grant can no longer expand a reviewer, editor, or operator beyond its canonical role. Owner/full automation remains uninterrupted, but owner requests are still risk-classified and audited.
89
+ - Bind retained process output, interactive process sessions, and managed jobs to account ID, account version, OAuth client, and refresh-token family. Cross-account or stale-session reads, input, cancellation, and output access fail closed. Protected local resources cannot be smuggled into delegated managed jobs, and non-owner accounts cannot create durable execution plans.
90
+ - Enforce request-specific path visibility, unrestricted-path authority, absolute-path disclosure, and child-process environment selection throughout file, Git, Agent-context, process, and job services. Generic path-based file tools cannot read or write Machine Bridge control-plane state even under owner/full; arbitrary owner shell execution remains equivalent to the OS user and is documented as a residual risk. Delegated process execution requires a behavior-verified OS workspace sandbox; platforms where the sandbox merely exists but fails a deny-default launch probe reject delegated execution rather than silently running with local-user authority. Owner execution is unchanged.
91
+ - Remove terminal-based operation authorization from the normal CLI and runtime. OAuth client authorization is the low-frequency trust event; ordinary operations run automatically within the account ceiling. Legacy leases are ignored by runtime and remain visible only for incident-response revocation. Trusted clients bind to one account and can be listed or revoked independently without rotating every account credential.
92
+ - Propagate refresh-token family identity to the local daemon and reject relay envelopes without it. Access tokens remain fifteen minutes and rotating refresh families remain bounded. Client trust, account version, role, and family identity participate in authorization and object ownership.
93
+ - Add a privacy-preserving chained security audit. It records tool, coarse risk category, result, duration, byte counts, target digest, and keyed principal references without storing command text, paths, file contents, form values, or output. Hash-chain verification detects local corruption or alteration and is exposed through runtime diagnostics without blocking ordinary work when the audit sink is unavailable.
94
+ - Stop nonce-capacity handling from evicting live replay markers. A full replay cache now rejects new signed requests until entries expire instead of reopening the replay window.
95
+ - Replace the long-lived file-backed device signer with a root-certified ephemeral session hierarchy. macOS prefers a non-exportable Secure Enclave P-256 root protected by user presence; one root signature per daemon start certifies a 24-hour in-memory session key used for preflight, challenge authentication, reconnect, and account administration. Root migration and rotation are two-phase: a pending public key is deployed and health-verified before local promotion.
96
+ - Remove `ACCOUNT_ADMIN_SECRET` from local state and Worker secrets. Account/client administration now uses the same root-certified ephemeral P-256 session, with each request bound to origin, method, path, body hash, key ID, timestamp, and nonce. Add optional DPoP ES256 token binding for compatible clients while preserving Bearer interoperability. DPoP proof verification no longer consumes replay capacity before OAuth credential validation, preventing unauthenticated cache exhaustion; unsupported critical JWS headers are rejected.
97
+ - Remove the terminal `job approve` execution path. `stage_job` remains a validated non-running draft; execution requires trusted owner `start_job` authority or an explicit local `machine-mcp job submit PLAN.json` action.
98
+ - Add behavior-level regressions for canonical-full daemon versus delegated-role boundaries, cross-account process/job ownership, control-plane path protection, token-family binding, nonce saturation, chained audit tampering, and delegated sandbox capability probing. Expand critical-module coverage and rewrite authorization, operations, upgrade, security, and threat-model documentation around the zero-routine-prompt model.
99
+ - This is a coordinated Worker, daemon, state, and browser-extension protocol upgrade. Version 3 components must converge together; existing remote clients must authorize once again because the relay principal now requires refresh-family and trusted-client binding.
100
+ - Replace the direct-to-stable release path with mandatory `dev`/`beta`/`rc` channels, registry-verified soak, and content-preserving stable promotion. Major, minor, and patch releases require at least seven days, three days, and one day respectively. A blocking fix increments the prerelease and restarts the interval.
101
+ - Add one persistent candidate activation command that verifies the exact tarball, updates the same-name Worker, proves candidate relay readiness, hands off to the login daemon, verifies the background version, and exits while the service remains active. Add exact prerelease npm/GitHub channel checks, published-package activation records, tracked soak evidence, promotion-content digests, and stable push/release/publication gates.
102
+ - Remove the remaining internal APIs that could create version 2 capability leases. Only migration cleanup (`list`, `revoke`, `clear`) remains.
103
+
3
104
  ## 2.0.0 - 2026-07-21
4
105
 
5
106
  ### Device identity and usable local transaction authorization
package/CONTRIBUTING.md CHANGED
@@ -34,31 +34,26 @@ An npm version is required when a change affects `package.json`, `package-lock.j
34
34
 
35
35
  Repository-only infrastructure changes, such as a `.github/` workflow update, do not require a synthetic npm version when package bytes are unchanged. They still require review and all applicable CI, dependency-review, CodeQL, governance, and Scorecard checks.
36
36
 
37
- ## Required before pushing an npm-package change
38
-
39
- 1. bump `package.json` to a version newer than the latest reachable `v*` tag;
40
- 2. add the matching dated section to `CHANGELOG.md` and update audit/documentation records;
41
- 3. run targeted tests, both dependency audits, `npm run worker:dry-run`, privacy/history review, signature verification, SBOM generation, and package inspection as applicable;
42
- 4. inspect the complete diff;
43
- 5. run `npm run release:candidate`, which executes the complete suite and creates the exact candidate tarball under ignored `.release-candidate/`;
44
- 6. give the repository owner `npm run release:candidate:start -- --allow-worker-deploy`; the owner explicitly authorizes the in-place candidate Worker deployment, starts the exact candidate locally, and leaves it running;
45
- 7. verify the live candidate through Machine Bridge, including Worker version/hash, remote health, relay readiness, exact local version, and representative functionality relevant to the change;
46
- 8. after observed verification succeeds, have the coding agent run the exact `release:accept` command printed by the candidate tool, creating `release-acceptance/v<version>.json`;
47
- 9. resolve every open issue and pull request before pushing. The current branch may cover an issue only with a standard closing keyword such as `Closes #47`; unrelated open PRs block the push. Commit the acceptance record and push the clean non-`main` branch only with `npm run github:push`, which paginates and enforces that backlog contract.
48
-
49
- Automated checks do not authorize step 8. The coding agent may record acceptance only after it has observed the owner-started candidate operating successfully. Any packaged-file change after acceptance changes the npm tarball hash and requires a regenerated candidate and another observed live verification.
50
-
51
- After all required pull-request checks pass, repository automation completes the source release: squash-merge, verify the exact `main` push CI, CodeQL, Governance, and Scorecard runs, and run `npm run release`. The helper requires `HEAD === origin/main`; it does not push `main`. It creates or verifies the annotated version tag and final GitHub Release only after the accepted package hash and exact-commit checks match. `release:publish` remains a compatibility alias.
52
-
53
- The release operator separately authorizes npm publication and any live machine update. Automation must not publish, deprecate, or unpublish npm packages; install the CLI globally; deploy the Worker; rotate credentials; mutate live deployment state; or start, stop, install, remove, or replace the daemon or autostart service without explicit user authorization.
54
-
55
- Supported upgrade and rollback behavior is defined in [docs/UPGRADING.md](docs/UPGRADING.md). Support requests follow [SUPPORT.md](SUPPORT.md), and repository participation follows [CODE_OF_CONDUCT.md](CODE_OF_CONDUCT.md).
56
-
57
- After npm publication, the standard machine update is:
58
-
59
- ```bash
60
- npm install -g --omit=optional --allow-scripts=esbuild,workerd,sharp,fsevents machine-bridge-mcp@latest && machine-mcp
61
- ```
37
+ ## Required prerelease flow for an npm-package change
38
+
39
+ 1. choose a `dev`, `beta`, or `rc` version; version 3 and later must not begin as stable;
40
+ 2. update changelog, audit notes, and documentation;
41
+ 3. run targeted and complete checks, dependency audits, Worker dry-run, privacy review, SBOM generation, and package inspection;
42
+ 4. inspect the complete diff and run `npm run release:candidate`;
43
+ 5. give the owner `npm run release:candidate:activate -- --allow-worker-deploy` and stop;
44
+ 6. after the owner runs it, verify the Worker, candidate relay, verified service daemon, exact version, representative behavior, and relevant failure paths through Machine Bridge;
45
+ 7. only after observed success, record exact candidate acceptance;
46
+ 8. commit and push only with `npm run github:push`, then complete review and required checks;
47
+ 9. create the GitHub Prerelease with `npm run prerelease:release`;
48
+ 10. the release operator runs `npm run prerelease:publish` and `npm run prerelease:install -- --allow-worker-deploy`;
49
+ 11. use the published prerelease for at least seven days for a major, three days for a minor, or one day for a patch;
50
+ 12. every blocking defect increments the prerelease number and restarts the interval;
51
+ 13. after explicit owner confirmation, record the soak result; stable promotion must pass `npm run release:soak:verify` and preserve the functional promotion digest;
52
+ 14. activate and observe the exact stable candidate, repeat acceptance and review, then run `npm run release`; the owner separately runs `npm run stable:publish`.
53
+
54
+ Automated checks do not authorize candidate acceptance or soak success. The agent observes the live candidate; the owner reports the real soak outcome. Release evidence contains bounded release metadata only and no private user content.
55
+
56
+ Repository-only infrastructure changes whose package bytes are unchanged skip candidate activation and soak but still require review and applicable checks. The complete state machine is in [docs/RELEASING.md](docs/RELEASING.md).
62
57
 
63
58
  ## Privacy
64
59
 
package/README.md CHANGED
@@ -3,7 +3,7 @@
3
3
  `machine-bridge-mcp` exposes one local workspace to MCP clients through a shared, policy-controlled runtime. Hosted clients connect through an OAuth-protected Cloudflare Worker relay; local clients may launch the same runtime over stdio.
4
4
 
5
5
  > [!WARNING]
6
- > The default `full` profile retains every local-user capability: unrestricted files, shell commands, the parent environment, browser automation, applications, resources, and jobs. It is **not** an operating-system sandbox. An authenticated owner may use that ceiling directly without terminal approval. Delegated non-owner accounts require bounded local capability leases for high-impact operations. Use a narrower profile or an isolated OS account, VM, or container for mutually untrusted workloads.
6
+ > The default `full` profile retains every local-user capability: unrestricted files, shell commands, the parent environment, browser automation, applications, resources, and jobs. It is **not** an operating-system sandbox. An authenticated owner may use that ceiling without per-operation prompts. Delegated accounts are permanently constrained by their role; no approval, token, or reconnect can elevate them. Use a narrower profile or an isolated OS account, VM, or container for mutually untrusted workloads.
7
7
 
8
8
  ## Choose a path
9
9
 
@@ -24,7 +24,7 @@ Support boundaries are defined in [SUPPORT.md](SUPPORT.md). Repository participa
24
24
  - policy profiles with shared local/Worker enforcement contracts;
25
25
  - bounded file, patch, Git, process, diagnostic, application, browser, and managed-job tools;
26
26
  - account roles whose authority is intersected with the connected daemon policy;
27
- - device-signed daemon transport, interruption-free authenticated owner authority, and account/client-bound capability leases for delegated high-impact transactions;
27
+ - root-certified ephemeral daemon sessions, trusted OAuth client binding, refresh-family ownership, and non-escalatable account roles;
28
28
  - structured, privacy-conscious lifecycle events and stable error codes;
29
29
  - fail-closed state, lock, release, package, and supply-chain checks.
30
30
 
@@ -34,8 +34,8 @@ The remote Worker authenticates and relays requests. It cannot directly read loc
34
34
  Hosted MCP client
35
35
  -> HTTPS + OAuth 2.1 / PKCE
36
36
  -> Cloudflare Worker + Durable Object
37
- -> P-256 device-authenticated outbound WebSocket
38
- -> local transaction authorization
37
+ -> root-certified ephemeral P-256 WebSocket session
38
+ -> request-level effective authority and object ownership
39
39
  -> local runtime
40
40
 
41
41
  Local MCP client
@@ -155,7 +155,7 @@ The shared source of truth is `src/shared/policy-contract.json`. The generated m
155
155
 
156
156
  For remote calls, `server_info.authorization.effective_policy` and `effective_tools` are authoritative. Daemon policy and tools describe only the local capability ceiling before account-role and host-side filtering.
157
157
 
158
- `full` is the daemon capability ceiling. An authenticated owner account may exercise it directly without approval IDs or terminal commands. Delegated reviewer, editor, and operator accounts remain constrained by their role profile, and their high-impact operations require account/client-bound, time-bounded local leases. Use `machine-mcp approval` only when administering those delegated-account leases. See [local transaction authorization](docs/LOCAL_AUTHORIZATION.md).
158
+ `full` is the daemon capability ceiling. An authenticated owner may exercise it without per-operation approval IDs. Delegated reviewer, editor, and operator accounts remain inside immutable role ceilings; out-of-role operations are denied rather than converted into a temporary elevation workflow. Process sessions, retained output, and managed jobs are additionally bound to account, client, and refresh-token family. See [local authorization](docs/LOCAL_AUTHORIZATION.md).
159
159
 
160
160
  ## Browser and application automation
161
161
 
@@ -194,11 +194,11 @@ machine-mcp status
194
194
  machine-mcp doctor
195
195
  machine-mcp workspace show|set|reset
196
196
  machine-mcp service status|install|start|stop|uninstall
197
- machine-mcp account list|add|role|enable|disable|rotate-password|remove
198
- machine-mcp approval list|approve|grant|revoke|clear
197
+ machine-mcp account list|clients|revoke-client|add|role|enable|disable|rotate-password|remove
198
+ machine-mcp approval list|revoke|clear
199
199
  machine-mcp browser status|setup|pair|path
200
200
  machine-mcp resource add|list|check|remove
201
- machine-mcp job submit|inspect|approve|list|read|cancel
201
+ machine-mcp job submit|inspect|list|read|cancel
202
202
  machine-mcp rotate-secrets
203
203
  machine-mcp uninstall [--keep-worker] [--yes]
204
204
  ```
@@ -236,17 +236,24 @@ Testing details and design rules are in [docs/TESTING.md](docs/TESTING.md). Engi
236
236
 
237
237
  ## Release boundary
238
238
 
239
- A package change requires a version bump, matching changelog section, complete verification, and interactive verification of the exact candidate tarball:
239
+ Version 3 and later use a mandatory prerelease and soak path. Package work starts as `dev`, `beta`, or `rc`; it does not claim the stable version while candidate testing is still underway.
240
240
 
241
241
  ```sh
242
242
  npm run release:candidate
243
- # After explicit owner authorization in the conversation, the coding agent starts and verifies:
244
- npm run release:candidate:start -- --allow-worker-deploy
245
- # The coding agent records acceptance, pushes, merges, then runs:
246
- npm run release
243
+ # The owner runs the exact persistent activation command printed above:
244
+ npm run release:candidate:activate -- --allow-worker-deploy
245
+ # After the coding agent verifies the live Worker/daemon and records acceptance:
246
+ npm run prerelease:release
247
+ # Explicit owner registry and live-install steps:
248
+ npm run prerelease:publish
249
+ npm run prerelease:install -- --allow-worker-deploy
247
250
  ```
248
251
 
249
- The owner action is to explicitly authorize the exact candidate and any in-place update of the configured same-name Worker in the active conversation; the coding agent performs the startup and verification through Machine Bridge. The coding agent must observe the deployed Worker version/hash, remote health, relay readiness, connected candidate version, and representative functionality before recording acceptance; automated checks alone are insufficient. npm publication and Worker deployment remain separate owner-operated live actions. See [docs/RELEASING.md](docs/RELEASING.md).
252
+ Formal soak begins only after the exact published prerelease is installed and activated. Minimum soak is seven days for a major release, three days for a minor release, and one day for a patch. Every blocking fix creates a new prerelease and restarts the clock.
253
+
254
+ Stable promotion must retain the soaked package's functional digest. After the owner reports successful soak, the agent records the soak result, prepares and verifies the stable candidate, and only then completes `npm run release`; npm stable publication is the separate explicit `npm run stable:publish` operation.
255
+
256
+ See [docs/RELEASING.md](docs/RELEASING.md).
250
257
 
251
258
  ## Documentation
252
259