@delete101020/aidlc 4.0.27 → 4.0.29

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 (2) hide show
  1. package/dist/bundle.js +393 -36
  2. package/package.json +10 -11
package/dist/bundle.js CHANGED
@@ -19806,7 +19806,7 @@ var require_WorkspaceSchema = __commonJS({
19806
19806
  // invalidate every workspace.yaml already on disk and buy nothing
19807
19807
  // (MULTI_PROVIDER_ALIGNMENT.md P0/D1). A closed enum is what lets
19808
19808
  // `aidlc validate` reject a typo instead of failing at spawn time.
19809
- runner: zod_1.z.enum(["default", "custom", "codex", "gemini"]).default("default"),
19809
+ runner: zod_1.z.enum(["default", "custom", "codex", "gemini", "copilot"]).default("default"),
19810
19810
  /** Required when runner === 'custom'. Relative path to .js or .ts file. */
19811
19811
  runner_path: zod_1.z.string().optional(),
19812
19812
  /** Per-agent env overrides (layered over workspace.environment). */
@@ -19981,6 +19981,13 @@ var require_WorkspaceSchema = __commonJS({
19981
19981
  * pipelines, which are their own source.
19982
19982
  */
19983
19983
  derived_from: zod_1.z.string().min(1).optional(),
19984
+ /**
19985
+ * Set by {@link assemblePipeline} to the recipe that picked the steps. A
19986
+ * creation-time label only — `steps` stays the source of truth, and a hand
19987
+ * edit may leave the two apart. Needed because two recipes can select the
19988
+ * same steps, so the recipe cannot be recovered from the step list.
19989
+ */
19990
+ recipe: zod_1.z.string().min(1).optional(),
19984
19991
  steps: zod_1.z.array(PipelineStepSchema).min(1),
19985
19992
  on_failure: zod_1.z.enum(["stop", "continue"]).default("stop"),
19986
19993
  budget: PipelineBudgetSchema.optional()
@@ -20361,6 +20368,7 @@ var require_PipelineAssembler = __commonJS({
20361
20368
  exports2.PipelineAssembleError = void 0;
20362
20369
  exports2.assemblePipeline = assemblePipeline4;
20363
20370
  exports2.recipePipelineId = recipePipelineId4;
20371
+ exports2.pipelineRecipeLabel = pipelineRecipeLabel;
20364
20372
  var WorkspaceSchema_1 = require_WorkspaceSchema();
20365
20373
  var PipelineAssembleError4 = class extends Error {
20366
20374
  constructor(message) {
@@ -20448,6 +20456,7 @@ var require_PipelineAssembler = __commonJS({
20448
20456
  const assembled = {
20449
20457
  id: opts.pipelineId ?? recipe.id,
20450
20458
  derived_from: source.id,
20459
+ recipe: recipe.id,
20451
20460
  steps,
20452
20461
  on_failure: source.on_failure
20453
20462
  };
@@ -20478,6 +20487,20 @@ var require_PipelineAssembler = __commonJS({
20478
20487
  }
20479
20488
  }
20480
20489
  }
20490
+ function pipelineRecipeLabel(pipeline, recipes) {
20491
+ if (typeof pipeline.recipe !== "string" || !pipeline.recipe) {
20492
+ return void 0;
20493
+ }
20494
+ const id = pipeline.recipe;
20495
+ const recipe = recipes?.find((r) => r.id === id);
20496
+ if (!recipe || !Array.isArray(recipe.steps) || !Array.isArray(pipeline.steps)) {
20497
+ return { id, modified: false };
20498
+ }
20499
+ const own = pipeline.steps.map((s) => (0, WorkspaceSchema_1.stepDagId)(s));
20500
+ const listed = recipe.steps.map(String);
20501
+ const modified = own.length !== listed.length || own.some((s, i) => s !== listed[i]);
20502
+ return { id, modified };
20503
+ }
20481
20504
  function resolveSource(config, recipe) {
20482
20505
  if (recipe.from) {
20483
20506
  const found = config.pipelines.find((p) => p.id === recipe.from);
@@ -25980,7 +26003,7 @@ var require_EpicArtifactCommit = __commonJS({
25980
26003
  if (!fs14.existsSync(p) || !fs14.statSync(p).isFile()) {
25981
26004
  continue;
25982
26005
  }
25983
- const rel = path17.relative(repoRoot, p).split(path17.sep).join("/");
26006
+ const rel = path17.relative(repoRoot, fs14.realpathSync(p)).split(path17.sep).join("/");
25984
26007
  if (rel.startsWith("../")) {
25985
26008
  continue;
25986
26009
  }
@@ -27210,6 +27233,10 @@ var require_FollowUps = __commonJS({
27210
27233
  if (!source) {
27211
27234
  return typeof own.id === "string" && own.id ? { kind: "pipeline", id: own.id } : void 0;
27212
27235
  }
27236
+ const labelled = typeof own.recipe === "string" ? own.recipe : "";
27237
+ if (labelled && recipes.some((r) => r.id === labelled)) {
27238
+ return { kind: "recipe", id: labelled };
27239
+ }
27213
27240
  const steps = stepIds(own.steps).join("\n");
27214
27241
  const recipe = recipes.find((r) => (r.from === void 0 || r.from === source) && stepIds(r.steps).join("\n") === steps);
27215
27242
  if (recipe && typeof recipe.id === "string") {
@@ -28887,6 +28914,170 @@ ${task}
28887
28914
  }
28888
28915
  });
28889
28916
 
28917
+ // ../core/dist/runner/CopilotRunner.js
28918
+ var require_CopilotRunner = __commonJS({
28919
+ "../core/dist/runner/CopilotRunner.js"(exports2) {
28920
+ "use strict";
28921
+ Object.defineProperty(exports2, "__esModule", { value: true });
28922
+ exports2.CopilotRunner = void 0;
28923
+ exports2.copilotGraphServer = copilotGraphServer;
28924
+ exports2.copilotMcpConfig = copilotMcpConfig;
28925
+ var child_process_1 = require("child_process");
28926
+ var CodexRunner_1 = require_CodexRunner();
28927
+ var claudeHome_1 = require_claudeHome();
28928
+ var mcp_1 = require_mcp();
28929
+ var ndjson_1 = require_ndjson();
28930
+ var models_1 = require_models();
28931
+ var resolveCommand_1 = require_resolveCommand();
28932
+ var GRAPH_SERVERS2 = ["ast-graph", "codegraph"];
28933
+ var CopilotRunner2 = class {
28934
+ opts;
28935
+ /**
28936
+ * `projectInstructions` is `false` although Copilot reads a root `CLAUDE.md`
28937
+ * and `AGENTS.md` by itself: it does not read `.claude/CLAUDE.md`, and the
28938
+ * composer cannot know which layout a repo uses. Inlining costs a duplicate
28939
+ * when the file is at the root; not inlining would cost the conventions when
28940
+ * it is not. `CLAUDE.md` is preferred over `AGENTS.md` because a repo that
28941
+ * keeps both usually has tool-generated boilerplate in the latter.
28942
+ *
28943
+ * `astGraph` is `true` because the runner attaches the server on every run
28944
+ * that has one registered; `doctor` reports the workspaces that do not.
28945
+ */
28946
+ capabilities = {
28947
+ persona: false,
28948
+ projectInstructions: false,
28949
+ astGraph: true,
28950
+ instructionFile: "CLAUDE.md"
28951
+ };
28952
+ constructor(opts = {}) {
28953
+ this.opts = opts;
28954
+ }
28955
+ async run(ctx) {
28956
+ const bin = this.opts.copilotBin ?? "copilot";
28957
+ const model = (0, models_1.resolveProviderModel)("copilot", ctx.model, ctx.modelAliases);
28958
+ const graph = (this.opts.graphServer ?? copilotGraphServer)(ctx.workspaceRoot);
28959
+ const args = [
28960
+ // Required for non-interactive runs: without it every tool call waits for
28961
+ // a confirmation nobody is there to give.
28962
+ "--allow-all-tools",
28963
+ "--output-format",
28964
+ "json",
28965
+ "--no-color",
28966
+ ...this.opts.keepBuiltinMcps ? [] : ["--disable-builtin-mcps"],
28967
+ ...graph ? ["--additional-mcp-config", copilotMcpConfig(graph)] : [],
28968
+ ...model ? ["--model", model] : [],
28969
+ ...this.opts.extraArgs ?? []
28970
+ ];
28971
+ const cmd = (0, resolveCommand_1.resolveCommand)(bin);
28972
+ const proc = (0, child_process_1.spawn)(cmd.command, [...cmd.args, ...args], {
28973
+ cwd: ctx.workspaceRoot,
28974
+ env: { ...process.env, ...ctx.env },
28975
+ stdio: ["pipe", "pipe", "pipe"]
28976
+ });
28977
+ let streamed = "";
28978
+ let lastMessage = "";
28979
+ const deltaSeen = /* @__PURE__ */ new Set();
28980
+ let premiumRequests;
28981
+ const emit = (text) => {
28982
+ streamed += text;
28983
+ ctx.onOutput(text);
28984
+ };
28985
+ const handle = (evt) => {
28986
+ const d = evt.data ?? {};
28987
+ switch (evt.type) {
28988
+ case "assistant.message_delta":
28989
+ if (d.deltaContent) {
28990
+ if (d.messageId) {
28991
+ deltaSeen.add(d.messageId);
28992
+ }
28993
+ emit(d.deltaContent);
28994
+ }
28995
+ return;
28996
+ case "assistant.message":
28997
+ if (!d.content) {
28998
+ return;
28999
+ }
29000
+ lastMessage = d.content;
29001
+ if (!d.messageId || !deltaSeen.has(d.messageId)) {
29002
+ emit(d.content);
29003
+ }
29004
+ emit("\n");
29005
+ return;
29006
+ case "tool.execution_start":
29007
+ if (d.toolName) {
29008
+ ctx.onOutput(`[${d.toolTitle ?? d.toolName}]
29009
+ `);
29010
+ }
29011
+ return;
29012
+ case "session.mcp_server_status_changed":
29013
+ if (d.status === "failed") {
29014
+ ctx.onError(`MCP server ${d.serverName ?? "?"} failed to start: ${d.error ?? "unknown error"}
29015
+ `);
29016
+ }
29017
+ return;
29018
+ case "result":
29019
+ if (typeof evt.usage?.premiumRequests === "number") {
29020
+ premiumRequests = evt.usage.premiumRequests;
29021
+ }
29022
+ return;
29023
+ default:
29024
+ if (evt.type?.endsWith(".error")) {
29025
+ ctx.onError(`${d.message ?? d.error ?? "copilot reported an error"}
29026
+ `);
29027
+ }
29028
+ }
29029
+ };
29030
+ const sink = (0, ndjson_1.createJsonSink)(handle, (line) => ctx.onOutput(line + "\n"));
29031
+ proc.stdout.on("data", (d) => sink.push(d.toString("utf8")));
29032
+ proc.stderr.on("data", (d) => ctx.onError(d.toString("utf8")));
29033
+ proc.stdin.on("error", () => {
29034
+ });
29035
+ proc.stdin.end((0, CodexRunner_1.buildPrompt)(ctx));
29036
+ return new Promise((resolve5) => {
29037
+ proc.on("error", (err) => {
29038
+ ctx.onError(`Failed to spawn ${bin}: ${err.message}
29039
+ `);
29040
+ resolve5({ success: false, output: "" });
29041
+ });
29042
+ proc.on("close", (code) => {
29043
+ sink.flush();
29044
+ resolve5({
29045
+ success: code === 0,
29046
+ output: lastMessage || streamed,
29047
+ // No costUsd or usage: Copilot bills premium requests, and turning
29048
+ // those into dollars or tokens would be a guess (P0, D5).
29049
+ ...premiumRequests !== void 0 ? { data: { premiumRequests } } : {}
29050
+ });
29051
+ });
29052
+ });
29053
+ }
29054
+ };
29055
+ exports2.CopilotRunner = CopilotRunner2;
29056
+ function copilotGraphServer(workspaceRoot) {
29057
+ for (const name of GRAPH_SERVERS2) {
29058
+ const server = (0, mcp_1.readProjectMcpServer)(workspaceRoot, name, (0, claudeHome_1.claudeJsonPath)());
29059
+ if (server) {
29060
+ return server;
29061
+ }
29062
+ }
29063
+ return null;
29064
+ }
29065
+ function copilotMcpConfig(server) {
29066
+ return JSON.stringify({
29067
+ mcpServers: {
29068
+ [server.name]: {
29069
+ type: "local",
29070
+ command: server.command,
29071
+ args: server.args,
29072
+ ...server.env && Object.keys(server.env).length ? { env: server.env } : {},
29073
+ tools: ["*"]
29074
+ }
29075
+ }
29076
+ });
29077
+ }
29078
+ }
29079
+ });
29080
+
28890
29081
  // ../core/dist/runner/types.js
28891
29082
  var require_types = __commonJS({
28892
29083
  "../core/dist/runner/types.js"(exports2) {
@@ -29071,6 +29262,7 @@ var require_RunnerRegistry = __commonJS({
29071
29262
  var path17 = __importStar(require("path"));
29072
29263
  var DefaultRunner_1 = require_DefaultRunner();
29073
29264
  var CodexRunner_1 = require_CodexRunner();
29265
+ var CopilotRunner_1 = require_CopilotRunner();
29074
29266
  var CustomRunnerLoader_1 = require_CustomRunnerLoader();
29075
29267
  var RunnerRegistry = class {
29076
29268
  builtins = /* @__PURE__ */ new Map();
@@ -29080,6 +29272,7 @@ var require_RunnerRegistry = __commonJS({
29080
29272
  this.loader = new CustomRunnerLoader_1.CustomRunnerLoader(workspaceRoot);
29081
29273
  this.register("default", new DefaultRunner_1.DefaultRunner());
29082
29274
  this.register("codex", new CodexRunner_1.CodexRunner());
29275
+ this.register("copilot", new CopilotRunner_1.CopilotRunner());
29083
29276
  }
29084
29277
  /** Add or replace a builtin runner. */
29085
29278
  register(id, runner) {
@@ -30237,8 +30430,8 @@ var require_userConfig = __commonJS({
30237
30430
  "# Settings for this checkout only \u2014 NOT committed (see .gitignore).",
30238
30431
  "# epic_id_prefix is your own two letters, so the epics you open are filed",
30239
30432
  "# under you and never collide with a colleague's numbering.",
30240
- "# active_epic / pinned_epics / recent_epics are your own working set; the",
30241
- "# extension and `aidlc epic use|pin` keep them, and hand edits are fine.",
30433
+ "# active_epic / recent_epics / watched_epics / epic_sort are your own; the",
30434
+ "# extension and `aidlc epic use|watch` keep them, and hand edits are fine.",
30242
30435
  ""
30243
30436
  ].join("\n");
30244
30437
  function writeUserEpicIdPrefix(root, prefix) {
@@ -30285,7 +30478,7 @@ var require_userConfig = __commonJS({
30285
30478
  }
30286
30479
  const sep4 = existing === "" || existing.endsWith("\n") ? "" : "\n";
30287
30480
  fs_1.default.writeFileSync(file, `${existing}${sep4}
30288
- # Per-checkout AIDLC settings (epic_id_prefix, active/pinned epics) \u2014 never shared
30481
+ # Per-checkout AIDLC settings (epic_id_prefix, active/watched epics) \u2014 never shared
30289
30482
  ${exports2.USER_CONFIG_IGNORE_LINE}
30290
30483
  `, "utf8");
30291
30484
  return true;
@@ -30301,18 +30494,22 @@ var require_epicFocus = __commonJS({
30301
30494
  "../core/dist/loader/epicFocus.js"(exports2) {
30302
30495
  "use strict";
30303
30496
  Object.defineProperty(exports2, "__esModule", { value: true });
30304
- exports2.RECENT_EPICS_LIMIT = exports2.RECENT_EPICS_KEY = exports2.PINNED_EPICS_KEY = exports2.ACTIVE_EPIC_KEY = void 0;
30497
+ exports2.RECENT_EPICS_LIMIT = exports2.EPIC_SORT_KEY = exports2.WATCHED_EPICS_KEY = exports2.RECENT_EPICS_KEY = exports2.ACTIVE_EPIC_KEY = void 0;
30305
30498
  exports2.epicFocusFrom = epicFocusFrom;
30306
30499
  exports2.readEpicFocus = readEpicFocus2;
30307
30500
  exports2.pushRecent = pushRecent;
30308
30501
  exports2.recordEpicOpened = recordEpicOpened;
30309
30502
  exports2.setActiveEpic = setActiveEpic2;
30310
- exports2.setEpicPinned = setEpicPinned2;
30503
+ exports2.setEpicWatched = setEpicWatched2;
30504
+ exports2.epicSortFrom = epicSortFrom;
30505
+ exports2.readEpicSort = readEpicSort;
30506
+ exports2.setEpicSort = setEpicSort;
30311
30507
  exports2.epicIdFromBranch = epicIdFromBranch;
30312
30508
  var userConfig_1 = require_userConfig();
30313
30509
  exports2.ACTIVE_EPIC_KEY = "active_epic";
30314
- exports2.PINNED_EPICS_KEY = "pinned_epics";
30315
30510
  exports2.RECENT_EPICS_KEY = "recent_epics";
30511
+ exports2.WATCHED_EPICS_KEY = "watched_epics";
30512
+ exports2.EPIC_SORT_KEY = "epic_sort";
30316
30513
  exports2.RECENT_EPICS_LIMIT = 10;
30317
30514
  function asId(v) {
30318
30515
  return typeof v === "string" && v.trim() !== "" ? v.trim() : null;
@@ -30333,8 +30530,8 @@ var require_epicFocus = __commonJS({
30333
30530
  function epicFocusFrom(doc) {
30334
30531
  return {
30335
30532
  active: asId(doc?.[exports2.ACTIVE_EPIC_KEY]),
30336
- pinned: asIdList(doc?.[exports2.PINNED_EPICS_KEY]),
30337
- recent: asIdList(doc?.[exports2.RECENT_EPICS_KEY])
30533
+ recent: asIdList(doc?.[exports2.RECENT_EPICS_KEY]),
30534
+ watched: asIdList(doc?.[exports2.WATCHED_EPICS_KEY])
30338
30535
  };
30339
30536
  }
30340
30537
  function readEpicFocus2(root) {
@@ -30365,13 +30562,29 @@ var require_epicFocus = __commonJS({
30365
30562
  }
30366
30563
  });
30367
30564
  }
30368
- function setEpicPinned2(root, id, pinned) {
30565
+ function setEpicWatched2(root, id, watched) {
30369
30566
  (0, userConfig_1.updateUserConfig)(root, (doc) => {
30370
- const list = asIdList(doc[exports2.PINNED_EPICS_KEY]).filter((x) => x !== id);
30371
- if (pinned) {
30372
- list.push(id);
30567
+ const list = asIdList(doc[exports2.WATCHED_EPICS_KEY]);
30568
+ if (watched === list.includes(id)) {
30569
+ return;
30373
30570
  }
30374
- writeList(doc, exports2.PINNED_EPICS_KEY, list);
30571
+ writeList(doc, exports2.WATCHED_EPICS_KEY, watched ? [...list, id] : list.filter((x) => x !== id));
30572
+ });
30573
+ }
30574
+ function epicSortFrom(doc) {
30575
+ const v = doc?.[exports2.EPIC_SORT_KEY];
30576
+ if (!v || typeof v !== "object" || Array.isArray(v)) {
30577
+ return null;
30578
+ }
30579
+ const by = asId(v.by);
30580
+ return by ? { by, reversed: v.reversed === true } : null;
30581
+ }
30582
+ function readEpicSort(root) {
30583
+ return epicSortFrom((0, userConfig_1.readUserConfig)(root));
30584
+ }
30585
+ function setEpicSort(root, pref) {
30586
+ (0, userConfig_1.updateUserConfig)(root, (doc) => {
30587
+ doc[exports2.EPIC_SORT_KEY] = pref.reversed ? { by: pref.by, reversed: true } : { by: pref.by };
30375
30588
  });
30376
30589
  }
30377
30590
  function epicIdFromBranch(branch, knownIds) {
@@ -30758,6 +30971,98 @@ var require_budget = __commonJS({
30758
30971
  }
30759
30972
  });
30760
30973
 
30974
+ // ../core/dist/runs/producesSnapshot.js
30975
+ var require_producesSnapshot = __commonJS({
30976
+ "../core/dist/runs/producesSnapshot.js"(exports2) {
30977
+ "use strict";
30978
+ var __createBinding = exports2 && exports2.__createBinding || (Object.create ? function(o, m, k, k2) {
30979
+ if (k2 === void 0) k2 = k;
30980
+ var desc = Object.getOwnPropertyDescriptor(m, k);
30981
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
30982
+ desc = { enumerable: true, get: function() {
30983
+ return m[k];
30984
+ } };
30985
+ }
30986
+ Object.defineProperty(o, k2, desc);
30987
+ } : function(o, m, k, k2) {
30988
+ if (k2 === void 0) k2 = k;
30989
+ o[k2] = m[k];
30990
+ });
30991
+ var __setModuleDefault = exports2 && exports2.__setModuleDefault || (Object.create ? function(o, v) {
30992
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
30993
+ } : function(o, v) {
30994
+ o["default"] = v;
30995
+ });
30996
+ var __importStar = exports2 && exports2.__importStar || /* @__PURE__ */ function() {
30997
+ var ownKeys = function(o) {
30998
+ ownKeys = Object.getOwnPropertyNames || function(o2) {
30999
+ var ar = [];
31000
+ for (var k in o2) if (Object.prototype.hasOwnProperty.call(o2, k)) ar[ar.length] = k;
31001
+ return ar;
31002
+ };
31003
+ return ownKeys(o);
31004
+ };
31005
+ return function(mod) {
31006
+ if (mod && mod.__esModule) return mod;
31007
+ var result = {};
31008
+ if (mod != null) {
31009
+ for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31010
+ }
31011
+ __setModuleDefault(result, mod);
31012
+ return result;
31013
+ };
31014
+ }();
31015
+ Object.defineProperty(exports2, "__esModule", { value: true });
31016
+ exports2.snapshotProduces = snapshotProduces;
31017
+ exports2.unchangedProduces = unchangedProduces;
31018
+ var crypto_1 = require("crypto");
31019
+ var fs14 = __importStar(require("fs"));
31020
+ var path17 = __importStar(require("path"));
31021
+ var WorkspaceSchema_1 = require_WorkspaceSchema();
31022
+ var RunState_1 = require_RunState();
31023
+ function snapshotProduces(args) {
31024
+ const snap = /* @__PURE__ */ new Map();
31025
+ const stepCfg = args.pipeline.steps[args.stepIdx];
31026
+ if (!stepCfg) {
31027
+ return snap;
31028
+ }
31029
+ for (const p of (0, WorkspaceSchema_1.normalizeStep)(stepCfg).produces) {
31030
+ const rel = (0, RunState_1.resolvePath)(p, args.state.context);
31031
+ snap.set(rel, fingerprint(absolute(args.workspaceRoot, rel)));
31032
+ }
31033
+ return snap;
31034
+ }
31035
+ function unchangedProduces(before, workspaceRoot) {
31036
+ const stale = [];
31037
+ for (const [rel, prior] of before) {
31038
+ const now = fingerprint(absolute(workspaceRoot, rel));
31039
+ if (now === null) {
31040
+ continue;
31041
+ }
31042
+ if (prior === null || prior !== now) {
31043
+ return [];
31044
+ }
31045
+ stale.push(rel);
31046
+ }
31047
+ return stale;
31048
+ }
31049
+ function absolute(root, rel) {
31050
+ return path17.isAbsolute(rel) ? rel : path17.join(root, rel);
31051
+ }
31052
+ function fingerprint(abs) {
31053
+ try {
31054
+ const st = fs14.statSync(abs);
31055
+ if (!st.isFile()) {
31056
+ return `dir:${st.mtimeMs}`;
31057
+ }
31058
+ return (0, crypto_1.createHash)("sha1").update(fs14.readFileSync(abs)).digest("hex");
31059
+ } catch {
31060
+ return null;
31061
+ }
31062
+ }
31063
+ }
31064
+ });
31065
+
30761
31066
  // ../core/dist/runs/pricing.js
30762
31067
  var require_pricing = __commonJS({
30763
31068
  "../core/dist/runs/pricing.js"(exports2) {
@@ -30982,6 +31287,7 @@ var require_execEngine = __commonJS({
30982
31287
  var EpicScaffold_1 = require_EpicScaffold();
30983
31288
  var runProgress_1 = require_runProgress();
30984
31289
  var budget_1 = require_budget();
31290
+ var producesSnapshot_1 = require_producesSnapshot();
30985
31291
  var pricing_1 = require_pricing();
30986
31292
  var models_1 = require_models();
30987
31293
  var WorkspaceSchema_1 = require_WorkspaceSchema();
@@ -31207,6 +31513,7 @@ var require_execEngine = __commonJS({
31207
31513
  });
31208
31514
  const aliases = (0, pricing_1.providerAliases)(ws.config.providers, agent.runner);
31209
31515
  const resolvedModel = (0, models_1.resolveProviderModel)(agent.runner, agent.model, aliases);
31516
+ const producedBefore = (0, producesSnapshot_1.snapshotProduces)({ state, pipeline, workspaceRoot: root, stepIdx });
31210
31517
  const result = await runner.run({
31211
31518
  skill: skillText,
31212
31519
  env,
@@ -31222,6 +31529,15 @@ var require_execEngine = __commonJS({
31222
31529
  hooks.onStepFailed?.({ stepIdx, agent: agentId, message: `Step "${agentId}" failed (non-zero exit).` });
31223
31530
  return false;
31224
31531
  }
31532
+ const stale = (0, producesSnapshot_1.unchangedProduces)(producedBefore, root);
31533
+ if (stale.length > 0) {
31534
+ hooks.onStepFailed?.({
31535
+ stepIdx,
31536
+ agent: agentId,
31537
+ message: `Step "${agentId}" reported success but left its artifacts unchanged: ${stale.join(", ")}. The agent may have failed to write them. Check its output, then rerun the step.`
31538
+ });
31539
+ return false;
31540
+ }
31225
31541
  let next;
31226
31542
  let freshState;
31227
31543
  try {
@@ -33650,13 +33966,13 @@ var require_dist = __commonJS({
33650
33966
  "../core/dist/index.js"(exports2) {
33651
33967
  "use strict";
33652
33968
  Object.defineProperty(exports2, "__esModule", { value: true });
33653
- exports2.openIncidentEpic = exports2.SignalParseError = exports2.isSignal = exports2.parseSignal = exports2.SignalSchema = exports2.EpicStepEditError = exports2.resolveStepRef = exports2.describeGateEffect = exports2.commitEpicStepEdit = exports2.planSetEpicStepGates = exports2.planRemoveEpicStep = exports2.planAddEpicStep = exports2.EpicWorkflowSwitchError = exports2.canSwitchEpicWorkflow = exports2.epicWorkflowLock = exports2.applyEpicWorkflowSwitch = exports2.stageEpicWorkflowSwitch = exports2.planEpicWorkflowSwitch = exports2.EpicDescriptionError = exports2.setEpicDescription = exports2.lockedEpicDirError = exports2.EpicScaffoldError = exports2.epicsRoot = exports2.mapStepStatusToEpic = exports2.mirrorRunStateToEpic = exports2.scaffoldEpic = exports2.resolveArtifactCommitConfig = exports2.commitApprovedArtifacts = exports2.PipelineAdaptError = exports2.applyAdaptation = exports2.parseAdaptationVerdict = exports2.buildAdaptationPrompt = exports2.buildPhaseCatalog = exports2.slugEpicId = exports2.parseClassificationVerdict = exports2.buildClassificationPrompt = exports2.heuristicClassify = exports2.PipelineAssembleError = exports2.recipePipelineId = exports2.assemblePipeline = exports2.collectWorkspaceRefIssues = exports2.resolveStepSkills = exports2.stepSkillAlternatives = exports2.stepDagId = exports2.stepAgentId = exports2.producesEntries = exports2.normalizeStep = exports2.WorkspaceValidationError = exports2.validateWorkspace = exports2.WorkspaceSchema = void 0;
33654
- exports2.dropRecipesForPipeline = exports2.dropRecipeStep = exports2.recipesDrawingFrom = exports2.WORKSPACE_DIR = exports2.WORKSPACE_FILENAME = exports2.WorkspaceParseError = exports2.WorkspaceNotFoundError = exports2.WorkspaceLoader = exports2.renderPlanMarkdown = exports2.generatePlan = exports2.collectContext = exports2.followUpHookFailures = exports2.pendingFollowUpDone = exports2.applyFollowUpHookRun = exports2.trackFollowUpChildren = exports2.writeFollowUpHookLedger = exports2.readFollowUpHookLedger = exports2.followUpHookLedgerPath = exports2.runFollowUpHook = exports2.fillFollowUpHookCommand = exports2.resolveFollowUpHooks = exports2.epicPipelineId = exports2.FOLLOW_UP_HOOK_TIMEOUT_MS = exports2.FOLLOW_UP_HOOKS_LEDGER = exports2.stepProducesFollowUps = exports2.collectFollowUpHookIssues = exports2.FOLLOW_UP_HOOK_PLACEHOLDERS = exports2.FOLLOW_UP_HOOK_KEYS = exports2.FOLLOW_UP_INTENT = exports2.FOLLOW_UPS_FILE = exports2.MANUAL_FOLLOW_UP_KEY_PREFIX = exports2.followUpDefaults = exports2.nextManualFollowUpKey = exports2.withFollowUpProvenance = exports2.openManifestFollowUp = exports2.followUpChildId = exports2.followUpsOf = exports2.readEpicFollowUps = exports2.parseFollowUps = exports2.FollowUpsParseError = exports2.FollowUpManifestSchema = exports2.FollowUpItemSchema = exports2.SIGNAL_FILE = exports2.FOLLOW_UP_ARTIFACT = exports2.readEpicSignal = exports2.existingEpicIds = exports2.followUpIdFor = exports2.followUpEpicId = exports2.renderIntentMarkdown = exports2.openFollowUpEpic = void 0;
33655
- exports2.epicIdFromBranch = exports2.epicFocusFrom = exports2.RECENT_EPICS_LIMIT = exports2.RECENT_EPICS_KEY = exports2.PINNED_EPICS_KEY = exports2.ACTIVE_EPIC_KEY = exports2.writeUserEpicIdPrefix = exports2.userConfigPath = exports2.updateUserConfig = exports2.readUserConfig = exports2.readGitUserName = exports2.ensureUserConfigIgnored = exports2.USER_CONFIG_RELPATH = exports2.USER_CONFIG_IGNORE_LINE = exports2.suggestEpicId = exports2.resolveEpicIdPrefixChain = exports2.resolveEpicIdPrefix = exports2.epicIdDateStamp = exports2.deriveEpicIdPrefix = exports2.EPIC_ID_PREFIX_PATTERN = exports2.EPIC_ID_PREFIX_KEY = exports2.resolveArtifactLanguage = exports2.commandBodyPredatesArtifactLanguage = exports2.artifactLanguageSection = exports2.ARTIFACT_LANGUAGE_HEADING = exports2.stripPersonaDirectives = exports2.composeAgentPrompt = exports2.PROJECT_INSTRUCTION_FILES = exports2.findProjectInstructions = exports2.stripPersonaMetadata = exports2.PersonaLoader = exports2.SkillNotFoundError = exports2.SkillLoader = exports2.EnvVarMissingError = exports2.EnvResolver = exports2.epicPipelineReport = exports2.planEpicPipelineExtraction = exports2.epicOwningPipeline = exports2.unstageEpicPipeline = exports2.stageEpicPipeline = exports2.writeEpicPipelines = exports2.splitEpicPipelines = exports2.mergeEpicPipelines = exports2.epicPipelinePath = exports2.EPIC_PIPELINE_FILENAME = exports2.unusedAfterStepRemoval = exports2.skillReferences = exports2.agentReferences = exports2.renameSkillRefs = exports2.renameAgentRefs = void 0;
33656
- exports2.startRun = exports2.activateBackendFromWorkspace = exports2.activateRunStateBackend = exports2.resolveRunStateBackend = exports2.GitRunStateStore = exports2.RUN_ID_PATTERN = exports2.FileRunStateStore = exports2.RunStateStore = exports2.harnessCapabilities = exports2.NO_HARNESS_CAPABILITIES = exports2.RunnerValidationError = exports2.validateRunnerExport = exports2.CustomRunnerLoader = exports2.buildClaudeSpawnEnv = exports2.hasClaudeLogin = exports2.isInsideClaudeCodeSession = exports2.createJsonSink = exports2.createLineSink = exports2.isCodexMcpConfigured = exports2.codexConfigPath = exports2.readProjectMcpServer = exports2.mcpRegistrarFor = exports2.codexMcpRegistrar = exports2.claudeMcpRegistrar = exports2.CodexRunner = exports2.claudeModelArg = exports2.DefaultRunner = exports2.RunnerRegistry = exports2.targetPath = exports2.scopePaths = exports2.discoverAssets = exports2.commandBodyIsStale = exports2.readEpicTags = exports2.normalizeTags = exports2.normalizeTag = exports2.epicMatchesTags = exports2.applyTagEdit = exports2.MAX_TAG_LENGTH = exports2.EPIC_TAGS_KEY = exports2.strictModeSection = exports2.resolveEpicStrictMode = exports2.epicStrictMode = exports2.commandBodyPredatesStrictMode = exports2.STRICT_MODE_KEY = exports2.STRICT_MODE_HEADING = exports2.setEpicPinned = exports2.setActiveEpic = exports2.recordEpicOpened = exports2.readEpicFocus = exports2.pushRecent = void 0;
33657
- exports2.planRecipeMigration = exports2.getBuiltinRecipeSummaries = exports2.getAllBuiltinPipelineSummaries = exports2.getSdlcBuiltinPipelineSummary = exports2.getBuiltinPipelineSummary = exports2.getBuiltinWorkflowByPipelineId = exports2.getBuiltinWorkflow = exports2.workflowSlug = exports2.builtinTemplatesRoot = exports2.pipelineCommandId = exports2.PHASES = exports2.BUILTIN_WORKFLOWS = exports2.withBackfilledStepNames = exports2.describeDrift = exports2.reconcileRunSteps = exports2.RUN_STATE_SCHEMA_VERSION = exports2.migrateRunState = exports2.stepIdentity = exports2.resolvePath = exports2.AutoReviewerError = exports2.runAutoReview = exports2.renderRunReport = exports2.verifyRun = exports2.runExecLoop = exports2.estimateCostUsd = exports2.providerAliases = exports2.ratesFromConfig = exports2.mergeRates = exports2.BUILTIN_RATES = exports2.checkBudget = exports2.weighStepProgress = exports2.isActiveStatus = exports2.isStepOptional = exports2.isRunComplete = exports2.deriveRunProgress = exports2.PipelineRunError = exports2.retryAutoReview = exports2.submitAutoReviewVerdict = exports2.dirtyUpstreamOf = exports2.rerunApprovedStep = exports2.canRerunApprovedStep = exports2.chooseStepSkill = exports2.requestStepUpdate = exports2.rerunStep = exports2.rejectStep = exports2.approveStep = exports2.undoStepDone = exports2.canUndoStepDone = exports2.markStepDone = exports2.canStartStep = void 0;
33658
- exports2.ProfileSchema = exports2.TRACE_RULES = exports2.PROFILES_DIR = exports2.DEFAULT_PROFILE_ID = exports2.BUILTIN_PROFILE_IDS = exports2.setEpicMemoryHook = exports2.isEpicMemoryHookEnabled = exports2.installAnnotationTools = exports2.relativeEpicRoot = exports2.provisionDeclaredWorkflows = exports2.provisionWorkflowFiles = exports2.writeWorkflowArtifactTemplates = exports2.writeWorkflowCommands = exports2.provisionShortcutDocs = exports2.writeTwoLayerCommands = exports2.shortcutCommandDoc = exports2.backboneCommandDoc = exports2.unprovisionedPhases = exports2.nextEligiblePhase = exports2.resolveComposition = exports2.shortcutCommandId = exports2.getCanonicalPhase = exports2.isCanonicalPhase = exports2.BACKBONE_COMMAND_ID = exports2.CANONICAL_PHASE_IDS = exports2.CANONICAL_PHASES = exports2.renderTemplate = exports2.DEFAULT_GLOBAL_WORKFLOW_IDS = exports2.detectGlobalBuiltinSource = exports2.uninstallWorkflowGlobalsByIds = exports2.isWorkflowGloballyInstalled = exports2.installWorkflowGlobalsByIds = exports2.installGlobalDefaults = exports2.resolveProviderModel = exports2.isClaudeTierAlias = exports2.CLAUDE_TIER_ALIASES = exports2.FAST_MODEL = exports2.CODING_MODEL = exports2.PLANNING_MODEL = exports2.isBuiltinPreset = exports2.BUILTIN_PRESET_IDS = exports2.writeBuiltinAutoReviewValidators = exports2.resolvePrimaryStack = exports2.getSdlcArtifactTemplates = exports2.getBuiltinArtifactTemplates = exports2.phaseArtifactFileName = exports2.sdlcClaudeCommand = exports2.builtinClaudeCommand = exports2.loadAllBuiltinPresets = exports2.loadBuiltinPreset = void 0;
33659
- exports2.AIDLC_CORE_VERSION = exports2.AIDLC_CLI_GUIDE_TEXT = exports2.AIDLC_KNOWLEDGE = exports2.clearResolveCommandCache = exports2.resolveCommand = exports2.remapClaudePath = exports2.claudeConfigEnv = exports2.claudeJsonPath = exports2.isDefaultClaudeConfigDir = exports2.claudeConfigDir = exports2.resolveClaudeConfigDir = exports2.defaultClaudeConfigDir = exports2.getClaudeConfigDirOverride = exports2.setClaudeConfigDir = exports2.resolveDeclaredPath = exports2.expandHome = exports2.ProfileLoadError = exports2.UnknownStandardError = exports2.builtinProfiles = exports2.loadActiveProfile = exports2.loadProfile = exports2.listProfileManifests = exports2.resolveStandard = exports2.workspaceStandard = exports2.isBuiltinProfileId = void 0;
33969
+ exports2.SignalParseError = exports2.isSignal = exports2.parseSignal = exports2.SignalSchema = exports2.EpicStepEditError = exports2.resolveStepRef = exports2.describeGateEffect = exports2.commitEpicStepEdit = exports2.planSetEpicStepGates = exports2.planRemoveEpicStep = exports2.planAddEpicStep = exports2.EpicWorkflowSwitchError = exports2.canSwitchEpicWorkflow = exports2.epicWorkflowLock = exports2.applyEpicWorkflowSwitch = exports2.stageEpicWorkflowSwitch = exports2.planEpicWorkflowSwitch = exports2.EpicDescriptionError = exports2.setEpicDescription = exports2.lockedEpicDirError = exports2.EpicScaffoldError = exports2.epicsRoot = exports2.mapStepStatusToEpic = exports2.mirrorRunStateToEpic = exports2.scaffoldEpic = exports2.resolveArtifactCommitConfig = exports2.commitApprovedArtifacts = exports2.PipelineAdaptError = exports2.applyAdaptation = exports2.parseAdaptationVerdict = exports2.buildAdaptationPrompt = exports2.buildPhaseCatalog = exports2.slugEpicId = exports2.parseClassificationVerdict = exports2.buildClassificationPrompt = exports2.heuristicClassify = exports2.PipelineAssembleError = exports2.pipelineRecipeLabel = exports2.recipePipelineId = exports2.assemblePipeline = exports2.collectWorkspaceRefIssues = exports2.resolveStepSkills = exports2.stepSkillAlternatives = exports2.stepDagId = exports2.stepAgentId = exports2.producesEntries = exports2.normalizeStep = exports2.WorkspaceValidationError = exports2.validateWorkspace = exports2.WorkspaceSchema = void 0;
33970
+ exports2.dropRecipeStep = exports2.recipesDrawingFrom = exports2.WORKSPACE_DIR = exports2.WORKSPACE_FILENAME = exports2.WorkspaceParseError = exports2.WorkspaceNotFoundError = exports2.WorkspaceLoader = exports2.renderPlanMarkdown = exports2.generatePlan = exports2.collectContext = exports2.followUpHookFailures = exports2.pendingFollowUpDone = exports2.applyFollowUpHookRun = exports2.trackFollowUpChildren = exports2.writeFollowUpHookLedger = exports2.readFollowUpHookLedger = exports2.followUpHookLedgerPath = exports2.runFollowUpHook = exports2.fillFollowUpHookCommand = exports2.resolveFollowUpHooks = exports2.epicPipelineId = exports2.FOLLOW_UP_HOOK_TIMEOUT_MS = exports2.FOLLOW_UP_HOOKS_LEDGER = exports2.stepProducesFollowUps = exports2.collectFollowUpHookIssues = exports2.FOLLOW_UP_HOOK_PLACEHOLDERS = exports2.FOLLOW_UP_HOOK_KEYS = exports2.FOLLOW_UP_INTENT = exports2.FOLLOW_UPS_FILE = exports2.MANUAL_FOLLOW_UP_KEY_PREFIX = exports2.followUpDefaults = exports2.nextManualFollowUpKey = exports2.withFollowUpProvenance = exports2.openManifestFollowUp = exports2.followUpChildId = exports2.followUpsOf = exports2.readEpicFollowUps = exports2.parseFollowUps = exports2.FollowUpsParseError = exports2.FollowUpManifestSchema = exports2.FollowUpItemSchema = exports2.SIGNAL_FILE = exports2.FOLLOW_UP_ARTIFACT = exports2.readEpicSignal = exports2.existingEpicIds = exports2.followUpIdFor = exports2.followUpEpicId = exports2.renderIntentMarkdown = exports2.openFollowUpEpic = exports2.openIncidentEpic = void 0;
33971
+ exports2.WATCHED_EPICS_KEY = exports2.RECENT_EPICS_LIMIT = exports2.RECENT_EPICS_KEY = exports2.EPIC_SORT_KEY = exports2.ACTIVE_EPIC_KEY = exports2.writeUserEpicIdPrefix = exports2.userConfigPath = exports2.updateUserConfig = exports2.readUserConfig = exports2.readGitUserName = exports2.ensureUserConfigIgnored = exports2.USER_CONFIG_RELPATH = exports2.USER_CONFIG_IGNORE_LINE = exports2.suggestEpicId = exports2.resolveEpicIdPrefixChain = exports2.resolveEpicIdPrefix = exports2.epicIdDateStamp = exports2.deriveEpicIdPrefix = exports2.EPIC_ID_PREFIX_PATTERN = exports2.EPIC_ID_PREFIX_KEY = exports2.resolveArtifactLanguage = exports2.commandBodyPredatesArtifactLanguage = exports2.artifactLanguageSection = exports2.ARTIFACT_LANGUAGE_HEADING = exports2.stripPersonaDirectives = exports2.composeAgentPrompt = exports2.PROJECT_INSTRUCTION_FILES = exports2.findProjectInstructions = exports2.stripPersonaMetadata = exports2.PersonaLoader = exports2.SkillNotFoundError = exports2.SkillLoader = exports2.EnvVarMissingError = exports2.EnvResolver = exports2.epicPipelineReport = exports2.planEpicPipelineExtraction = exports2.epicOwningPipeline = exports2.unstageEpicPipeline = exports2.stageEpicPipeline = exports2.writeEpicPipelines = exports2.splitEpicPipelines = exports2.mergeEpicPipelines = exports2.epicPipelinePath = exports2.EPIC_PIPELINE_FILENAME = exports2.unusedAfterStepRemoval = exports2.skillReferences = exports2.agentReferences = exports2.renameSkillRefs = exports2.renameAgentRefs = exports2.dropRecipesForPipeline = void 0;
33972
+ exports2.harnessCapabilities = exports2.NO_HARNESS_CAPABILITIES = exports2.RunnerValidationError = exports2.validateRunnerExport = exports2.CustomRunnerLoader = exports2.buildClaudeSpawnEnv = exports2.hasClaudeLogin = exports2.isInsideClaudeCodeSession = exports2.createJsonSink = exports2.createLineSink = exports2.isCodexMcpConfigured = exports2.codexConfigPath = exports2.readProjectMcpServer = exports2.mcpRegistrarFor = exports2.codexMcpRegistrar = exports2.claudeMcpRegistrar = exports2.copilotMcpConfig = exports2.copilotGraphServer = exports2.CopilotRunner = exports2.CodexRunner = exports2.claudeModelArg = exports2.DefaultRunner = exports2.RunnerRegistry = exports2.targetPath = exports2.scopePaths = exports2.discoverAssets = exports2.commandBodyIsStale = exports2.readEpicTags = exports2.normalizeTags = exports2.normalizeTag = exports2.epicMatchesTags = exports2.applyTagEdit = exports2.MAX_TAG_LENGTH = exports2.EPIC_TAGS_KEY = exports2.strictModeSection = exports2.resolveEpicStrictMode = exports2.epicStrictMode = exports2.commandBodyPredatesStrictMode = exports2.STRICT_MODE_KEY = exports2.STRICT_MODE_HEADING = exports2.setEpicWatched = exports2.setEpicSort = exports2.setActiveEpic = exports2.recordEpicOpened = exports2.readEpicSort = exports2.readEpicFocus = exports2.pushRecent = exports2.epicSortFrom = exports2.epicIdFromBranch = exports2.epicFocusFrom = void 0;
33973
+ exports2.PHASES = exports2.BUILTIN_WORKFLOWS = exports2.withBackfilledStepNames = exports2.describeDrift = exports2.reconcileRunSteps = exports2.RUN_STATE_SCHEMA_VERSION = exports2.migrateRunState = exports2.stepIdentity = exports2.resolvePath = exports2.AutoReviewerError = exports2.runAutoReview = exports2.renderRunReport = exports2.verifyRun = exports2.runExecLoop = exports2.estimateCostUsd = exports2.providerAliases = exports2.ratesFromConfig = exports2.mergeRates = exports2.BUILTIN_RATES = exports2.unchangedProduces = exports2.snapshotProduces = exports2.checkBudget = exports2.weighStepProgress = exports2.isActiveStatus = exports2.isStepOptional = exports2.isRunComplete = exports2.deriveRunProgress = exports2.PipelineRunError = exports2.retryAutoReview = exports2.submitAutoReviewVerdict = exports2.dirtyUpstreamOf = exports2.rerunApprovedStep = exports2.canRerunApprovedStep = exports2.chooseStepSkill = exports2.requestStepUpdate = exports2.rerunStep = exports2.rejectStep = exports2.approveStep = exports2.undoStepDone = exports2.canUndoStepDone = exports2.markStepDone = exports2.canStartStep = exports2.startRun = exports2.activateBackendFromWorkspace = exports2.activateRunStateBackend = exports2.resolveRunStateBackend = exports2.GitRunStateStore = exports2.RUN_ID_PATTERN = exports2.FileRunStateStore = exports2.RunStateStore = void 0;
33974
+ exports2.provisionWorkflowFiles = exports2.writeWorkflowArtifactTemplates = exports2.writeWorkflowCommands = exports2.provisionShortcutDocs = exports2.writeTwoLayerCommands = exports2.shortcutCommandDoc = exports2.backboneCommandDoc = exports2.unprovisionedPhases = exports2.nextEligiblePhase = exports2.resolveComposition = exports2.shortcutCommandId = exports2.getCanonicalPhase = exports2.isCanonicalPhase = exports2.BACKBONE_COMMAND_ID = exports2.CANONICAL_PHASE_IDS = exports2.CANONICAL_PHASES = exports2.renderTemplate = exports2.DEFAULT_GLOBAL_WORKFLOW_IDS = exports2.detectGlobalBuiltinSource = exports2.uninstallWorkflowGlobalsByIds = exports2.isWorkflowGloballyInstalled = exports2.installWorkflowGlobalsByIds = exports2.installGlobalDefaults = exports2.resolveProviderModel = exports2.isClaudeTierAlias = exports2.CLAUDE_TIER_ALIASES = exports2.FAST_MODEL = exports2.CODING_MODEL = exports2.PLANNING_MODEL = exports2.isBuiltinPreset = exports2.BUILTIN_PRESET_IDS = exports2.writeBuiltinAutoReviewValidators = exports2.resolvePrimaryStack = exports2.getSdlcArtifactTemplates = exports2.getBuiltinArtifactTemplates = exports2.phaseArtifactFileName = exports2.sdlcClaudeCommand = exports2.builtinClaudeCommand = exports2.loadAllBuiltinPresets = exports2.loadBuiltinPreset = exports2.planRecipeMigration = exports2.getBuiltinRecipeSummaries = exports2.getAllBuiltinPipelineSummaries = exports2.getSdlcBuiltinPipelineSummary = exports2.getBuiltinPipelineSummary = exports2.getBuiltinWorkflowByPipelineId = exports2.getBuiltinWorkflow = exports2.workflowSlug = exports2.builtinTemplatesRoot = exports2.pipelineCommandId = void 0;
33975
+ exports2.AIDLC_CORE_VERSION = exports2.AIDLC_CLI_GUIDE_TEXT = exports2.AIDLC_KNOWLEDGE = exports2.clearResolveCommandCache = exports2.resolveCommand = exports2.remapClaudePath = exports2.claudeConfigEnv = exports2.claudeJsonPath = exports2.isDefaultClaudeConfigDir = exports2.claudeConfigDir = exports2.resolveClaudeConfigDir = exports2.defaultClaudeConfigDir = exports2.getClaudeConfigDirOverride = exports2.setClaudeConfigDir = exports2.resolveDeclaredPath = exports2.expandHome = exports2.ProfileLoadError = exports2.UnknownStandardError = exports2.builtinProfiles = exports2.loadActiveProfile = exports2.loadProfile = exports2.listProfileManifests = exports2.resolveStandard = exports2.workspaceStandard = exports2.isBuiltinProfileId = exports2.ProfileSchema = exports2.TRACE_RULES = exports2.PROFILES_DIR = exports2.DEFAULT_PROFILE_ID = exports2.BUILTIN_PROFILE_IDS = exports2.setEpicMemoryHook = exports2.isEpicMemoryHookEnabled = exports2.installAnnotationTools = exports2.relativeEpicRoot = exports2.provisionDeclaredWorkflows = void 0;
33660
33976
  var WorkspaceSchema_1 = require_WorkspaceSchema();
33661
33977
  Object.defineProperty(exports2, "WorkspaceSchema", { enumerable: true, get: function() {
33662
33978
  return WorkspaceSchema_1.WorkspaceSchema;
@@ -33695,6 +34011,9 @@ var require_dist = __commonJS({
33695
34011
  Object.defineProperty(exports2, "recipePipelineId", { enumerable: true, get: function() {
33696
34012
  return PipelineAssembler_1.recipePipelineId;
33697
34013
  } });
34014
+ Object.defineProperty(exports2, "pipelineRecipeLabel", { enumerable: true, get: function() {
34015
+ return PipelineAssembler_1.pipelineRecipeLabel;
34016
+ } });
33698
34017
  Object.defineProperty(exports2, "PipelineAssembleError", { enumerable: true, get: function() {
33699
34018
  return PipelineAssembler_1.PipelineAssembleError;
33700
34019
  } });
@@ -34121,8 +34440,8 @@ var require_dist = __commonJS({
34121
34440
  Object.defineProperty(exports2, "ACTIVE_EPIC_KEY", { enumerable: true, get: function() {
34122
34441
  return epicFocus_1.ACTIVE_EPIC_KEY;
34123
34442
  } });
34124
- Object.defineProperty(exports2, "PINNED_EPICS_KEY", { enumerable: true, get: function() {
34125
- return epicFocus_1.PINNED_EPICS_KEY;
34443
+ Object.defineProperty(exports2, "EPIC_SORT_KEY", { enumerable: true, get: function() {
34444
+ return epicFocus_1.EPIC_SORT_KEY;
34126
34445
  } });
34127
34446
  Object.defineProperty(exports2, "RECENT_EPICS_KEY", { enumerable: true, get: function() {
34128
34447
  return epicFocus_1.RECENT_EPICS_KEY;
@@ -34130,26 +34449,38 @@ var require_dist = __commonJS({
34130
34449
  Object.defineProperty(exports2, "RECENT_EPICS_LIMIT", { enumerable: true, get: function() {
34131
34450
  return epicFocus_1.RECENT_EPICS_LIMIT;
34132
34451
  } });
34452
+ Object.defineProperty(exports2, "WATCHED_EPICS_KEY", { enumerable: true, get: function() {
34453
+ return epicFocus_1.WATCHED_EPICS_KEY;
34454
+ } });
34133
34455
  Object.defineProperty(exports2, "epicFocusFrom", { enumerable: true, get: function() {
34134
34456
  return epicFocus_1.epicFocusFrom;
34135
34457
  } });
34136
34458
  Object.defineProperty(exports2, "epicIdFromBranch", { enumerable: true, get: function() {
34137
34459
  return epicFocus_1.epicIdFromBranch;
34138
34460
  } });
34461
+ Object.defineProperty(exports2, "epicSortFrom", { enumerable: true, get: function() {
34462
+ return epicFocus_1.epicSortFrom;
34463
+ } });
34139
34464
  Object.defineProperty(exports2, "pushRecent", { enumerable: true, get: function() {
34140
34465
  return epicFocus_1.pushRecent;
34141
34466
  } });
34142
34467
  Object.defineProperty(exports2, "readEpicFocus", { enumerable: true, get: function() {
34143
34468
  return epicFocus_1.readEpicFocus;
34144
34469
  } });
34470
+ Object.defineProperty(exports2, "readEpicSort", { enumerable: true, get: function() {
34471
+ return epicFocus_1.readEpicSort;
34472
+ } });
34145
34473
  Object.defineProperty(exports2, "recordEpicOpened", { enumerable: true, get: function() {
34146
34474
  return epicFocus_1.recordEpicOpened;
34147
34475
  } });
34148
34476
  Object.defineProperty(exports2, "setActiveEpic", { enumerable: true, get: function() {
34149
34477
  return epicFocus_1.setActiveEpic;
34150
34478
  } });
34151
- Object.defineProperty(exports2, "setEpicPinned", { enumerable: true, get: function() {
34152
- return epicFocus_1.setEpicPinned;
34479
+ Object.defineProperty(exports2, "setEpicSort", { enumerable: true, get: function() {
34480
+ return epicFocus_1.setEpicSort;
34481
+ } });
34482
+ Object.defineProperty(exports2, "setEpicWatched", { enumerable: true, get: function() {
34483
+ return epicFocus_1.setEpicWatched;
34153
34484
  } });
34154
34485
  var strictMode_1 = require_strictMode();
34155
34486
  Object.defineProperty(exports2, "STRICT_MODE_HEADING", { enumerable: true, get: function() {
@@ -34221,6 +34552,16 @@ var require_dist = __commonJS({
34221
34552
  Object.defineProperty(exports2, "CodexRunner", { enumerable: true, get: function() {
34222
34553
  return CodexRunner_1.CodexRunner;
34223
34554
  } });
34555
+ var CopilotRunner_1 = require_CopilotRunner();
34556
+ Object.defineProperty(exports2, "CopilotRunner", { enumerable: true, get: function() {
34557
+ return CopilotRunner_1.CopilotRunner;
34558
+ } });
34559
+ Object.defineProperty(exports2, "copilotGraphServer", { enumerable: true, get: function() {
34560
+ return CopilotRunner_1.copilotGraphServer;
34561
+ } });
34562
+ Object.defineProperty(exports2, "copilotMcpConfig", { enumerable: true, get: function() {
34563
+ return CopilotRunner_1.copilotMcpConfig;
34564
+ } });
34224
34565
  var mcp_1 = require_mcp();
34225
34566
  Object.defineProperty(exports2, "claudeMcpRegistrar", { enumerable: true, get: function() {
34226
34567
  return mcp_1.claudeMcpRegistrar;
@@ -34367,6 +34708,13 @@ var require_dist = __commonJS({
34367
34708
  Object.defineProperty(exports2, "checkBudget", { enumerable: true, get: function() {
34368
34709
  return budget_1.checkBudget;
34369
34710
  } });
34711
+ var producesSnapshot_1 = require_producesSnapshot();
34712
+ Object.defineProperty(exports2, "snapshotProduces", { enumerable: true, get: function() {
34713
+ return producesSnapshot_1.snapshotProduces;
34714
+ } });
34715
+ Object.defineProperty(exports2, "unchangedProduces", { enumerable: true, get: function() {
34716
+ return producesSnapshot_1.unchangedProduces;
34717
+ } });
34370
34718
  var pricing_1 = require_pricing();
34371
34719
  Object.defineProperty(exports2, "BUILTIN_RATES", { enumerable: true, get: function() {
34372
34720
  return pricing_1.BUILTIN_RATES;
@@ -43365,7 +43713,7 @@ var require_package = __commonJS({
43365
43713
  "package.json"(exports2, module2) {
43366
43714
  module2.exports = {
43367
43715
  name: "@delete101020/aidlc",
43368
- version: "4.0.27",
43716
+ version: "4.0.29",
43369
43717
  description: "AIDLC Native CLI, a fork of AIDLC \u2014 drive Claude through the six-stage AI-Native SDLC Playbook: Plan \u2192 Design \u2192 Build \u2192 Test \u2192 Deploy \u2192 Maintain, with artifact gates, requirements traceability, an incident loop back to Plan, and Spec Kit support.",
43370
43718
  license: "MIT",
43371
43719
  repository: {
@@ -46497,6 +46845,9 @@ function parityChecks(root, ws) {
46497
46845
  if (runner === "codex") {
46498
46846
  return new import_core5.CodexRunner().capabilities;
46499
46847
  }
46848
+ if (runner === "copilot") {
46849
+ return new import_core5.CopilotRunner().capabilities;
46850
+ }
46500
46851
  return import_core5.NO_HARNESS_CAPABILITIES;
46501
46852
  };
46502
46853
  const runners = [...new Set(ws.config.agents.map((a) => a.runner))];
@@ -46546,6 +46897,12 @@ function parityChecks(root, ws) {
46546
46897
  `${engine} via codex`,
46547
46898
  'not in ~/.codex/config.toml \u2014 run "aidlc mcp register --runner codex"'
46548
46899
  ));
46900
+ } else if (runner === "copilot") {
46901
+ const server = (0, import_core5.readProjectMcpServer)(root, engine, (0, import_core5.claudeJsonPath)());
46902
+ checks.push(server ? ok(`${engine} via copilot`, "attached to each run from this project's Claude registration") : warn(
46903
+ `${engine} via copilot`,
46904
+ 'no project registration to attach \u2014 run "AIDLC: Rescan AST Graph" in VS Code'
46905
+ ));
46549
46906
  } else {
46550
46907
  checks.push(warn(
46551
46908
  `${engine} via ${runner}`,
@@ -50386,7 +50743,7 @@ ${plan.length} pipeline(s) would move. Re-run without --dry-run.`));
50386
50743
  console.log(import_chalk15.default.dim(` Added ${import_core19.USER_CONFIG_IGNORE_LINE} to .gitignore \u2014 it is yours, not the team's.`));
50387
50744
  }
50388
50745
  };
50389
- cmd.command("current").description("Print the active epic id (from .aidlc/user.yaml); exits 1 when none is set").option("--json", "Print active, pinned and recent as JSON").action((opts, actionCmd) => {
50746
+ cmd.command("current").description("Print the active epic id (from .aidlc/user.yaml); exits 1 when none is set").option("--json", "Print active, recent and watched as JSON").action((opts, actionCmd) => {
50390
50747
  const root = resolveWorkspaceRoot(actionCmd);
50391
50748
  const focus = (0, import_core19.readEpicFocus)(root);
50392
50749
  if (opts.json) {
@@ -50414,18 +50771,18 @@ ${plan.length} pipeline(s) would move. Re-run without --dry-run.`));
50414
50771
  console.log(import_chalk15.default.green("\u2714") + ` Active epic: ${import_chalk15.default.bold(epicId)}`);
50415
50772
  noteIgnored(root);
50416
50773
  });
50417
- for (const [name, pinned] of [["pin", true], ["unpin", false]]) {
50418
- cmd.command(`${name} [id]`).description(pinned ? "Pin an epic to the top of the sidebar and Go to Epic picker; bare `pin` lists pins" : "Unpin an epic").action((id, _opts, actionCmd) => {
50774
+ for (const [name, watched] of [["watch", true], ["unwatch", false]]) {
50775
+ cmd.command(`${name} [id]`).description(watched ? "Watch an epic \u2014 listed under My epics in the sidebar; bare `watch` lists them" : "Stop watching an epic").action((id, _opts, actionCmd) => {
50419
50776
  const root = resolveWorkspaceRoot(actionCmd);
50420
50777
  if (!id) {
50421
- const list = (0, import_core19.readEpicFocus)(root).pinned;
50422
- console.log(list.length > 0 ? import_chalk15.default.cyan(list.join(" ")) : import_chalk15.default.dim("(nothing pinned)"));
50778
+ const list = (0, import_core19.readEpicFocus)(root).watched;
50779
+ console.log(list.length > 0 ? import_chalk15.default.cyan(list.join(" ")) : import_chalk15.default.dim("(nothing watched)"));
50423
50780
  return;
50424
50781
  }
50425
- const epicId = pinned ? requireKnownEpic(root, id) : id;
50426
- (0, import_core19.setEpicPinned)(root, epicId, pinned);
50427
- console.log(import_chalk15.default.green("\u2714") + ` ${pinned ? "Pinned" : "Unpinned"} ${import_chalk15.default.bold(epicId)}`);
50428
- if (pinned) {
50782
+ const epicId = watched ? requireKnownEpic(root, id) : id;
50783
+ (0, import_core19.setEpicWatched)(root, epicId, watched);
50784
+ console.log(import_chalk15.default.green("\u2714") + ` ${watched ? "Watching" : "Stopped watching"} ${import_chalk15.default.bold(epicId)}`);
50785
+ if (watched) {
50429
50786
  noteIgnored(root);
50430
50787
  }
50431
50788
  });
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@delete101020/aidlc",
3
- "version": "4.0.27",
3
+ "version": "4.0.29",
4
4
  "description": "AIDLC Native CLI, a fork of AIDLC — drive Claude through the six-stage AI-Native SDLC Playbook: Plan → Design → Build → Test → Deploy → Maintain, with artifact gates, requirements traceability, an incident loop back to Plan, and Spec Kit support.",
5
5
  "license": "MIT",
6
6
  "repository": {
@@ -36,19 +36,11 @@
36
36
  "README.md",
37
37
  "AUTOMATION.md"
38
38
  ],
39
- "scripts": {
40
- "compile": "tsc -p ./",
41
- "build": "tsc -p ./",
42
- "clean": "rm -rf dist",
43
- "bundle": "esbuild src/index.ts --bundle --platform=node --target=node18 --outfile=dist/bundle.js --external:fsevents && rm -rf dist/templates && cp -R ../core/templates dist/templates && rm -rf dist/tools dist/vendor dist/assets && cp -R ../../tools dist/tools && node -e \"require('fs').mkdirSync('dist/vendor', { recursive: true })\" && cp -R ../../vendor/annotron dist/vendor/annotron && cp -R ../extension/assets dist/assets",
44
- "prepublishOnly": "pnpm bundle"
45
- },
46
39
  "publishConfig": {
47
40
  "access": "public",
48
41
  "registry": "https://registry.npmjs.org/"
49
42
  },
50
43
  "devDependencies": {
51
- "@aidlc/core": "workspace:*",
52
44
  "@types/js-yaml": "^4.0.9",
53
45
  "@types/node": "^20.0.0",
54
46
  "chalk": "^4.1.2",
@@ -56,6 +48,13 @@
56
48
  "cli-table3": "^0.6.5",
57
49
  "commander": "^11.1.0",
58
50
  "esbuild": "^0.21.0",
59
- "js-yaml": "^4.1.1"
51
+ "js-yaml": "^4.1.1",
52
+ "@aidlc/core": "0.0.1"
53
+ },
54
+ "scripts": {
55
+ "compile": "tsc -p ./",
56
+ "build": "tsc -p ./",
57
+ "clean": "rm -rf dist",
58
+ "bundle": "esbuild src/index.ts --bundle --platform=node --target=node18 --outfile=dist/bundle.js --external:fsevents && rm -rf dist/templates && cp -R ../core/templates dist/templates && rm -rf dist/tools dist/vendor dist/assets && cp -R ../../tools dist/tools && node -e \"require('fs').mkdirSync('dist/vendor', { recursive: true })\" && cp -R ../../vendor/annotron dist/vendor/annotron && cp -R ../extension/assets dist/assets"
60
59
  }
61
- }
60
+ }