@brainervirus/workit-opencode 8.11.0 → 8.12.1

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.
@@ -25,7 +25,7 @@ REPORT: branch, head SHA, files changed, each VERIFY command with its exit code,
25
25
  each ACCEPTANCE line met / not met, rulings you made (`workit ledger ruling`),
26
26
  anything out of scope as a follow-up, not a diff.
27
27
  STANDING: <the standing orders, verbatim: `workit ledger standing add` records each one>
28
- export WORKIT_SESSION_ID=<lead>-w<n> (set by the lead for a worker's commits; a verifier brief sets none: the host derives it)
28
+ <identity line, per the lead's host: see "Identity and git rules per host" below>
29
29
  ```
30
30
 
31
31
  ## Worked example
@@ -97,17 +97,32 @@ is the slice's STUCK threshold in `workit fanout status`. `"fanIn":
97
97
  }
98
98
  ```
99
99
 
100
+ ## Identity and git rules per host
101
+
102
+ `workit fanout brief` renders the identity line and RULES 1 and 3 for the
103
+ lead's host (`WORKIT_HOST`, or the host's own session variable):
104
+
105
+ | Lead's host | Identity line | RULES 1 and 3 |
106
+ | --- | --- | --- |
107
+ | Claude Code | `Session: your env already has WORKIT_SESSION_ID (the lead's id)`; no `export`, no hand-minted id (SubagentStart issues `<lead>:<agent id>` only to verifiers and reviewers, never to an implementer, so the worker's commits carry the lead's id) | plain git: `git fetch origin && git switch -c <branch> origin/<base>` and `git commit -m <msg> --trailer "Workit-Session: <the env WORKIT_SESSION_ID>" --trailer "<host attribution>" -- <paths in SCOPE>`, because worktree isolation refuses every `workit git` form |
108
+ | OpenCode, Pi, Codex | `Session: your host already sets WORKIT_SESSION_ID in your shell`; export nothing (the host derives the id and an export cannot replace it) | `workit git branch <branch> --base <base>`, `workit git commit -m <msg> -- <paths in SCOPE>` |
109
+ | Cursor, CI, a plain terminal | `export WORKIT_SESSION_ID=<lead>-w-<slice>` (`+try<n>` for a race attempt): declared, not checked | the same `workit git` forms |
110
+
111
+ `MODE: resume` is `git switch <branch>` on every host (the branch exists; the
112
+ lead removed the dead worker's worktree after its exit, so the switch
113
+ succeeds), then continue from its head. A race attempt (`--attempt <n>`)
114
+ follows its host's row with the branch `<branch>-try<n>`.
115
+
100
116
  ## Worker rules (`workit fanout brief` appends them as RULES)
101
117
 
102
- 1. First command. `MODE: new`: `workit git branch <branch> --base <base>` (the
103
- worktree may start on a name that breaks branch policy). `MODE: resume`:
104
- `git switch <branch>` (the branch exists; the lead removed the dead
105
- worker's worktree after its exit, so the switch succeeds), then continue
106
- from its head.
118
+ 1. First command: create the branch (`MODE: new`; the worktree may start on a
119
+ name that breaks branch policy) or `git switch` to it (`MODE: resume`),
120
+ as the table above says for your host.
107
121
  2. Decide ambiguities yourself and record them:
108
122
  `workit ledger ruling "<what>" --why "<why>" --cost-if-wrong "<cost>"`.
109
123
  Stop only for an irreversible action, a security-sensitive one, or a side
110
124
  effect outside the worktree.
111
- 3. Commit with `workit git commit -m "<msg>" -- <paths in SCOPE>`; push only if
112
- the brief says so.
125
+ 3. Commit as the table says (`workit git commit -m "<msg>" -- <paths in SCOPE>`,
126
+ or plain git with the trailers on Claude Code); push only if the brief says
127
+ so.
113
128
  4. Never record a verdict on your own work.
@@ -73,8 +73,8 @@ Which session id a verdict carries, per host:
73
73
  - Claude Code: subagents inherit your `WORKIT_SESSION_ID`, so the
74
74
  SubagentStart hook names each `verifier` and `reviewer` its own session
75
75
  (`<lead>:<agent id>`), passed exactly as `--session`: the hook records the
76
- ids it issues, and only those are accepted. An `implementer` uses the
77
- session its brief exports for its workit commands.
76
+ ids it issues, and only those are accepted. An `implementer` is issued
77
+ none: it keeps your id in its env for its workit commands and commits.
78
78
  - Codex: the `workit-verifier` and `workit-reviewer` agents get the same
79
79
  issued `--session` from SubagentStart; any other verifier passes
80
80
  `--as verifier`.
@@ -84,8 +84,13 @@ Which session id a verdict carries, per host:
84
84
  - Cursor (no session id in the shell): the brief sets the verifier's
85
85
  `WORKIT_SESSION_ID=<lead>:verifier-<random hex>`, a fresh suffix per
86
86
  verifier. Cursor cannot check it: it is declared, not derived.
87
- - A worker's commits use `export WORKIT_SESSION_ID=<lead>-w-<slice>` from
88
- `workit fanout brief`. A verdict under an id you made up (`<lead>-v1`,
87
+ - A worker's commits: on Claude Code the lead's `WORKIT_SESSION_ID` already in
88
+ its env (SubagentStart issues no implementer id; plain git, no export, so the
89
+ lead authored those commits: a verifier or reviewer records the verdict, not
90
+ the lead); on OpenCode, Pi and Codex the id the host already
91
+ puts in its shell; on Cursor, CI and a plain terminal the brief's
92
+ `export WORKIT_SESSION_ID=<lead>-w-<slice>` (see `brief.md`, "Identity and
93
+ git rules per host"). A verdict under an id you made up (`<lead>-v1`,
89
94
  `<lead>:v1`) is refused as `forged_session` on Claude Code, Codex,
90
95
  OpenCode and Pi.
91
96
 
package/dist/plugin.js CHANGED
@@ -9597,6 +9597,48 @@ function acquireFileLockSync(targetPath, options) {
9597
9597
  }
9598
9598
  }
9599
9599
  }
9600
+ // packages/workit-core/src/core/logger.ts
9601
+ import os from "node:os";
9602
+ var SENSITIVE_WORDS = new Set([
9603
+ "token",
9604
+ "secret",
9605
+ "password",
9606
+ "passwd",
9607
+ "authorization",
9608
+ "credential",
9609
+ "credentials",
9610
+ "cookie",
9611
+ "api",
9612
+ "apikey",
9613
+ "apitoken",
9614
+ "accesstoken",
9615
+ "clientsecret",
9616
+ "refreshtoken",
9617
+ "key",
9618
+ "bearer",
9619
+ "prompt",
9620
+ "message",
9621
+ "messages",
9622
+ "content",
9623
+ "body",
9624
+ "args",
9625
+ "argument",
9626
+ "result",
9627
+ "results",
9628
+ "output",
9629
+ "issue",
9630
+ "description",
9631
+ "summary",
9632
+ "payload",
9633
+ "script",
9634
+ "command",
9635
+ "text",
9636
+ "query"
9637
+ ]);
9638
+ var STACK_WORDS = new Set(["stack", "stacktrace", "trace"]);
9639
+ var escapeRegExp = (value) => value.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
9640
+ var homePattern = new RegExp(`${escapeRegExp(os.homedir())}(?=[/\\\\]|$)|\\$HOME(?=[/\\\\]|$)`, "g");
9641
+
9600
9642
  // packages/workit-core/src/store/paths.ts
9601
9643
  import { spawnSync } from "node:child_process";
9602
9644
  import { createHash as createHash2 } from "node:crypto";
@@ -12391,7 +12433,7 @@ function loadCheckConfig(cwd) {
12391
12433
  gates[gate] = names;
12392
12434
  }
12393
12435
  }
