@agfpd/iapeer 0.4.133 → 0.4.134

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.
@@ -77,7 +77,7 @@ The full list of `iapeer <command>`. General rules: `--help` / `-h` anywhere in
77
77
  |---|---|
78
78
  | `enable <plugin> [peer] [--no-setup]` | Install and enable a capability plugin for a peer (across runtimes), run its setup step. |
79
79
  | `native-memory <off\|on> (--peer <p> \| --all)` | Turn off/restore a peer's runtimes' native memory. |
80
- | `trust-hooks <hooks.json> [--check]` | Pre-trust codex hooks from a file (without the modal). `--check` — a divergence report. |
80
+ | `trust-hooks <hooks.json> [--check]` | Pre-trust codex hooks from a file (without the modal). `--check` — a divergence report. The core also re-asserts the trust of `<cwd>/.codex/hooks.json` on EVERY codex launch (idempotent), and `rename` / `approval-mode yolo` restore what must stay trusted — a codex peer boots to its input with no human even after its trust was wiped (18.10). |
81
81
 
82
82
  ## Agent self-calls
83
83
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@agfpd/iapeer",
3
- "version": "0.4.133",
3
+ "version": "0.4.134",
4
4
  "description": "Run Claude Code and Codex CLI as local background agents that message each other, wake on demand, and share one memory.",
5
5
  "license": "Apache-2.0",
6
6
  "author": "agfpd",
@@ -161,6 +161,10 @@ export function removeCodexApproval(cwd: string, env: NodeJS.ProcessEnv = proces
161
161
  return path
162
162
  }
163
163
  writeFileAtomic(path, `${JSON.stringify(obj, null, 2)}\n`, 0o644)
164
+ // The trust wipe above is cwd-wide (codex keys state POSITIONALLY, so removing our group shifts the
165
+ // others' keys). Re-seed whatever hooks REMAIN — the memory provider's among them — or the next codex
166
+ // boot stops at «hooks need review» (incident 18.10).
167
+ preSeedCodexHooksTrust(path, env)
164
168
  return path
165
169
  }
166
170
 
package/src/cli/index.ts CHANGED
@@ -1439,9 +1439,13 @@ export async function renamePeerCli(
1439
1439
  const { preTrustCodexCwd, removeCodexCwdTrust } = await import('../launch/nativeMemory.ts')
1440
1440
  preTrustCodexCwd(newCwd, env)
1441
1441
  removeCodexCwdTrust(oldCwd, env)
1442
- const { removeCodexHooksTrustUnder } = await import('../launch/codexHooksTrust.ts')
1442
+ const { removeCodexHooksTrustUnder, preSeedCodexHooksTrust } = await import('../launch/codexHooksTrust.ts')
1443
1443
  removeCodexHooksTrustUnder(oldCwd, env)
1444
- sideEffects.push('codex-trust: re-trusted new cwd + cleaned old')
1444
+ // Hooks trust is keyed by the hooks.json PATH, so it must move with the cwd — without this a
1445
+ // rename round-trip (a→b→a) wiped it entirely and codex stopped at «hooks need review» (18.10).
1446
+ const newHooks = join(newCwd, '.codex', 'hooks.json')
1447
+ if (existsSync(newHooks)) preSeedCodexHooksTrust(newHooks, env)
1448
+ sideEffects.push('codex-trust: re-trusted new cwd (+ hooks) + cleaned old')
1445
1449
  } catch (e) {
1446
1450
  sideEffects.push(`codex-trust: failed (${e instanceof Error ? e.message : String(e)})`)
1447
1451
  }
@@ -41,10 +41,11 @@
41
41
 
42
42
  import { homedir } from 'os'
43
43
  import { join } from 'path'
44
- import { readdirSync, realpathSync, statSync } from 'fs'
44
+ import { existsSync, readdirSync, realpathSync, statSync } from 'fs'
45
+ import { preSeedCodexHooksTrust } from '../codexHooksTrust.ts'
45
46
  import { codexSessionCwd, lastTimestampedEntryMs } from './transcriptTail.ts'
46
47
  import { detectNumberedModal } from './modalDetect.ts'
47
- import type { ApprovalMode, ControlCommand, ControlPlan, LaunchAdapterConfig, LaunchSpec, RuntimeAdapter } from '../types.ts'
48
+ import type { ApprovalMode, ControlCommand, ControlPlan, LaunchAdapterConfig, LaunchSpec, PreparedLaunch, RuntimeAdapter } from '../types.ts'
48
49
 
49
50
  /**
50
51
  * The `/goal` subcommands we will type into a live codex session (see executeControl → 'goal').
@@ -170,6 +171,27 @@ export const codexAdapter: RuntimeAdapter = {
170
171
  kind: 'tui',
171
172
  usesDoctrine: true,
172
173
 
174
+ /**
175
+ * Hooks trust, re-asserted on EVERY launch (incident 18.10: oc-test-nemo/codex stopped at «PostToolUse
176
+ * hooks — 1 hook needs review» after a rename round-trip had wiped its `[hooks.state]` — a fresh codex
177
+ * that meets an untrusted hook waits for a human forever). The invariant «a codex peer boots to its
178
+ * input with no human» therefore lives HERE, not only at provision time: whatever erased the trust
179
+ * (rename, an approval-mode flip, a hand edit of config.toml), the next launch restores it. The peer's
180
+ * `.codex/hooks.json` is operator/provider-owned configuration, trusted like its `.mcp.json`.
181
+ * Idempotent (no write when the hashes already match); a failure is a launch WARNING, never a block —
182
+ * the modal is still better than no session, and the warning names it.
183
+ */
184
+ prepareLaunch(spec, _baseEnv, cfg): PreparedLaunch {
185
+ const env = cfg.env ?? process.env
186
+ const hooks = join(spec.cwd, '.codex', 'hooks.json')
187
+ const warnings: string[] = []
188
+ if (existsSync(hooks)) {
189
+ const t = preSeedCodexHooksTrust(hooks, env)
190
+ if (t.state === 'failed') warnings.push(`codex hooks trust not seeded (${t.detail ?? 'unknown'}) — a review modal may block the boot`)
191
+ }
192
+ return { env: {}, ...(warnings.length ? { warnings } : {}) }
193
+ },
194
+
173
195
  /**
174
196
  * Delivery markers for submitIntoTui (docs/Рантайм codex "Доставка"):
175
197
  * - promptGlyphs ['›'] — codex's input-row arrow (the same stable invariant as