@tekmidian/pai 0.54.1 → 0.56.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/dist/{aibroker-client-CNfIBrl5.mjs → aibroker-client-B8Wtasez.mjs} +1 -1
- package/dist/{aibroker-client-DzkTpVjx.mjs → aibroker-client-BK1h--W_.mjs} +3 -3
- package/dist/{aibroker-client-DzkTpVjx.mjs.map → aibroker-client-BK1h--W_.mjs.map} +1 -1
- package/dist/{indexer-backend-CdvCJCkD.mjs → async-CLvuY7b-.mjs} +7 -7
- package/dist/async-CLvuY7b-.mjs.map +1 -0
- package/dist/auto-route-CF8WNaoy.mjs +100 -0
- package/dist/auto-route-CF8WNaoy.mjs.map +1 -0
- package/dist/{chain-CZKlI0hq.mjs → chain-26f7uGUs.mjs} +4 -4
- package/dist/{chain-CZKlI0hq.mjs.map → chain-26f7uGUs.mjs.map} +1 -1
- package/dist/cli/index.mjs +22 -23
- package/dist/cli/index.mjs.map +1 -1
- package/dist/cli/program.d.mts.map +1 -1
- package/dist/cli/program.mjs +22 -23
- package/dist/{clusters-Cw_P6lO-.mjs → clusters-Ci1mseh2.mjs} +4 -36
- package/dist/clusters-Ci1mseh2.mjs.map +1 -0
- package/dist/{config-B3EPzRjf.mjs → config-B93YS8tP.mjs} +3 -3
- package/dist/{config-B3EPzRjf.mjs.map → config-B93YS8tP.mjs.map} +1 -1
- package/dist/{config-Bn9jpblO.mjs → config-D1omG_UU.mjs} +3 -3
- package/dist/{config-Bn9jpblO.mjs.map → config-D1omG_UU.mjs.map} +1 -1
- package/dist/{config-RjeVGJ7K.mjs → config-DCYWFaEi.mjs} +1 -1
- package/dist/{context-handover-cache-CXyH6QsC.mjs → context-handover-cache-k2kWbE6G.mjs} +82 -99
- package/dist/context-handover-cache-k2kWbE6G.mjs.map +1 -0
- package/dist/daemon/index.mjs +18 -24
- package/dist/daemon/index.mjs.map +1 -1
- package/dist/daemon-BOWol-LF.mjs +19 -0
- package/dist/{daemon-aJTxzg20.mjs → daemon-BsuM0UdV.mjs} +97 -466
- package/dist/daemon-BsuM0UdV.mjs.map +1 -0
- package/dist/daemon-mcp/index.mjs +10 -10
- package/dist/daemon-mcp/index.mjs.map +1 -1
- package/dist/{detector-DWXkeTlk.mjs → detector-3g7XuU1r.mjs} +5 -12
- package/dist/detector-3g7XuU1r.mjs.map +1 -0
- package/dist/detector-DgDn56j-.mjs +3 -0
- package/dist/{embeddings-ClqKtLZ8.mjs → embeddings-BNv3TQC5.mjs} +1 -1
- package/dist/{embeddings-DvRKcQyt.mjs → embeddings-DfrYNIng.mjs} +1 -1
- package/dist/{embeddings-DvRKcQyt.mjs.map → embeddings-DfrYNIng.mjs.map} +1 -1
- package/dist/factory-C9wGUe30.mjs +3 -0
- package/dist/factory-DiuntvwG.mjs +250 -0
- package/dist/factory-DiuntvwG.mjs.map +1 -0
- package/dist/{fallback-CCFIpPha.mjs → fallback-CVe3sb94.mjs} +192 -134
- package/dist/fallback-CVe3sb94.mjs.map +1 -0
- package/dist/federation-db-CJDw_Pwq.mjs +3 -0
- package/dist/{db-DJ8rk0VM.mjs → federation-db-w8e-sKjp.mjs} +5 -5
- package/dist/federation-db-w8e-sKjp.mjs.map +1 -0
- package/dist/{helpers-crDEr6S2.mjs → helpers-D9WkIf9R.mjs} +1 -1
- package/dist/{helpers-crDEr6S2.mjs.map → helpers-D9WkIf9R.mjs.map} +1 -1
- package/dist/hooks/capture-all-events.mjs.map +1 -1
- package/dist/hooks/capture-session-summary.mjs.map +1 -1
- package/dist/hooks/capture-tool-output.mjs.map +1 -1
- package/dist/hooks/context-compression-hook.mjs.map +1 -1
- package/dist/hooks/load-core-context.mjs +5 -0
- package/dist/hooks/load-core-context.mjs.map +2 -2
- package/dist/hooks/load-project-context.mjs.map +1 -1
- package/dist/hooks/post-compact-inject.mjs.map +1 -1
- package/dist/hooks/route-agents-to-worker.mjs.map +1 -1
- package/dist/hooks/route-edits-to-worker.mjs +1 -1
- package/dist/hooks/route-edits-to-worker.mjs.map +2 -2
- package/dist/hooks/security-validator.mjs +8367 -19
- package/dist/hooks/security-validator.mjs.map +4 -4
- package/dist/hooks/stop-hook.mjs.map +2 -2
- package/dist/hooks/whisper-rules.mjs.map +2 -2
- package/dist/hooks/worker-proxy.mjs.map +1 -1
- package/dist/hooks/worker-status-line.mjs.map +2 -2
- package/dist/hooks/worker-supervision.mjs.map +1 -1
- package/dist/index.d.mts +327 -100
- package/dist/index.d.mts.map +1 -1
- package/dist/index.mjs +7 -11
- package/dist/indexer-backend-Cc-_NK3q.mjs +1 -0
- package/dist/indexer-backend-DcDtin1O.mjs +5 -0
- package/dist/{ipc-client-C6NryMMb.mjs → ipc-client-Dasm515c.mjs} +2 -2
- package/dist/{ipc-client-C6NryMMb.mjs.map → ipc-client-Dasm515c.mjs.map} +1 -1
- package/dist/kg-entity-Cj8Q6YmU.mjs +29 -0
- package/dist/kg-entity-Cj8Q6YmU.mjs.map +1 -0
- package/dist/{latent-ideas-BfL4nCQ3.mjs → latent-ideas-BRy6HNwg.mjs} +4 -4
- package/dist/{latent-ideas-BfL4nCQ3.mjs.map → latent-ideas-BRy6HNwg.mjs.map} +1 -1
- package/dist/{link-boost-C5PaNdzm.mjs → link-boost-BptbAPuv.mjs} +1 -1
- package/dist/{link-boost-C5PaNdzm.mjs.map → link-boost-BptbAPuv.mjs.map} +1 -1
- package/dist/{main-resolver-Bt1f6jJc.mjs → main-resolver-Dx-pxic1.mjs} +56 -31
- package/dist/main-resolver-Dx-pxic1.mjs.map +1 -0
- package/dist/main-resolver-uDtK9p6e.mjs +7 -0
- package/dist/merge-BncjJTfb.mjs +3 -0
- package/dist/merge-xoyfZQ4W.mjs +6 -0
- package/dist/merge-xoyfZQ4W.mjs.map +1 -0
- package/dist/{migrate-CfERwXhY.mjs → migrate-BD7D8EEh.mjs} +21 -54
- package/dist/migrate-BD7D8EEh.mjs.map +1 -0
- package/dist/{neighborhood-CETR_P4y.mjs → neighborhood-D8uscnGy.mjs} +4 -25
- package/dist/neighborhood-D8uscnGy.mjs.map +1 -0
- package/dist/{note-context-DCcRWBoN.mjs → note-context-CgffaUMh.mjs} +3 -23
- package/dist/note-context-CgffaUMh.mjs.map +1 -0
- package/dist/{pai-home-ChAOupZc.mjs → pai-home-CeOIYltV.mjs} +2 -2
- package/dist/pai-home-CeOIYltV.mjs.map +1 -0
- package/dist/{pai-marker-B20KqhA8.mjs → pai-marker-D1MMswkz.mjs} +1 -1
- package/dist/{pai-marker-B20KqhA8.mjs.map → pai-marker-D1MMswkz.mjs.map} +1 -1
- package/dist/{planner-D3keWys5.mjs → planner-ye7wrrfB.mjs} +7 -7
- package/dist/{planner-D3keWys5.mjs.map → planner-ye7wrrfB.mjs.map} +1 -1
- package/dist/{postgres-CUSXWgTG.mjs → postgres-nvU5pShF.mjs} +863 -4
- package/dist/postgres-nvU5pShF.mjs.map +1 -0
- package/dist/{program-B3eRMhff.mjs → program-DuC1RcaO.mjs} +2268 -1402
- package/dist/program-DuC1RcaO.mjs.map +1 -0
- package/dist/query-feedback-COYCnvHQ.mjs +3 -0
- package/dist/{query-feedback-CTs_jx6i.mjs → query-feedback-xz5axTj3.mjs} +3 -3
- package/dist/query-feedback-xz5axTj3.mjs.map +1 -0
- package/dist/{db-Ddns80yf.mjs → registry-db-Bkpbp7Gf.mjs} +5 -5
- package/dist/registry-db-Bkpbp7Gf.mjs.map +1 -0
- package/dist/registry-db-DwXpf7yF.mjs +3 -0
- package/dist/registry-postgres-B07-hmn8.mjs +795 -0
- package/dist/registry-postgres-B07-hmn8.mjs.map +1 -0
- package/dist/registry-sqlite-CkGND_tm.mjs +593 -0
- package/dist/registry-sqlite-CkGND_tm.mjs.map +1 -0
- package/dist/{reranker-B5qUTamW.mjs → reranker-BS5gqGeF.mjs} +1 -1
- package/dist/{reranker-HHmhZk6v.mjs → reranker-CRVawoEh.mjs} +1 -1
- package/dist/{reranker-HHmhZk6v.mjs.map → reranker-CRVawoEh.mjs.map} +1 -1
- package/dist/router-BXOf_e9e.mjs +3 -0
- package/dist/{router-DBAZfE7X.mjs → router-BdxdsAvs.mjs} +2 -2
- package/dist/{router-DBAZfE7X.mjs.map → router-BdxdsAvs.mjs.map} +1 -1
- package/dist/{run-DLG25bzt.mjs → run-CqRvXGjd.mjs} +309 -49
- package/dist/run-CqRvXGjd.mjs.map +1 -0
- package/dist/{runtime-paths-B0P1TvUr.mjs → runtime-paths-BRwDeBEg.mjs} +1 -1
- package/dist/{runtime-paths-B0P1TvUr.mjs.map → runtime-paths-BRwDeBEg.mjs.map} +1 -1
- package/dist/search-BQHL5wDr.mjs +3 -0
- package/dist/search-BaTbyWjK.mjs +107 -0
- package/dist/search-BaTbyWjK.mjs.map +1 -0
- package/dist/{server-CGiHdaUp.mjs → server-CGuZFOeR.mjs} +4 -4
- package/dist/{server-CGiHdaUp.mjs.map → server-CGuZFOeR.mjs.map} +1 -1
- package/dist/{session-keepalive-DklS8VmU.mjs → session-keepalive-BQ6AQ9ez.mjs} +7 -7
- package/dist/{session-keepalive-DklS8VmU.mjs.map → session-keepalive-BQ6AQ9ez.mjs.map} +1 -1
- package/dist/skills/Plan/SKILL.md +1 -1
- package/dist/{sources-KBGEA_E6.mjs → sources-BBe3AZ-W.mjs} +8 -27
- package/dist/sources-BBe3AZ-W.mjs.map +1 -0
- package/dist/sqlite-D9p5a4qe.mjs +935 -0
- package/dist/sqlite-D9p5a4qe.mjs.map +1 -0
- package/dist/state-CwlGAKgF.mjs +3 -0
- package/dist/{state-DwrsOoMi.mjs → state-n13uPK5B.mjs} +6 -5
- package/dist/state-n13uPK5B.mjs.map +1 -0
- package/dist/{stop-words-BaMEGVeY.mjs → stop-words-ClCwO8mZ.mjs} +1 -1
- package/dist/{stop-words-BaMEGVeY.mjs.map → stop-words-ClCwO8mZ.mjs.map} +1 -1
- package/dist/{themes-BVoAnLZj.mjs → themes-B2v7RNnA.mjs} +3 -3
- package/dist/{themes-BVoAnLZj.mjs.map → themes-B2v7RNnA.mjs.map} +1 -1
- package/dist/{tools-BEqiJt_j.mjs → tools-Diro2s8J.mjs} +157 -398
- package/dist/tools-Diro2s8J.mjs.map +1 -0
- package/dist/{tools-BwsOTmjh.mjs → tools-KgL1rkPD.mjs} +4 -4
- package/dist/{trace-Cy8quQTm.mjs → trace-BRflVyBi.mjs} +1 -1
- package/dist/{trace-Cy8quQTm.mjs.map → trace-BRflVyBi.mjs.map} +1 -1
- package/dist/{utils-BD8g8oSf.mjs → utils-BrX9FLeK.mjs} +1 -1
- package/dist/{utils-CJymHkYm.mjs → utils-C9HsYDpO.mjs} +1 -1
- package/dist/{utils-CJymHkYm.mjs.map → utils-C9HsYDpO.mjs.map} +1 -1
- package/dist/{vault-indexer-C5i-OAyr.mjs → vault-indexer-DHYBpRZ5.mjs} +2 -2
- package/dist/{vault-indexer-C5i-OAyr.mjs.map → vault-indexer-DHYBpRZ5.mjs.map} +1 -1
- package/dist/{wakeup-Yk5lQ0jb.mjs → wakeup-D0uvqLsE.mjs} +95 -4
- package/dist/wakeup-D0uvqLsE.mjs.map +1 -0
- package/dist/work-queue-worker-DEbWsrDQ.mjs +11 -0
- package/dist/{work-queue-worker-utPp4hUv.mjs → work-queue-worker-DufMOtrL.mjs} +9 -9
- package/dist/work-queue-worker-DufMOtrL.mjs.map +1 -0
- package/dist/{zettelkasten-DezbXghl.mjs → zettelkasten-BPxSOalU.mjs} +4 -4
- package/dist/{zettelkasten-DezbXghl.mjs.map → zettelkasten-BPxSOalU.mjs.map} +1 -1
- package/docker/init.sql +5 -1
- package/docs/commands/README.md +5 -0
- package/docs/commands/audit.md +1 -1
- package/docs/commands/backup.md +1 -1
- package/docs/commands/clear-names.md +1 -1
- package/docs/commands/config.md +4 -4
- package/docs/commands/daemon.md +1 -1
- package/docs/commands/db.md +15 -1
- package/docs/commands/end.md +1 -1
- package/docs/commands/help.md +1 -1
- package/docs/commands/hooks-db.md +47 -0
- package/docs/commands/identity.md +1 -1
- package/docs/commands/kg.md +1 -1
- package/docs/commands/launch.md +1 -1
- package/docs/commands/mcp.md +1 -1
- package/docs/commands/memory.md +1 -1
- package/docs/commands/notify.md +1 -1
- package/docs/commands/observation.md +1 -1
- package/docs/commands/obsidian.md +1 -1
- package/docs/commands/pause.md +1 -1
- package/docs/commands/project.md +1 -1
- package/docs/commands/projects.md +1 -1
- package/docs/commands/registry.md +1 -1
- package/docs/commands/restore.md +1 -1
- package/docs/commands/session.md +2 -2
- package/docs/commands/sessions.md +1 -1
- package/docs/commands/setup.md +1 -1
- package/docs/commands/shell-init.md +1 -1
- package/docs/commands/skill.md +1 -1
- package/docs/commands/task.md +1 -1
- package/docs/commands/topic.md +1 -1
- package/docs/commands/update.md +1 -1
- package/docs/commands/worker.md +1 -1
- package/docs/commands/zettel.md +1 -1
- package/docs/design/postgres-only.md +438 -0
- package/docs/design/registry-method-map.md +174 -0
- package/package.json +1 -1
- package/src/hooks/pre-compact.sh +2 -40
- package/src/hooks/session-hooks-db.test.ts +93 -0
- package/src/hooks/session-stop.sh +2 -26
- package/src/hooks/ts/lib/edit-gate.test.ts +9 -0
- package/src/hooks/ts/lib/edit-gate.ts +5 -2
- package/src/hooks/ts/lib/plutil-guard.test.ts +54 -0
- package/src/hooks/ts/lib/plutil-guard.ts +43 -0
- package/src/hooks/ts/lib/worker-git-guard.test.ts +134 -0
- package/src/hooks/ts/lib/worker-git-guard.ts +103 -0
- package/src/hooks/ts/pre-tool-use/security-validator.test.ts +68 -0
- package/src/hooks/ts/pre-tool-use/security-validator.ts +69 -21
- package/src/hooks/ts/session-start/load-core-context.ts +13 -0
- package/src/hooks/ts/session-start/session-start-worker-guard.test.ts +13 -0
- package/dist/auto-route-CcD0OWWB.mjs +0 -86
- package/dist/auto-route-CcD0OWWB.mjs.map +0 -1
- package/dist/clusters-Cw_P6lO-.mjs.map +0 -1
- package/dist/context-handover-cache-CXyH6QsC.mjs.map +0 -1
- package/dist/daemon-CknQ6YGZ.mjs +0 -25
- package/dist/daemon-aJTxzg20.mjs.map +0 -1
- package/dist/db-BOBfewFH.mjs +0 -3
- package/dist/db-DJ8rk0VM.mjs.map +0 -1
- package/dist/db-DbY2O8QO.mjs +0 -3
- package/dist/db-Ddns80yf.mjs.map +0 -1
- package/dist/detect-Bf2z-oKB.mjs +0 -86
- package/dist/detect-Bf2z-oKB.mjs.map +0 -1
- package/dist/detector-CkwkXuGh.mjs +0 -5
- package/dist/detector-DWXkeTlk.mjs.map +0 -1
- package/dist/factory-Ba8j9K7q.mjs +0 -3
- package/dist/factory-Bt7TWQje.mjs +0 -150
- package/dist/factory-Bt7TWQje.mjs.map +0 -1
- package/dist/fallback-CCFIpPha.mjs.map +0 -1
- package/dist/indexer-backend-CdvCJCkD.mjs.map +0 -1
- package/dist/kg-entity-BSW7ra8i.mjs +0 -176
- package/dist/kg-entity-BSW7ra8i.mjs.map +0 -1
- package/dist/main-resolver-Bt1f6jJc.mjs.map +0 -1
- package/dist/main-resolver-DYHhw5Ig.mjs +0 -7
- package/dist/migrate-CfERwXhY.mjs.map +0 -1
- package/dist/neighborhood-CETR_P4y.mjs.map +0 -1
- package/dist/note-context-DCcRWBoN.mjs.map +0 -1
- package/dist/pai-home-ChAOupZc.mjs.map +0 -1
- package/dist/postgres-CUSXWgTG.mjs.map +0 -1
- package/dist/program-B3eRMhff.mjs.map +0 -1
- package/dist/query-feedback-Bm6XvCmg.mjs +0 -3
- package/dist/query-feedback-CTs_jx6i.mjs.map +0 -1
- package/dist/router-CremHKTI.mjs +0 -3
- package/dist/run-DLG25bzt.mjs.map +0 -1
- package/dist/search-B69cQwDB.mjs +0 -303
- package/dist/search-B69cQwDB.mjs.map +0 -1
- package/dist/search-fb-5ovj4.mjs +0 -4
- package/dist/sources-KBGEA_E6.mjs.map +0 -1
- package/dist/sqlite-By6r2YhZ.mjs +0 -271
- package/dist/sqlite-By6r2YhZ.mjs.map +0 -1
- package/dist/state-Ca0ltLgI.mjs +0 -3
- package/dist/state-DwrsOoMi.mjs.map +0 -1
- package/dist/sync-Btcb6xA4.mjs +0 -310
- package/dist/sync-Btcb6xA4.mjs.map +0 -1
- package/dist/tools-BEqiJt_j.mjs.map +0 -1
- package/dist/wakeup-Yk5lQ0jb.mjs.map +0 -1
- package/dist/work-queue-worker-DsdJx-jn.mjs +0 -14
- package/dist/work-queue-worker-utPp4hUv.mjs.map +0 -1
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import { C as readWorkersSection, E as resolveProviderKey, S as providerKeyPath, T as resolveModelCapability, _ as isModelCapability, d as WorkersConfigError, f as assertProviderRunnable, p as classModelCapability } from "./config-
|
|
3
|
-
import { _ as ledgerPath, a as claudeCommand, b as workersLogDir, c as isQuotaFailure, f as resolveCapabilityRun, g as eventsPath, h as ensureNoMcpConfig, i as buildRunEnv, l as nextAutoProvider, m as setCooldown, n as ensureProxyRunning, o as capabilityForRun, p as resolveTarget, t as DEFAULT_PROXY_PORT, v as panesDir, y as statusPath } from "./server-
|
|
1
|
+
import { i as getRegistryBackend } from "./factory-DiuntvwG.mjs";
|
|
2
|
+
import { C as readWorkersSection, E as resolveProviderKey, S as providerKeyPath, T as resolveModelCapability, _ as isModelCapability, d as WorkersConfigError, f as assertProviderRunnable, p as classModelCapability } from "./config-B93YS8tP.mjs";
|
|
3
|
+
import { _ as ledgerPath, a as claudeCommand, b as workersLogDir, c as isQuotaFailure, f as resolveCapabilityRun, g as eventsPath, h as ensureNoMcpConfig, i as buildRunEnv, l as nextAutoProvider, m as setCooldown, n as ensureProxyRunning, o as capabilityForRun, p as resolveTarget, t as DEFAULT_PROXY_PORT, v as panesDir, y as statusPath } from "./server-CGuZFOeR.mjs";
|
|
4
4
|
import { appendFileSync, closeSync, existsSync, mkdirSync, mkdtempSync, openSync, readFileSync, readdirSync, renameSync, rmSync, statSync, unlinkSync, writeFileSync, writeSync } from "node:fs";
|
|
5
5
|
import { homedir, tmpdir } from "node:os";
|
|
6
6
|
import { dirname, isAbsolute, join, relative, resolve } from "node:path";
|
|
@@ -454,6 +454,18 @@ function ageOf(ts, now = /* @__PURE__ */ new Date()) {
|
|
|
454
454
|
const s = Math.max(0, Math.floor((now.getTime() - t) / 1e3));
|
|
455
455
|
return s < 90 ? `${s}s` : `${Math.floor(s / 60)}m`;
|
|
456
456
|
}
|
|
457
|
+
/** Precise elapsed time: "45s", "1m 23s", "12m 05s", "1h 02m 05s" — seconds zero-padded after a larger unit. */
|
|
458
|
+
function elapsedOf(ts, now = /* @__PURE__ */ new Date()) {
|
|
459
|
+
const t = Date.parse(ts.replace(" ", "T"));
|
|
460
|
+
if (Number.isNaN(t)) return "?";
|
|
461
|
+
const secs = Math.max(0, Math.floor((now.getTime() - t) / 1e3));
|
|
462
|
+
const hours = Math.floor(secs / 3600);
|
|
463
|
+
const mins = Math.floor(secs % 3600 / 60);
|
|
464
|
+
const sec = secs % 60;
|
|
465
|
+
if (hours > 0) return `${hours}h ${String(mins).padStart(2, "0")}m ${String(sec).padStart(2, "0")}s`;
|
|
466
|
+
if (mins > 0) return `${mins}m ${String(sec).padStart(2, "0")}s`;
|
|
467
|
+
return `${sec}s`;
|
|
468
|
+
}
|
|
457
469
|
/** One-line description of a tool call, e.g. "Bash: npm test". */
|
|
458
470
|
function describeTool(name, inp) {
|
|
459
471
|
if (typeof inp !== "object" || inp === null) return name;
|
|
@@ -563,8 +575,8 @@ function worktreeBranch(id) {
|
|
|
563
575
|
function worktreePath(logDir, id) {
|
|
564
576
|
return join(worktreesDir(logDir), id);
|
|
565
577
|
}
|
|
566
|
-
/** Run git in `cwd
|
|
567
|
-
function
|
|
578
|
+
/** Run git in `cwd` with an optional env override, trimmed stdout, stderr on failure. */
|
|
579
|
+
function runGit(cwd, args, env) {
|
|
568
580
|
try {
|
|
569
581
|
return execFileSync("git", [
|
|
570
582
|
"-C",
|
|
@@ -577,7 +589,8 @@ function git(cwd, args) {
|
|
|
577
589
|
"ignore",
|
|
578
590
|
"pipe",
|
|
579
591
|
"pipe"
|
|
580
|
-
]
|
|
592
|
+
],
|
|
593
|
+
...env ? { env } : {}
|
|
581
594
|
}).trim();
|
|
582
595
|
} catch (e) {
|
|
583
596
|
const err = e;
|
|
@@ -585,6 +598,10 @@ function git(cwd, args) {
|
|
|
585
598
|
throw new Error(`git ${args.join(" ")} in ${cwd}: ${why.trim()}`);
|
|
586
599
|
}
|
|
587
600
|
}
|
|
601
|
+
/** Run git in `cwd`, returning trimmed stdout; throws with stderr on failure. */
|
|
602
|
+
function git(cwd, args) {
|
|
603
|
+
return runGit(cwd, args);
|
|
604
|
+
}
|
|
588
605
|
/** Is `cwd` inside a git repository (a .git dir — worktrees: a .git file)? */
|
|
589
606
|
function isGitRepo(cwd) {
|
|
590
607
|
try {
|
|
@@ -618,7 +635,43 @@ function worktreeWanted(flag, opts) {
|
|
|
618
635
|
return !promptLooksReadonly(opts.prompt ?? "");
|
|
619
636
|
}
|
|
620
637
|
/**
|
|
621
|
-
*
|
|
638
|
+
* Commit `cwd`'s current index + working tree (including untracked files) as
|
|
639
|
+
* a floating commit on top of HEAD, without touching the real index, working
|
|
640
|
+
* tree or HEAD: a temporary `GIT_INDEX_FILE` collects the snapshot, `git
|
|
641
|
+
* commit-tree` writes the commit object directly (it updates no ref). The
|
|
642
|
+
* caller then branches a worktree from that commit, so the worktree sees
|
|
643
|
+
* exactly what was on disk, uncommitted or not.
|
|
644
|
+
*/
|
|
645
|
+
function snapshotUncommitted(cwd, id, head) {
|
|
646
|
+
const idxDir = mkdtempSync(join(tmpdir(), "pai-worktree-idx-"));
|
|
647
|
+
const idx = join(idxDir, "index");
|
|
648
|
+
try {
|
|
649
|
+
const env = {
|
|
650
|
+
...process.env,
|
|
651
|
+
GIT_INDEX_FILE: idx
|
|
652
|
+
};
|
|
653
|
+
runGit(cwd, ["read-tree", head], env);
|
|
654
|
+
runGit(cwd, ["add", "-A"], env);
|
|
655
|
+
return runGit(cwd, [
|
|
656
|
+
"commit-tree",
|
|
657
|
+
runGit(cwd, ["write-tree"], env),
|
|
658
|
+
"-p",
|
|
659
|
+
head,
|
|
660
|
+
"-m",
|
|
661
|
+
`worker ${id}: snapshot of uncommitted checkout`
|
|
662
|
+
]);
|
|
663
|
+
} finally {
|
|
664
|
+
rmSync(idxDir, {
|
|
665
|
+
recursive: true,
|
|
666
|
+
force: true
|
|
667
|
+
});
|
|
668
|
+
}
|
|
669
|
+
}
|
|
670
|
+
/**
|
|
671
|
+
* Create the worktree and branch for `id` from `cwd`'s HEAD — or, when the
|
|
672
|
+
* checkout has uncommitted changes, from a snapshot commit of that dirty
|
|
673
|
+
* state (see `snapshotUncommitted`), so a worktree worker sees the same
|
|
674
|
+
* files the operator sees, not just what was last committed. Throws when git
|
|
622
675
|
* refuses (no commits yet, branch exists, …) — the caller decides whether to
|
|
623
676
|
* degrade to an in-place run.
|
|
624
677
|
*/
|
|
@@ -630,18 +683,22 @@ function addWorktree(logDir, id, cwd) {
|
|
|
630
683
|
});
|
|
631
684
|
const dir = worktreePath(logDir, id);
|
|
632
685
|
const branch = worktreeBranch(id);
|
|
633
|
-
const
|
|
686
|
+
const head = git(cwd, ["rev-parse", "HEAD"]);
|
|
687
|
+
const dirty = dirtyPaths(cwd).length > 0;
|
|
688
|
+
const base = dirty ? snapshotUncommitted(cwd, id, head) : head;
|
|
634
689
|
git(cwd, [
|
|
635
690
|
"worktree",
|
|
636
691
|
"add",
|
|
637
692
|
dir,
|
|
638
693
|
"-b",
|
|
639
|
-
branch
|
|
694
|
+
branch,
|
|
695
|
+
base
|
|
640
696
|
]);
|
|
641
697
|
return {
|
|
642
698
|
dir,
|
|
643
699
|
branch,
|
|
644
|
-
base
|
|
700
|
+
base,
|
|
701
|
+
snapshot: dirty
|
|
645
702
|
};
|
|
646
703
|
}
|
|
647
704
|
/**
|
|
@@ -707,6 +764,7 @@ function recordWorktree(logDir, status, info, ok) {
|
|
|
707
764
|
s.commits = commitsSince(info.dir, info.base);
|
|
708
765
|
s.worktreeDir = info.dir;
|
|
709
766
|
s.worktreeBase = info.base;
|
|
767
|
+
s.worktreeSnapshot = info.snapshot;
|
|
710
768
|
} else {
|
|
711
769
|
removeWorktree(s.cwd, info.dir, true);
|
|
712
770
|
try {
|
|
@@ -720,6 +778,7 @@ function recordWorktree(logDir, status, info, ok) {
|
|
|
720
778
|
s.worktreeDir = null;
|
|
721
779
|
s.worktreeBase = null;
|
|
722
780
|
s.commits = null;
|
|
781
|
+
s.worktreeSnapshot = null;
|
|
723
782
|
}
|
|
724
783
|
saveStatus(logDir, s);
|
|
725
784
|
return s;
|
|
@@ -839,6 +898,118 @@ function assertWorktreeClean(wtDir, id) {
|
|
|
839
898
|
const leftover = uncommittedPaths(wtDir);
|
|
840
899
|
if (leftover.length) throw new Error(`worker ${id}: the worktree ${wtDir} still holds uncommitted changes (${leftover.join(", ")}) — it was NOT removed; commit or copy them by hand, then re-run merge`);
|
|
841
900
|
}
|
|
901
|
+
/** Blob sha of `path` at `rev` in `cwd`, or null when it does not exist there. */
|
|
902
|
+
function blobAt(cwd, rev, path) {
|
|
903
|
+
try {
|
|
904
|
+
return git(cwd, [
|
|
905
|
+
"rev-parse",
|
|
906
|
+
"--verify",
|
|
907
|
+
"-q",
|
|
908
|
+
`${rev}:${path}`
|
|
909
|
+
]);
|
|
910
|
+
} catch {
|
|
911
|
+
return null;
|
|
912
|
+
}
|
|
913
|
+
}
|
|
914
|
+
/** Blob sha of `path` as it sits on disk in `cwd`, or null when it is absent. */
|
|
915
|
+
function workingBlob(cwd, path) {
|
|
916
|
+
if (!existsSync(join(cwd, path))) return null;
|
|
917
|
+
try {
|
|
918
|
+
return git(cwd, [
|
|
919
|
+
"hash-object",
|
|
920
|
+
"--",
|
|
921
|
+
path
|
|
922
|
+
]);
|
|
923
|
+
} catch {
|
|
924
|
+
return null;
|
|
925
|
+
}
|
|
926
|
+
}
|
|
927
|
+
/**
|
|
928
|
+
* Refuse a snapshot merge when the checkout differs from the snapshot the
|
|
929
|
+
* worker branched from, for any path the branch touched: the operator edited
|
|
930
|
+
* it, or it was created/deleted since — applying the branch's diff on top
|
|
931
|
+
* would silently discard that. Absent-in-both counts as equal.
|
|
932
|
+
*/
|
|
933
|
+
function assertNoSnapshotDrift(cwd, snapshot, paths, id) {
|
|
934
|
+
const drifted = paths.filter((p) => blobAt(cwd, snapshot, p) !== workingBlob(cwd, p)).sort();
|
|
935
|
+
if (!drifted.length) return;
|
|
936
|
+
throw new Error(`worker ${id}: the checkout ${cwd} has changed since the worktree's snapshot in paths the branch touches: ${drifted.join(", ")}. Resolve by hand, then re-run: pai worker merge ${id}. No merge was made; the worktree was kept.`);
|
|
937
|
+
}
|
|
938
|
+
/**
|
|
939
|
+
* `pai worker merge <id>` for a snapshot-based worktree (see `addWorktree`):
|
|
940
|
+
* git's own merge only moves committed history, and the snapshot commit was
|
|
941
|
+
* never on any branch reachable from `cwd`'s HEAD, so there is nothing to
|
|
942
|
+
* `git merge` here. Instead the worker's own changes — `git diff --binary
|
|
943
|
+
* <snapshot> <branch>` — are applied straight onto the checkout's working
|
|
944
|
+
* tree as uncommitted edits, exactly like the uncommitted state the worker
|
|
945
|
+
* started from. Works even if `cwd`'s HEAD moved since the snapshot: the
|
|
946
|
+
* diff is applied to files, not merged into a tree.
|
|
947
|
+
*/
|
|
948
|
+
function mergeSnapshotWorker(logDir, id, st) {
|
|
949
|
+
const snapshot = st.worktreeBase;
|
|
950
|
+
const branch = st.branch;
|
|
951
|
+
const worktreeDir = st.worktreeDir;
|
|
952
|
+
const salvaged = existsSync(worktreeDir) ? salvageUncommitted(worktreeDir, st.label || UNLABELED) : [];
|
|
953
|
+
if ((parseInt(git(st.cwd, [
|
|
954
|
+
"rev-list",
|
|
955
|
+
"--count",
|
|
956
|
+
`${snapshot}..${branch}`
|
|
957
|
+
]), 10) || 0) <= 0) throw new Error(`worker ${id}: branch ${branch} has no commits beyond its snapshot to merge. The worktree ${worktreeDir} was NOT removed — uncommitted work there would be destroyed. Commit it yourself, or drop everything with: pai worker discard ${id}`);
|
|
958
|
+
const changedPaths = git(st.cwd, [
|
|
959
|
+
"diff",
|
|
960
|
+
"--name-only",
|
|
961
|
+
snapshot,
|
|
962
|
+
branch
|
|
963
|
+
]).split("\n").filter(Boolean);
|
|
964
|
+
assertNoSnapshotDrift(st.cwd, snapshot, changedPaths, id);
|
|
965
|
+
const diff = execFileSync("git", [
|
|
966
|
+
"-C",
|
|
967
|
+
st.cwd,
|
|
968
|
+
"diff",
|
|
969
|
+
"--binary",
|
|
970
|
+
snapshot,
|
|
971
|
+
branch
|
|
972
|
+
], {
|
|
973
|
+
encoding: "utf8",
|
|
974
|
+
timeout: 3e4,
|
|
975
|
+
maxBuffer: 64 * 1024 * 1024
|
|
976
|
+
});
|
|
977
|
+
if (diff.trim()) try {
|
|
978
|
+
execFileSync("git", [
|
|
979
|
+
"-C",
|
|
980
|
+
st.cwd,
|
|
981
|
+
"apply",
|
|
982
|
+
"--binary"
|
|
983
|
+
], {
|
|
984
|
+
input: diff,
|
|
985
|
+
encoding: "utf8",
|
|
986
|
+
timeout: 3e4,
|
|
987
|
+
stdio: [
|
|
988
|
+
"pipe",
|
|
989
|
+
"pipe",
|
|
990
|
+
"pipe"
|
|
991
|
+
]
|
|
992
|
+
});
|
|
993
|
+
} catch (e) {
|
|
994
|
+
const err = e;
|
|
995
|
+
const why = (typeof err.stderr === "string" ? err.stderr : err.stderr?.toString("utf8")) || err.message || String(e);
|
|
996
|
+
throw new Error(`worker ${id}: git refused to apply ${branch}'s changes to ${st.cwd} — ${why.trim()}. The worktree ${worktreeDir} was kept: resolve by hand, then re-run merge`);
|
|
997
|
+
}
|
|
998
|
+
removeWorktree(st.cwd, worktreeDir, true);
|
|
999
|
+
try {
|
|
1000
|
+
git(st.cwd, [
|
|
1001
|
+
"branch",
|
|
1002
|
+
"-D",
|
|
1003
|
+
branch
|
|
1004
|
+
]);
|
|
1005
|
+
} catch {}
|
|
1006
|
+
saveStatus(logDir, {
|
|
1007
|
+
...st,
|
|
1008
|
+
merged: true
|
|
1009
|
+
});
|
|
1010
|
+
const base = `applied worker ${id}'s changes (branch ${branch}) to ${st.cwd} as uncommitted changes: ${changedPaths.join(", ")} (worktree removed, branch deleted)`;
|
|
1011
|
+
return salvaged.length ? `${base}; salvaged ${salvaged.length} uncommitted change(s) onto the branch first: ${salvaged.join(", ")}` : base;
|
|
1012
|
+
}
|
|
842
1013
|
/**
|
|
843
1014
|
* `pai worker merge <id>`: salvage whatever the worker left uncommitted onto
|
|
844
1015
|
* its branch, refuse when the original checkout is dirty in paths the branch
|
|
@@ -851,6 +1022,7 @@ function assertWorktreeClean(wtDir, id) {
|
|
|
851
1022
|
function mergeWorker(logDir, id) {
|
|
852
1023
|
const st = mustHaveBranch(logDir, id);
|
|
853
1024
|
if (st.merged) return `worker ${id}: branch ${st.branch} already merged`;
|
|
1025
|
+
if (st.worktreeSnapshot) return mergeSnapshotWorker(logDir, id, st);
|
|
854
1026
|
const salvaged = existsSync(st.worktreeDir) ? salvageUncommitted(st.worktreeDir, st.label || UNLABELED) : [];
|
|
855
1027
|
if ((parseInt(git(st.cwd, [
|
|
856
1028
|
"rev-list",
|
|
@@ -919,6 +1091,7 @@ function discardWorker(logDir, id) {
|
|
|
919
1091
|
branch: null,
|
|
920
1092
|
worktreeDir: null,
|
|
921
1093
|
worktreeBase: null,
|
|
1094
|
+
worktreeSnapshot: null,
|
|
922
1095
|
commits: null,
|
|
923
1096
|
merged: false
|
|
924
1097
|
});
|
|
@@ -935,14 +1108,28 @@ function mustHaveBranch(logDir, id) {
|
|
|
935
1108
|
* own branch (the no-commit rule holds for the main branch only), it must not
|
|
936
1109
|
* merge or push itself, and the parent or operator merges.
|
|
937
1110
|
*/
|
|
938
|
-
function worktreeSystemPrompt(id, branch, dir) {
|
|
1111
|
+
function worktreeSystemPrompt(id, branch, dir, snapshot = false) {
|
|
939
1112
|
return [
|
|
940
1113
|
"You are running in your own git worktree:",
|
|
941
1114
|
` ${dir} on branch ${branch} (worker id ${id}).`,
|
|
942
1115
|
"Commit your work on that branch as you go (git add / git commit) — committing here is expected;",
|
|
943
1116
|
"the no-commit rule applies to the main branch only, and this is not it.",
|
|
944
1117
|
"Do not merge, rebase or push; the operator merges your branch back with `pai worker merge`.",
|
|
945
|
-
"Use ONLY relative paths inside the worktree, never absolute worktree paths — absolute paths break after merge and leak machine layout."
|
|
1118
|
+
"Use ONLY relative paths inside the worktree, never absolute worktree paths — absolute paths break after merge and leak machine layout.",
|
|
1119
|
+
...snapshot ? ["This worktree was branched from a snapshot that includes files the parent checkout had uncommitted at spawn time — not just its last commit."] : []
|
|
1120
|
+
].join("\n");
|
|
1121
|
+
}
|
|
1122
|
+
/**
|
|
1123
|
+
* For headless runs WITHOUT a worktree: the worker shares the operator's
|
|
1124
|
+
* checkout with other in-flight workers, so a hook blocks git stash (except
|
|
1125
|
+
* list/show), reset, clean, checkout/restore of paths, switch, rebase and
|
|
1126
|
+
* merge — take baselines from measurements before editing, not from stash.
|
|
1127
|
+
*/
|
|
1128
|
+
function inPlaceSystemPrompt() {
|
|
1129
|
+
return [
|
|
1130
|
+
"You are running in the operator's shared git checkout, alongside other workers editing it at the same time.",
|
|
1131
|
+
"A hook blocks git stash (except list/show), reset, clean, checkout/restore of files, switch, rebase and merge — take baselines from measurements taken before you edit, not from stashing.",
|
|
1132
|
+
"Read-only git (status, diff, log, show, stash list) is fine."
|
|
946
1133
|
].join("\n");
|
|
947
1134
|
}
|
|
948
1135
|
|
|
@@ -2333,6 +2520,53 @@ function renderReport(c, prefix, r, cwd = "") {
|
|
|
2333
2520
|
if (r.notes) out.push(`${prefix}${c("bold", "notes")} ${shortText(r.notes, 120)}`);
|
|
2334
2521
|
return out;
|
|
2335
2522
|
}
|
|
2523
|
+
/** A summary that names its own deletion — the path is expected to be gone. */
|
|
2524
|
+
const DELETED_RE = /\b(delete|deleted|deleting|remove|removed|removing)\b/i;
|
|
2525
|
+
/**
|
|
2526
|
+
* Check every path a report's `changed` list claims against the filesystem:
|
|
2527
|
+
* it must exist (mtime at or after `startMs`, the run's start) unless its
|
|
2528
|
+
* summary says it was deleted, in which case it must be absent. Mechanical
|
|
2529
|
+
* only — counts, row totals and other free-text claims are not checked (a
|
|
2530
|
+
* worker's R report is trusted as written; a 2026-09-23 report claimed "181
|
|
2531
|
+
* rows saved" while it had written 31, and only its listed paths are
|
|
2532
|
+
* something the filesystem can confirm or refute).
|
|
2533
|
+
*/
|
|
2534
|
+
function verifyReportChanges(changed, cwd, startMs) {
|
|
2535
|
+
const failures = [];
|
|
2536
|
+
for (const ch of changed ?? []) {
|
|
2537
|
+
const raw = (ch.path ?? "").trim();
|
|
2538
|
+
if (!raw) continue;
|
|
2539
|
+
const abs = isAbsolute(raw) ? raw : resolve(cwd, raw);
|
|
2540
|
+
let mtimeMs;
|
|
2541
|
+
try {
|
|
2542
|
+
mtimeMs = statSync(abs).mtimeMs;
|
|
2543
|
+
} catch {
|
|
2544
|
+
mtimeMs = null;
|
|
2545
|
+
}
|
|
2546
|
+
if (DELETED_RE.test(ch.summary ?? "")) {
|
|
2547
|
+
if (mtimeMs !== null) failures.push({
|
|
2548
|
+
path: raw,
|
|
2549
|
+
reason: "not-deleted"
|
|
2550
|
+
});
|
|
2551
|
+
} else if (mtimeMs === null) failures.push({
|
|
2552
|
+
path: raw,
|
|
2553
|
+
reason: "missing"
|
|
2554
|
+
});
|
|
2555
|
+
else if (mtimeMs < startMs) failures.push({
|
|
2556
|
+
path: raw,
|
|
2557
|
+
reason: "stale"
|
|
2558
|
+
});
|
|
2559
|
+
}
|
|
2560
|
+
return {
|
|
2561
|
+
ok: failures.length === 0,
|
|
2562
|
+
failures
|
|
2563
|
+
};
|
|
2564
|
+
}
|
|
2565
|
+
/** The one-line note appended to a report/ledger when verify fails. */
|
|
2566
|
+
function verifyFailNote(v) {
|
|
2567
|
+
const paths = v.failures.map((f) => f.path).slice(0, 5).join(", ");
|
|
2568
|
+
return `verify: ${v.failures.length} claimed change${v.failures.length === 1 ? "" : "s"} not confirmed: ${paths}`;
|
|
2569
|
+
}
|
|
2336
2570
|
/** repo-relative display of a changed path when it lies under cwd. */
|
|
2337
2571
|
function relShort(p, cwd) {
|
|
2338
2572
|
if (!cwd) return p;
|
|
@@ -2362,35 +2596,30 @@ function asStringArray(v) {
|
|
|
2362
2596
|
/**
|
|
2363
2597
|
* The launch config of the project whose root_path is `cwd` or an ancestor
|
|
2364
2598
|
* of it (longest match wins) — null when no registered project covers it,
|
|
2365
|
-
* or when the matching project has no mcp/tools pin set. `
|
|
2366
|
-
* injectable for tests; production callers take the
|
|
2599
|
+
* or when the matching project has no mcp/tools pin set. `registry` is
|
|
2600
|
+
* injectable for tests; production callers take the process-wide backend.
|
|
2367
2601
|
*/
|
|
2368
|
-
function projectLaunchConfig(cwd,
|
|
2602
|
+
async function projectLaunchConfig(cwd, registry) {
|
|
2369
2603
|
const target = resolve(cwd);
|
|
2370
|
-
const
|
|
2371
|
-
|
|
2372
|
-
const
|
|
2373
|
-
|
|
2374
|
-
|
|
2375
|
-
|
|
2376
|
-
|
|
2377
|
-
|
|
2378
|
-
|
|
2379
|
-
|
|
2380
|
-
} catch {
|
|
2381
|
-
return null;
|
|
2382
|
-
}
|
|
2383
|
-
const mcp = asStringArray(parsed.mcp);
|
|
2384
|
-
const tools = asStringArray(parsed.tools);
|
|
2385
|
-
return mcp || tools ? {
|
|
2386
|
-
mcp,
|
|
2387
|
-
tools
|
|
2388
|
-
} : null;
|
|
2604
|
+
const rows = await (registry ?? await getRegistryBackend()).listProjectsByPathLengthDesc({ excludeArchived: true });
|
|
2605
|
+
for (const row of rows) {
|
|
2606
|
+
const root = resolve(row.root_path);
|
|
2607
|
+
if (target !== root && !target.startsWith(root + "/")) continue;
|
|
2608
|
+
if (!row.session_config) return null;
|
|
2609
|
+
let parsed;
|
|
2610
|
+
try {
|
|
2611
|
+
parsed = JSON.parse(row.session_config);
|
|
2612
|
+
} catch {
|
|
2613
|
+
return null;
|
|
2389
2614
|
}
|
|
2390
|
-
|
|
2391
|
-
|
|
2392
|
-
|
|
2615
|
+
const mcp = asStringArray(parsed.mcp);
|
|
2616
|
+
const tools = asStringArray(parsed.tools);
|
|
2617
|
+
return mcp || tools ? {
|
|
2618
|
+
mcp,
|
|
2619
|
+
tools
|
|
2620
|
+
} : null;
|
|
2393
2621
|
}
|
|
2622
|
+
return null;
|
|
2394
2623
|
}
|
|
2395
2624
|
|
|
2396
2625
|
//#endregion
|
|
@@ -2770,7 +2999,7 @@ async function runWorker(opts) {
|
|
|
2770
2999
|
const logDir = workersLogDir(config);
|
|
2771
3000
|
mkdirSync(logDir, { recursive: true });
|
|
2772
3001
|
if (opts.className === "plan" && !opts._planner) {
|
|
2773
|
-
const { runPlanner } = await import("./planner-
|
|
3002
|
+
const { runPlanner } = await import("./planner-ye7wrrfB.mjs");
|
|
2774
3003
|
return runPlanner(opts);
|
|
2775
3004
|
}
|
|
2776
3005
|
const parent = launchParent(opts.parent);
|
|
@@ -3117,7 +3346,7 @@ async function executeRun(a) {
|
|
|
3117
3346
|
];
|
|
3118
3347
|
} else if (!headless && !parsed.callerMcpConfig) {
|
|
3119
3348
|
const explicitMcp = [...a.mcpFlag ? [a.mcpFlag] : [], ...parsed.mcp];
|
|
3120
|
-
const projectLaunch = projectLaunchConfig(cwd);
|
|
3349
|
+
const projectLaunch = await projectLaunchConfig(cwd);
|
|
3121
3350
|
const picked = interactiveMcpTools(explicitMcp, parsed.callerTools, projectLaunch);
|
|
3122
3351
|
if (picked.mcpNames.length) mcpArgs = [
|
|
3123
3352
|
"--strict-mcp-config",
|
|
@@ -3136,7 +3365,8 @@ async function executeRun(a) {
|
|
|
3136
3365
|
if (headless) {
|
|
3137
3366
|
cmd.push("--output-format", "stream-json", "--verbose", "--input-format", "stream-json");
|
|
3138
3367
|
if (!parsed.callerSystemPrompt) cmd.push("--append-system-prompt", workerContractPrompt(a.className, a.reportFormat));
|
|
3139
|
-
if (worktree) cmd.push("--append-system-prompt", worktreeSystemPrompt(wid, worktree.branch, worktree.dir));
|
|
3368
|
+
if (worktree) cmd.push("--append-system-prompt", worktreeSystemPrompt(wid, worktree.branch, worktree.dir, worktree.snapshot));
|
|
3369
|
+
else cmd.push("--append-system-prompt", inPlaceSystemPrompt());
|
|
3140
3370
|
}
|
|
3141
3371
|
cmd = ensureToolSearch(cmd);
|
|
3142
3372
|
if (a.printCmd) {
|
|
@@ -3146,7 +3376,7 @@ async function executeRun(a) {
|
|
|
3146
3376
|
}));
|
|
3147
3377
|
return 0;
|
|
3148
3378
|
}
|
|
3149
|
-
|
|
3379
|
+
let status = {
|
|
3150
3380
|
id: wid,
|
|
3151
3381
|
pid: process.pid,
|
|
3152
3382
|
label,
|
|
@@ -3175,7 +3405,8 @@ async function executeRun(a) {
|
|
|
3175
3405
|
...worktree ? {
|
|
3176
3406
|
worktreeDir: worktree.dir,
|
|
3177
3407
|
branch: worktree.branch,
|
|
3178
|
-
worktreeBase: worktree.base
|
|
3408
|
+
worktreeBase: worktree.base,
|
|
3409
|
+
worktreeSnapshot: worktree.snapshot
|
|
3179
3410
|
} : {},
|
|
3180
3411
|
...a.specPath ? { spec: a.specPath } : {}
|
|
3181
3412
|
};
|
|
@@ -3377,6 +3608,20 @@ async function executeRun(a) {
|
|
|
3377
3608
|
} catch {}
|
|
3378
3609
|
}
|
|
3379
3610
|
}
|
|
3611
|
+
if (headless && ctx.resultReport?.changed?.length) {
|
|
3612
|
+
const verify = verifyReportChanges(ctx.resultReport.changed, worktree?.dir ?? cwd, t0);
|
|
3613
|
+
if (!verify.ok) {
|
|
3614
|
+
status.reportValid = false;
|
|
3615
|
+
const note = verifyFailNote(verify);
|
|
3616
|
+
status.last = shortText(note, 90);
|
|
3617
|
+
ctx.resultReport.notes = ctx.resultReport.notes ? `${ctx.resultReport.notes} — ${note}` : note;
|
|
3618
|
+
appendLedger(ledger, "REPORT-UNVERIFIED", {
|
|
3619
|
+
id: wid,
|
|
3620
|
+
failures: verify.failures.length,
|
|
3621
|
+
paths: verify.failures.map((f) => f.path).slice(0, 5).join(",")
|
|
3622
|
+
});
|
|
3623
|
+
}
|
|
3624
|
+
}
|
|
3380
3625
|
saveStatus(logDir, status);
|
|
3381
3626
|
appendLedger(ledger, "WORKER-END", {
|
|
3382
3627
|
id: wid,
|
|
@@ -3389,7 +3634,7 @@ async function executeRun(a) {
|
|
|
3389
3634
|
tools: status.tools,
|
|
3390
3635
|
label
|
|
3391
3636
|
});
|
|
3392
|
-
if (worktree) recordWorktree(logDir, status, worktree, ok);
|
|
3637
|
+
if (worktree) status = recordWorktree(logDir, status, worktree, ok);
|
|
3393
3638
|
if (headless && !a.quiet) printResult(parsed.outputFormat, resultEvent, rc, logDir, wid, ctx.resultReport, worktreeExtras(status));
|
|
3394
3639
|
const resultText = resultEvent?.result ?? "";
|
|
3395
3640
|
if (!ok && headless && a.target.via === "auto" && config.routing.retryOnQuota && status.turns <= 1 && status.tools === 0 && isQuotaFailure(resultText)) {
|
|
@@ -3508,8 +3753,8 @@ async function executeCodexRun(a) {
|
|
|
3508
3753
|
});
|
|
3509
3754
|
}
|
|
3510
3755
|
env.PAI_WORKER_ID = wid;
|
|
3511
|
-
const prompt = (worktree ? worktreeSystemPrompt(wid, worktree.branch, worktree.dir) + "\n\n" : "") + parsed.prompt;
|
|
3512
|
-
|
|
3756
|
+
const prompt = (worktree ? worktreeSystemPrompt(wid, worktree.branch, worktree.dir, worktree.snapshot) + "\n\n" : "") + parsed.prompt;
|
|
3757
|
+
let status = {
|
|
3513
3758
|
id: wid,
|
|
3514
3759
|
pid: process.pid,
|
|
3515
3760
|
label,
|
|
@@ -3538,7 +3783,8 @@ async function executeCodexRun(a) {
|
|
|
3538
3783
|
...worktree ? {
|
|
3539
3784
|
worktreeDir: worktree.dir,
|
|
3540
3785
|
branch: worktree.branch,
|
|
3541
|
-
worktreeBase: worktree.base
|
|
3786
|
+
worktreeBase: worktree.base,
|
|
3787
|
+
worktreeSnapshot: worktree.snapshot
|
|
3542
3788
|
} : {},
|
|
3543
3789
|
...a.specPath ? { spec: a.specPath } : {}
|
|
3544
3790
|
};
|
|
@@ -3648,6 +3894,20 @@ async function executeCodexRun(a) {
|
|
|
3648
3894
|
status.rc = rc;
|
|
3649
3895
|
status.secs = secs;
|
|
3650
3896
|
status.last = shortText(report?.notes ?? finalText, 90) || (ok ? "done" : "failed");
|
|
3897
|
+
if (report?.changed?.length) {
|
|
3898
|
+
const verify = verifyReportChanges(report.changed, worktree?.dir ?? cwd, t0);
|
|
3899
|
+
if (!verify.ok) {
|
|
3900
|
+
status.reportValid = false;
|
|
3901
|
+
const note = verifyFailNote(verify);
|
|
3902
|
+
status.last = shortText(note, 90);
|
|
3903
|
+
report.notes = report.notes ? `${report.notes} — ${note}` : note;
|
|
3904
|
+
appendLedger(ledger, "REPORT-UNVERIFIED", {
|
|
3905
|
+
id: wid,
|
|
3906
|
+
failures: verify.failures.length,
|
|
3907
|
+
paths: verify.failures.map((f) => f.path).slice(0, 5).join(",")
|
|
3908
|
+
});
|
|
3909
|
+
}
|
|
3910
|
+
}
|
|
3651
3911
|
saveStatus(logDir, status);
|
|
3652
3912
|
appendLedger(ledger, "WORKER-END", {
|
|
3653
3913
|
id: wid,
|
|
@@ -3661,7 +3921,7 @@ async function executeCodexRun(a) {
|
|
|
3661
3921
|
tools: status.tools,
|
|
3662
3922
|
label
|
|
3663
3923
|
});
|
|
3664
|
-
if (worktree) recordWorktree(logDir, status, worktree, ok);
|
|
3924
|
+
if (worktree) status = recordWorktree(logDir, status, worktree, ok);
|
|
3665
3925
|
if (!a.quiet) printResult(parsed.outputFormat, resultEvent, rc, logDir, wid, report, worktreeExtras(status));
|
|
3666
3926
|
const finalRc = rc !== 0 ? rc : ok ? 0 : 1;
|
|
3667
3927
|
if (status.parent && isWorkerId(logDir, status.parent)) try {
|
|
@@ -3814,5 +4074,5 @@ function resultFromOutput(out) {
|
|
|
3814
4074
|
}
|
|
3815
4075
|
|
|
3816
4076
|
//#endregion
|
|
3817
|
-
export { contextLabel as A,
|
|
3818
|
-
//# sourceMappingURL=run-
|
|
4077
|
+
export { contextLabel as A, saveStatus as B, mergeWorker as C, UNLABELED as D, ledgerSummary as E, loadStatus as F, shortText as G, waitForTerminalStatus as H, loadStatuses as I, describeMcp as K, newWorkerId as L, elapsedOf as M, isChatPane as N, ageOf as O, isLive as P, nowStamp as R, discardWorker as S, appendLedger as T, longInlinePromptHint as U, setWorkerLabel as V, parseRunnerArgs as W, itermUuid as _, projectLaunchConfig as a, sessionTag as b, handoffFromInside as c, workerDepth as d, checkPaneForWorker as f, itermForClaudeSession as g, currentTabKey as h, usageContextTokens as i, contextPercent as j, alive as k, readInbox as l, openPaneForWorker as m, runWorker as n, parseWorkerReport as o, openFollowPane as p, expandMcpNames as q, testProvider as r, renderReport as s, printResult as t, sayToWorker as u, resolveSession as v, worktreesDir as w, workerInScope as x, sessionMapPath as y, ownsPid as z };
|
|
4078
|
+
//# sourceMappingURL=run-CqRvXGjd.mjs.map
|