12394
- return { source: CHECKS_FILE, root, checks, gates, error: null };
12436
+ return { source: CHECKS_FILE, root, checks, gates, error: null, resources: parsed.resources };
12395
12437
  }
12396
12438
  var sameArgv = (left, right) => left.length === right.length && left.every((item, index) => item === right[index]);
12397
12439
  function matchesNamedCheck(config, name, argv, cwd) {
@@ -12433,7 +12475,7 @@ function checkCommand(args, version, onPath = workitAvailable()) {
12433
12475
  import { spawnSync as spawnSync4 } from "node:child_process";
12434
12476
  import { createHash as createHash5 } from "node:crypto";
12435
12477
  import fs9 from "node:fs";
12436
- import os from "node:os";
12478
+ import os2 from "node:os";
12437
12479
  import path8 from "node:path";
12438
12480
  var MAX_BUFFER = 256 * 1024 * 1024;
12439
12481
  var GIT_TIMEOUTS = { local: 20000, worktree: 120000, network: 15000 };
@@ -12481,7 +12523,7 @@ function worktreeTree(cwd, options = {}) {
12481
12523
  return null;
12482
12524
  const cap = options.maxUntrackedBytes ?? MAX_UNTRACKED_BYTES;
12483
12525
  const timeoutMs = options.timeoutMs ?? GIT_TIMEOUTS.worktree;
12484
- const scratch = fs9.mkdtempSync(path8.join(os.tmpdir(), "workit-tree-"));
12526
+ const scratch = fs9.mkdtempSync(path8.join(os2.tmpdir(), "workit-tree-"));
12485
12527
  try {
12486
12528
  const tempIndex = path8.join(scratch, "index");
12487
12529
  if (fs9.existsSync(indexPath))
@@ -12635,7 +12677,7 @@ import {
12635
12677
  readdirSync as readdirSync2,
12636
12678
  writeFileSync as writeFileSync2
12637
12679
  } from "node:fs";
12638
- import os2 from "node:os";
12680
+ import os3 from "node:os";
12639
12681
  import path9 from "node:path";
12640
12682
 
12641
12683
  // packages/workit-core/src/core/boundary.ts
@@ -12695,7 +12737,7 @@ var mergePreset = (preset, input = {}, current = {
12695
12737
  protected: preset === "custom" ? input.protectedNames ?? current.branchPolicy.protected : [...defs.protected]
12696
12738
  };
12697
12739
  };
12698
- var resolveConfigDir = () => process.env.WORKFLOW_TOOLKIT_CONFIG ?? process.env.WORKFLOW_TOOLKIT_CONFIG_DIR ?? path9.join(process.env.XDG_CONFIG_HOME || path9.join(os2.homedir(), ".config"), "workit");
12740
+ var resolveConfigDir = () => process.env.WORKFLOW_TOOLKIT_CONFIG ?? process.env.WORKFLOW_TOOLKIT_CONFIG_DIR ?? path9.join(process.env.XDG_CONFIG_HOME || path9.join(os3.homedir(), ".config"), "workit");
12699
12741
  var migratedDir = null;
12700
12742
  var migrationFailed = false;
12701
12743
  var ensureConfigDir = (dir = resolveConfigDir()) => {
@@ -12705,7 +12747,7 @@ var ensureConfigDir = (dir = resolveConfigDir()) => {
12705
12747
  migratedDir = dir;
12706
12748
  return dir;
12707
12749
  }
12708
- const legacy = path9.join(process.env.XDG_CONFIG_HOME || path9.join(os2.homedir(), ".config"), "workflow-toolkit");
12750
+ const legacy = path9.join(process.env.XDG_CONFIG_HOME || path9.join(os3.homedir(), ".config"), "workflow-toolkit");
12709
12751
  if (!existsSync3(legacy)) {
12710
12752
  migratedDir = dir;
12711
12753
  return dir;
@@ -13002,6 +13044,7 @@ var workspaceConfigSchema = object({
13002
13044
  autoApprove: union([boolean2(), array(nonBlank)]).optional(),
13003
13045
  defaultEndpoint: unknown().optional(),
13004
13046
  verification: _enum(["self", "independent"]).optional(),
13047
+ trailers: boolean2().optional(),
13005
13048
  autonomy: object(Object.fromEntries(["push", "pr", "merge", "release", "rerun"].map((kind) => [
13006
13049
  kind,
13007
13050
  union([boolean2(), literal("verified")]).optional()
@@ -13283,8 +13326,8 @@ var resolveRuntimeWorkspaceVcs = (cwd) => resolveRuntimeWorkspaceCandidate(cwd,
13283
13326
  var runtimeWorkspaceIndexSchema = object({
13284
13327
  workspaces: array(object({ name: nonBlank, glob: nonBlank }).passthrough()).optional()
13285
13328
  }).passthrough();
13286
- var matchRuntimeWorkspace = (cwd) => {
13287
- const file = path10.join(configDir(), "workspaces.json");
13329
+ var matchRuntimeWorkspace = (cwd, dir = configDir()) => {
13330
+ const file = path10.join(dir, "workspaces.json");
13288
13331
  let raw;
13289
13332
  try {
13290
13333
  raw = readFileSync3(file, "utf8");
@@ -13313,7 +13356,7 @@ var matchRuntimeWorkspace = (cwd) => {
13313
13356
  const matches = matchingEntries(cwd, entries ?? []);
13314
13357
  const workspaceName = process.env.WORKFLOW_WORKSPACE_NAME?.trim() || undefined;
13315
13358
  const selected = selectWorkspaceMatch(matches, cwd, workspaceName);
13316
- return selected ? { file, selected } : null;
13359
+ return selected ? { file, selected, matches } : null;
13317
13360
  };
13318
13361
  var resolveRuntimeReleaseTracks = (cwd) => {
13319
13362
  const matched = matchRuntimeWorkspace(cwd);
@@ -13655,7 +13698,7 @@ var git3 = (cwd, args) => {
13655
13698
  return run.status === 0 ? (run.stdout ?? "").trim() : null;
13656
13699
  };
13657
13700
  var recordedBaseKey = (branch) => `branch.${branch}.workitBase`;
13658
- var escapeRegExp = (text) => text.replace(/[.*+?^${}()|[\]\\]/gu, "\\$&");
13701
+ var escapeRegExp2 = (text) => text.replace(/[.*+?^${}()|[\]\\]/gu, "\\$&");
13659
13702
  var reflog = (cwd, ref) => (git3(cwd, ["log", "-g", "--date=unix", "--format=%H%x09%gd%x09%gs", ref, "--"]) ?? "").split(`
13660
13703
  `).map((line) => {
13661
13704
  const [sha = "", selector = "", ...subject] = line.split("\t");
@@ -13687,7 +13730,7 @@ function gitTrackProbe(cwd) {
13687
13730
  const created = own.at(-1);
13688
13731
  if (!created || created.subject !== "branch: Created from HEAD")
13689
13732
  return null;
13690
- const pattern = new RegExp(`^checkout: moving from (\\S+) to ${escapeRegExp(branch)}$`, "u");
13733
+ const pattern = new RegExp(`^checkout: moving from (\\S+) to ${escapeRegExp2(branch)}$`, "u");
13691
13734
  const entry = reflog(cwd, "HEAD").findLast((item) => item.time >= created.time && item.sha === created.sha && pattern.test(item.subject));
13692
13735
  return entry ? pattern.exec(entry.subject)?.[1] ?? null : null;
13693
13736
  },
@@ -15691,9 +15734,9 @@ Autonomy contract:
15691
15734
  ship), go to the effective endpoint in \`workit grant show\`: \`pr\` opens
15692
15735
  the PR; \`green\` babysits it without asking (workit-ship) to merge-ready,
15693
15736
  never merging; \`merged\` also lands it with \`workit pr merge\`.
15694
- Merge and release need a workspace grant, which only the user raises from
15695
- their own terminal (a blocked verb names how); never edit workspaces.json or
15696
- route around a grant_required.
15737
+ Merge and release need a workspace grant only the user raises from their
15738
+ own terminal (a blocked verb names how); never edit workspaces.json or route
15739
+ around a grant_required.
15697
15740
  - Ask only for a product or preference choice, or for authority you lack, with
15698
15741
  your recommended answer. Facts are yours: read, run or prototype.
15699
15742
  - Label claims measured (run and seen this session), inferred, or guess.
@@ -15702,17 +15745,19 @@ Autonomy contract:
15702
15745
  - Author is not verifier: your own verdict is \`--self\`, shown as
15703
15746
  self-reviewed, never verified. High risk, \`verification: independent\` and
15704
15747
  merge need a verifier with its own host-derived session (a subagent's
15705
- \`<lead>:<child>\`, set by the host); never hand-mint one such as \`<lead>-v1\`.
15748
+ \`<lead>:<child>\`); never hand-mint one (\`<lead>-v1\`).
15706
15749
  - A local-commit endpoint does not imply PR readiness, and a local commit alone
15707
15750
  is not evidence of a requested remote push. Before reporting delivery,
15708
15751
  reconcile every requested item and observe it (\`workit verify-delivery\`).
15709
15752
 
15710
15753
  CLI first: if a step has one right answer, use the \`workit\` verb instead of
15711
15754
  hand-running git, gh or glab (\`workit git|pr|ci|check\`; \`workit help\` lists
15712
- the rest; without \`workit\` on PATH, \`npx -y @brainervirus/workit-cli\`).
15755
+ the rest; lacking \`workit\`, \`npx -y @brainervirus/workit-cli\`).
15756
+ Add Co-Authored-By via \`workit git commit --trailer "K: v" -- <paths>\`, never
15757
+ an amend.
15713
15758
  The task families (task, policy, evidence, finding, decision, worker, state)
15714
15759
  are optional continuity for tracked work; each branch has one implicit task,
15715
- created by the first recording, and a solo edit needs no task. A decision
15760
+ and a solo edit needs no task. A decision
15716
15761
  records a user choice; it never authorizes an effect. Judge work once with
15717
15762
  \`workit policy assess --judge risk= behavior= product-choice= plan=\`.
15718
15763
  Across repositories, bind each item to its checkout, branch and endpoint,
@@ -15867,7 +15912,7 @@ import path17 from "node:path";
15867
15912
  import { spawnSync as spawnSync11 } from "node:child_process";
15868
15913
  import { createHash as createHash12 } from "node:crypto";
15869
15914
  import fs14 from "node:fs";
15870
- import os3 from "node:os";
15915
+ import os4 from "node:os";
15871
15916
  import path16 from "node:path";
15872
15917
 
15873
15918
  // packages/workit-core/src/core/branch.ts
@@ -16293,7 +16338,7 @@ var isAbsolute = (value) => path16.isAbsolute(value) || /^[A-Za-z]:[\\/]/.test(v
16293
16338
  var joinDir = (base, next) => {
16294
16339
  if (base === undefined || /[$`*?]/.test(next) || next === "-")
16295
16340
  return;
16296
- const expanded = next === "~" || next.startsWith("~/") ? path16.join(os3.homedir(), next.slice(1)) : next;
16341
+ const expanded = next === "~" || next.startsWith("~/") ? path16.join(os4.homedir(), next.slice(1)) : next;
16297
16342
  return base === null || isAbsolute(expanded) ? expanded : path16.join(base, expanded);
16298
16343
  };
16299
16344
  var cdTarget = (words) => {
@@ -16345,7 +16390,7 @@ function rawInvocations(command, dialect = "posix", depth = 0) {
16345
16390
  const name = commandName(words[0]);
16346
16391
  if (CD.has(name)) {
16347
16392
  const target = cdTarget(words);
16348
- dir = target === null ? os3.homedir() : joinDir(dir, target);
16393
+ dir = target === null ? os4.homedir() : joinDir(dir, target);
16349
16394
  continue;
16350
16395
  }
16351
16396
  if (PUSHD.has(name)) {
@@ -17179,7 +17224,7 @@ var judgeInputSummary = (raw) => {
17179
17224
  };
17180
17225
 
17181
17226
  // packages/workit-core/src/autonomy.ts
17182
- import os4 from "node:os";
17227
+ import os5 from "node:os";
17183
17228
  import path18 from "node:path";
17184
17229
 
17185
17230
  // packages/workit-core/src/core/safe-write.ts
@@ -17208,9 +17253,9 @@ function writeFileExclusive(file, content, mode) {
17208
17253
  // packages/workit-core/src/autonomy.ts
17209
17254
  var accountHome = () => {
17210
17255
  try {
17211
- return os4.userInfo().homedir;
17256
+ return os5.userInfo().homedir;
17212
17257
  } catch {
17213
- return os4.homedir();
17258
+ return os5.homedir();
17214
17259
  }
17215
17260
  };
17216
17261
  var grantsHome = { resolve: accountHome };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@brainervirus/workit-opencode",
3
- "version": "8.11.0",
3
+ "version": "8.12.1",
4
4
  "private": false,
5
5
  "description": "Workit OpenCode plugin — native tools, adaptive policy, and sixteen method skills",
6
6
  "keywords": [
@@ -39,7 +39,7 @@
39
39
  "typecheck": "tsc --noEmit"
40
40
  },
41
41
  "dependencies": {
42
- "@brainervirus/workit-core": "^8.11.0"
42
+ "@brainervirus/workit-core": "^8.12.1"
43
43
  },
44
44
  "devDependencies": {
45
45
  "@opencode/plugin": "2.0.18"