agentwheel 0.19.9 → 0.20.0

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/AGENT.md CHANGED
@@ -41,8 +41,8 @@ agentwheel install --fleet example-fleet --profile daily --dry-run
41
41
  `--user`, `--local`, and `--fleet <fleet-id>` select separate desired-state scopes. Named fleets
42
42
  are optional. Do not merge scopes or assume a fleet has priority over user or local state.
43
43
 
44
- Register and inspect a schema-v3 fleet only after its canonical root, matching `fleetId`, and
45
- required packages exist:
44
+ Register and inspect a fleet using schema v3 or newer only after its canonical root, matching
45
+ `fleetId`, and required packages exist:
46
46
 
47
47
  ```bash
48
48
  agentwheel fleet register example-fleet --root /srv/agentwheel/fleets/example-fleet --required-package core-agent-pack
@@ -60,7 +60,7 @@ agentwheel fleet normalize example-fleet --from user --package core-agent-pack -
60
60
  agentwheel fleet normalize example-fleet --from user --recover
61
61
  ```
62
62
 
63
- Named fleets require a schema-v3-capable CLI. Upgrade Agentwheel first and verify
63
+ Named fleets require a CLI that supports schema v3 or newer. Upgrade Agentwheel first and verify
64
64
  `agentwheel fleet --help` before creating, registering, reading, or planning fleet state. Do not
65
65
  downgrade the config, strip fleet fields, or run a planning/mutation command with the old CLI.
66
66
 
package/README.md CHANGED
@@ -383,7 +383,7 @@ agentwheel fleet normalize example-fleet --from user --recover
383
383
  Recovery restores the source side from a pending normalization journal after verifying that the
384
384
  recorded configs, manifests, and graph locks have not changed outside the transaction.
385
385
 
386
- Configuration with named fleets requires a schema-v3-capable Agentwheel CLI. Upgrade the CLI first,
386
+ Named fleets use workspace schema v3 or newer and require a compatible Agentwheel CLI. Upgrade the CLI first,
387
387
  verify `agentwheel --version` and `agentwheel fleet --help`, then create the fleet config and
388
388
  register it. Do not edit the config to an older schema or run an older CLI against it.
389
389
 
@@ -408,6 +408,31 @@ reserved for configured agents.
408
408
 
409
409
  Flow: **author + workspace → `install` → runtime**.
410
410
 
411
+ ## Governed mutations
412
+
413
+ Workspace schema v4 can require a full mutation reason, durable receipts, and automatic
414
+ commit-after-verify revisioning for Agentwheel's mutating commands. Revision providers can use the
415
+ built-in exact-path Git implementation or a strict JSON command whose absolute entrypoint is
416
+ SHA-256 pinned. Runtime output remains generated state; only declared and verified repository paths
417
+ are eligible for a commit.
418
+
419
+ ```bash
420
+ agentwheel install --reason "Install the reviewed artifact set"
421
+ agentwheel mutation list
422
+ agentwheel mutation show <operation-id>
423
+ agentwheel mutation finalize <operation-id>
424
+ agentwheel mutation recover-runtime <operation-id>
425
+ ```
426
+
427
+ See [the v1 revision-provider specification](docs/specs/revision-provider-v1.md) for configuration,
428
+ the JSON protocol, crash recovery, and fail-closed boundaries.
429
+
430
+ Provider-owned drafts are recorded as `owned-but-unpublished`, including their stack, branch,
431
+ projected draft tip, and integration control commit. Agentwheel never publishes them and does not
432
+ invent a publication command; inspect the durable record and follow the provider's separately
433
+ documented, authorized workflow. An active-active provider check may deliberately remain blocked
434
+ until then.
435
+
411
436
  ## Packages
412
437
 
413
438
  A package is a git repo or folder with an OpenPack manifest and a canonical layout:
@@ -610,7 +635,8 @@ OpenPack packages can depend on other packages and compose shared markdown fragm
610
635
  resolve.
611
636
  - **Offline & frozen installs.** `--offline` guarantees zero network; `--frozen-lock` hard-fails if
612
637
  resolution would differ from the lock.
613
- - **Introspection.** `agentwheel deps tree` prints the resolved graph; `agentwheel deps why
638
+ - **Introspection.** `agentwheel deps tree` prints the resolved graph (source resolution may refresh
639
+ incidental local caches but does not recover runtime journals or persist trust); `agentwheel deps why
614
640
  <selector>` explains why an artifact is installed.
615
641
 
616
642
  ### Meta-packages (packs)
@@ -0,0 +1,15 @@
1
+ #!/usr/bin/env node
2
+ import {
3
+ applyCombinedInstallPlan,
4
+ applyInstallPlan,
5
+ recoverPendingApply,
6
+ uninstall
7
+ } from "./chunk-USHT7FGV.js";
8
+ import "./chunk-HOYIIUL5.js";
9
+ import "./chunk-7VPI5J5Y.js";
10
+ export {
11
+ applyCombinedInstallPlan,
12
+ applyInstallPlan,
13
+ recoverPendingApply,
14
+ uninstall
15
+ };
@@ -1,9 +1,5 @@
1
1
  #!/usr/bin/env node
2
2
 
3
- // src/source/identify.ts
4
- import { homedir } from "os";
5
- import { resolve } from "path";
6
-
7
3
  // src/utils/fs.ts
8
4
  import { createHash } from "crypto";
9
5
  import {
@@ -97,7 +93,7 @@ async function withFilesystemLock(lockPath, timeoutMs, fn, description = "cache"
97
93
  if (Date.now() - started > timeoutMs) {
98
94
  throw new Error(`Timed out waiting for ${description} lock at ${lockPath}`);
99
95
  }
100
- await new Promise((resolve2) => setTimeout(resolve2, 50));
96
+ await new Promise((resolve) => setTimeout(resolve, 50));
101
97
  }
102
98
  }
103
99
  try {
@@ -110,29 +106,6 @@ function isAlreadyExists(error) {
110
106
  return typeof error === "object" && error !== null && "code" in error && error.code === "EEXIST";
111
107
  }
112
108
 
113
- // src/source/identify.ts
114
- function inferSourceDriverName(source) {
115
- if (source.startsWith("clawhub:")) return "clawhub";
116
- if (source.startsWith("mcp-registry:")) return "mcp-registry";
117
- if (source.startsWith("skillkit:")) return "skillkit";
118
- if (source.startsWith("vercel:")) return "vercel-skills";
119
- return source.startsWith("github:") || source.startsWith("git:") ? "git" : "local";
120
- }
121
- async function isExplicitSource(source) {
122
- if (source.startsWith("github:") || source.startsWith("git:") || source.startsWith("skillkit:") || source.startsWith("vercel:") || source.startsWith("mcp-registry:") || source.startsWith("clawhub:")) {
123
- return true;
124
- }
125
- if (source === "." || source === ".." || source.startsWith("./") || source.startsWith("../") || source.startsWith("/") || source.startsWith("~/")) {
126
- return true;
127
- }
128
- return pathExists(resolveLocalPath(source));
129
- }
130
- function resolveLocalPath(source) {
131
- if (source === "~") return homedir();
132
- if (source.startsWith("~/")) return resolve(homedir(), source.slice(2));
133
- return resolve(source);
134
- }
135
-
136
109
  export {
137
110
  pathExists,
138
111
  hashPath,
@@ -141,7 +114,5 @@ export {
141
114
  atomicCopy,
142
115
  writeJsonAtomic,
143
116
  withFilesystemLock,
144
- isAlreadyExists,
145
- inferSourceDriverName,
146
- isExplicitSource
117
+ isAlreadyExists
147
118
  };
@@ -0,0 +1,34 @@
1
+ #!/usr/bin/env node
2
+ import {
3
+ pathExists
4
+ } from "./chunk-7VPI5J5Y.js";
5
+
6
+ // src/source/identify.ts
7
+ import { homedir } from "os";
8
+ import { resolve } from "path";
9
+ function inferSourceDriverName(source) {
10
+ if (source.startsWith("clawhub:")) return "clawhub";
11
+ if (source.startsWith("mcp-registry:")) return "mcp-registry";
12
+ if (source.startsWith("skillkit:")) return "skillkit";
13
+ if (source.startsWith("vercel:")) return "vercel-skills";
14
+ return source.startsWith("github:") || source.startsWith("git:") ? "git" : "local";
15
+ }
16
+ async function isExplicitSource(source) {
17
+ if (source.startsWith("github:") || source.startsWith("git:") || source.startsWith("skillkit:") || source.startsWith("vercel:") || source.startsWith("mcp-registry:") || source.startsWith("clawhub:")) {
18
+ return true;
19
+ }
20
+ if (source === "." || source === ".." || source.startsWith("./") || source.startsWith("../") || source.startsWith("/") || source.startsWith("~/")) {
21
+ return true;
22
+ }
23
+ return pathExists(resolveLocalPath(source));
24
+ }
25
+ function resolveLocalPath(source) {
26
+ if (source === "~") return homedir();
27
+ if (source.startsWith("~/")) return resolve(homedir(), source.slice(2));
28
+ return resolve(source);
29
+ }
30
+
31
+ export {
32
+ inferSourceDriverName,
33
+ isExplicitSource
34
+ };