@staff0rd/assist 0.763.0 → 0.764.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/index.js CHANGED
@@ -6,7 +6,7 @@ import { Command } from "commander";
6
6
  // package.json
7
7
  var package_default = {
8
8
  name: "@staff0rd/assist",
9
- version: "0.763.0",
9
+ version: "0.764.0",
10
10
  type: "module",
11
11
  main: "dist/index.js",
12
12
  bin: {
@@ -1792,9 +1792,9 @@ var daemonPaths = {
1792
1792
 
1793
1793
  // src/commands/sessions/daemon/connectToDaemon.ts
1794
1794
  function connectToDaemon() {
1795
- return new Promise((resolve26, reject) => {
1795
+ return new Promise((resolve27, reject) => {
1796
1796
  const socket = net.connect(daemonPaths.socket);
1797
- socket.once("connect", () => resolve26(socket));
1797
+ socket.once("connect", () => resolve27(socket));
1798
1798
  socket.once("error", reject);
1799
1799
  });
1800
1800
  }
@@ -2112,7 +2112,7 @@ ${failed3.length} script(s) failed:`);
2112
2112
  }
2113
2113
  }
2114
2114
  function runEntry(entry) {
2115
- return new Promise((resolve26) => {
2115
+ return new Promise((resolve27) => {
2116
2116
  const startTime = Date.now();
2117
2117
  const child = spawnCommand(
2118
2118
  entry.fullCommand,
@@ -2124,7 +2124,7 @@ function runEntry(entry) {
2124
2124
  child.on("close", (code) => {
2125
2125
  const exitCode = code ?? 1;
2126
2126
  flushIfFailed(exitCode, chunks);
2127
- resolve26({
2127
+ resolve27({
2128
2128
  script: entry.name,
2129
2129
  code: exitCode,
2130
2130
  durationMs: Date.now() - startTime
@@ -2974,7 +2974,7 @@ function parsePreviewDecision(line, requestId) {
2974
2974
 
2975
2975
  // src/commands/sessions/shared/requestPreviewDecision.ts
2976
2976
  function requestPreviewDecision(request) {
2977
- return new Promise((resolve26, reject) => {
2977
+ return new Promise((resolve27, reject) => {
2978
2978
  connectToDaemon().then((socket) => {
2979
2979
  let settled = false;
2980
2980
  const finish2 = (error, decision) => {
@@ -2982,7 +2982,7 @@ function requestPreviewDecision(request) {
2982
2982
  settled = true;
2983
2983
  socket.destroy();
2984
2984
  if (error) reject(error);
2985
- else resolve26(decision);
2985
+ else resolve27(decision);
2986
2986
  };
2987
2987
  readSocketLines(socket, (line) => {
2988
2988
  const incoming = parsePreviewDecision(line, request.requestId);
@@ -7225,8 +7225,8 @@ function spawnInherit(command, args, options2 = {}) {
7225
7225
  env: { ...env, ...options2.env },
7226
7226
  cwd: options2.cwd
7227
7227
  });
7228
- const done2 = new Promise((resolve26, reject) => {
7229
- child.on("close", (code) => resolve26(code ?? 0));
7228
+ const done2 = new Promise((resolve27, reject) => {
7229
+ child.on("close", (code) => resolve27(code ?? 0));
7230
7230
  child.on("error", reject);
7231
7231
  });
7232
7232
  return { child, done: done2 };
@@ -7658,7 +7658,7 @@ Failed to launch Claude for ${context}: ${message3}`)
7658
7658
  // src/commands/sessions/daemon/sendToDaemon.ts
7659
7659
  var WRITE_TIMEOUT_MS = 500;
7660
7660
  function sendToDaemon(message3) {
7661
- return new Promise((resolve26, reject) => {
7661
+ return new Promise((resolve27, reject) => {
7662
7662
  connectToDaemon().then((socket) => {
7663
7663
  const timer = setTimeout(() => {
7664
7664
  socket.destroy();
@@ -7672,7 +7672,7 @@ function sendToDaemon(message3) {
7672
7672
  `, () => {
7673
7673
  clearTimeout(timer);
7674
7674
  socket.end();
7675
- resolve26();
7675
+ resolve27();
7676
7676
  });
7677
7677
  }, reject);
7678
7678
  });
@@ -7681,7 +7681,7 @@ function sendToDaemon(message3) {
7681
7681
  // src/commands/sessions/daemon/sendToDaemonAwaitAck.ts
7682
7682
  var ACK_TIMEOUT_MS = 1e3;
7683
7683
  function sendToDaemonAwaitAck(message3) {
7684
- return new Promise((resolve26, reject) => {
7684
+ return new Promise((resolve27, reject) => {
7685
7685
  connectToDaemon().then((socket) => {
7686
7686
  let settled = false;
7687
7687
  const finish2 = (error) => {
@@ -7690,7 +7690,7 @@ function sendToDaemonAwaitAck(message3) {
7690
7690
  clearTimeout(timer);
7691
7691
  socket.destroy();
7692
7692
  if (error) reject(error);
7693
- else resolve26();
7693
+ else resolve27();
7694
7694
  };
7695
7695
  const timer = setTimeout(
7696
7696
  () => finish2(new Error("timed out awaiting daemon ack")),
@@ -7781,7 +7781,7 @@ async function deliverReliably(sessionId, status2, payload) {
7781
7781
  }
7782
7782
  }
7783
7783
  function sleep(ms) {
7784
- return new Promise((resolve26) => setTimeout(resolve26, ms));
7784
+ return new Promise((resolve27) => setTimeout(resolve27, ms));
7785
7785
  }
7786
7786
  function describeError(error) {
7787
7787
  return error instanceof Error ? error.message : String(error);
@@ -8232,6 +8232,7 @@ var activitySchema = z7.object({
8232
8232
  phaseName: z7.string().optional(),
8233
8233
  totalPhases: z7.number().optional(),
8234
8234
  claudeSessionId: z7.string().optional(),
8235
+ watchState: z7.enum(["waiting", "updating"]).optional(),
8235
8236
  startedAt: z7.number()
8236
8237
  });
8237
8238
  function activityPath(sessionId) {
@@ -10756,7 +10757,7 @@ function spawnDaemon(reason4) {
10756
10757
  child.unref();
10757
10758
  }
10758
10759
  function delay(ms) {
10759
- return new Promise((resolve26) => setTimeout(resolve26, ms));
10760
+ return new Promise((resolve27) => setTimeout(resolve27, ms));
10760
10761
  }
10761
10762
 
10762
10763
  // src/commands/sessions/daemon/originForCwd.ts
@@ -10798,10 +10799,10 @@ function gitInvocation(cwd, args) {
10798
10799
  }
10799
10800
  function git(cwd, args) {
10800
10801
  const { file, argv, options: options2 } = gitInvocation(cwd, args);
10801
- return new Promise((resolve26, reject) => {
10802
+ return new Promise((resolve27, reject) => {
10802
10803
  execFile2(file, argv, options2, (error, stdout) => {
10803
10804
  if (error) reject(error);
10804
- else resolve26(stdout.toString());
10805
+ else resolve27(stdout.toString());
10805
10806
  });
10806
10807
  });
10807
10808
  }
@@ -11060,7 +11061,7 @@ var defaultDeps = {
11060
11061
  serve: async (args) => {
11061
11062
  await runTailscale(args);
11062
11063
  },
11063
- sleep: (ms) => new Promise((resolve26) => setTimeout(resolve26, ms)),
11064
+ sleep: (ms) => new Promise((resolve27) => setTimeout(resolve27, ms)),
11064
11065
  httpsPort: tailnetHttpsPort
11065
11066
  };
11066
11067
  async function ensureTailscaleServe(port, deps2 = {}) {
@@ -11467,12 +11468,12 @@ async function loadVisibleItems(req) {
11467
11468
 
11468
11469
  // src/commands/backlog/web/parseStatusBody.ts
11469
11470
  function readBody(req) {
11470
- return new Promise((resolve26, reject) => {
11471
+ return new Promise((resolve27, reject) => {
11471
11472
  let body = "";
11472
11473
  req.on("data", (chunk) => {
11473
11474
  body += chunk.toString();
11474
11475
  });
11475
- req.on("end", () => resolve26(body));
11476
+ req.on("end", () => resolve27(body));
11476
11477
  req.on("error", reject);
11477
11478
  });
11478
11479
  }
@@ -13581,11 +13582,11 @@ async function queryNodes() {
13581
13582
  } catch {
13582
13583
  return void 0;
13583
13584
  }
13584
- return new Promise((resolve26) => {
13585
+ return new Promise((resolve27) => {
13585
13586
  const finish2 = (result) => {
13586
13587
  clearTimeout(timer);
13587
13588
  socket.destroy();
13588
- resolve26(result);
13589
+ resolve27(result);
13589
13590
  };
13590
13591
  const timer = setTimeout(() => finish2(void 0), QUERY_TIMEOUT_MS);
13591
13592
  const lines2 = createInterface5({ input: socket });
@@ -15077,7 +15078,7 @@ function forwardToPeer(req, res, node, url) {
15077
15078
  const label2 = `link ${node} http: ${req.method} ${url.pathname} trace=${traceId}`;
15078
15079
  const log2 = (outcome) => console.log(`${label2} -> ${outcome} (${Date.now() - started}ms)`);
15079
15080
  const send = url.protocol === "https:" ? httpsRequest : httpRequest;
15080
- return new Promise((resolve26) => {
15081
+ return new Promise((resolve27) => {
15081
15082
  const upstream = send(
15082
15083
  url,
15083
15084
  {
@@ -15089,7 +15090,7 @@ function forwardToPeer(req, res, node, url) {
15089
15090
  [TRACE_HEADER]: traceId
15090
15091
  }
15091
15092
  },
15092
- (peer) => relayPeerResponse(peer, res, url.pathname, log2, resolve26)
15093
+ (peer) => relayPeerResponse(peer, res, url.pathname, log2, resolve27)
15093
15094
  );
15094
15095
  boundUpstream(upstream, res, peerTimeoutFor(url.pathname));
15095
15096
  upstream.on("error", (error) => {
@@ -15099,7 +15100,7 @@ function forwardToPeer(req, res, node, url) {
15099
15100
  respondJson(res, 502, {
15100
15101
  error: `${node} unreachable: ${error.message}`
15101
15102
  });
15102
- resolve26();
15103
+ resolve27();
15103
15104
  });
15104
15105
  req.pipe(upstream);
15105
15106
  });
@@ -15679,17 +15680,17 @@ async function stopDaemon() {
15679
15680
  }
15680
15681
  }
15681
15682
  function closedBeforeTimeout(socket) {
15682
- return new Promise((resolve26) => {
15683
+ return new Promise((resolve27) => {
15683
15684
  const timer = setTimeout(() => {
15684
15685
  socket.destroy();
15685
- resolve26(false);
15686
+ resolve27(false);
15686
15687
  }, STOP_TIMEOUT_MS);
15687
15688
  socket.resume();
15688
15689
  socket.on("error", () => {
15689
15690
  });
15690
15691
  socket.once("close", () => {
15691
15692
  clearTimeout(timer);
15692
- resolve26(true);
15693
+ resolve27(true);
15693
15694
  });
15694
15695
  });
15695
15696
  }
@@ -15747,8 +15748,8 @@ async function restartWeb(req, res, deps2 = {}) {
15747
15748
  return;
15748
15749
  }
15749
15750
  console.log(`restart ${target} ${linkedRequester(req)}`);
15750
- await new Promise((resolve26) => {
15751
- res.once("finish", resolve26);
15751
+ await new Promise((resolve27) => {
15752
+ res.once("finish", resolve27);
15752
15753
  respondJson(res, 200, { ok: true });
15753
15754
  });
15754
15755
  await performRestart(target, deps2);
@@ -15884,8 +15885,8 @@ async function selfUpdate(req, res, deps2 = {}) {
15884
15885
  return;
15885
15886
  }
15886
15887
  console.log("self-update: updated; restarting daemon and web server");
15887
- await new Promise((resolve26) => {
15888
- res.once("finish", resolve26);
15888
+ await new Promise((resolve27) => {
15889
+ res.once("finish", resolve27);
15889
15890
  respondJson(res, 200, { ok: true });
15890
15891
  });
15891
15892
  await performRestart("both", restartDeps);
@@ -15986,14 +15987,14 @@ function linkWebSocketUrl(url) {
15986
15987
  return target.toString();
15987
15988
  }
15988
15989
  function connectLinkWebSocket(url, handlers) {
15989
- return new Promise((resolve26, reject) => {
15990
+ return new Promise((resolve27, reject) => {
15990
15991
  const ws = new WebSocket(linkWebSocketUrl(url), {
15991
15992
  handshakeTimeout: HANDSHAKE_TIMEOUT_MS
15992
15993
  });
15993
15994
  let open = false;
15994
15995
  ws.on("open", () => {
15995
15996
  open = true;
15996
- resolve26({
15997
+ resolve27({
15997
15998
  send: (line) => {
15998
15999
  if (ws.readyState !== WebSocket.OPEN) return false;
15999
16000
  ws.send(line);
@@ -16019,8 +16020,8 @@ var HELLO_TIMEOUT_MS = 5e3;
16019
16020
  async function probePeerHello(url) {
16020
16021
  let settle = () => {
16021
16022
  };
16022
- const reply2 = new Promise((resolve26) => {
16023
- settle = resolve26;
16023
+ const reply2 = new Promise((resolve27) => {
16024
+ settle = resolve27;
16024
16025
  });
16025
16026
  const socket = await connectLinkWebSocket(url, {
16026
16027
  onLine: (line) => {
@@ -19059,12 +19060,12 @@ function hasSubcommands(helpText) {
19059
19060
  // src/commands/permitCliReads/runHelp.ts
19060
19061
  import { exec as exec2 } from "child_process";
19061
19062
  function runHelp(args) {
19062
- return new Promise((resolve26) => {
19063
+ return new Promise((resolve27) => {
19063
19064
  exec2(
19064
19065
  `${args.join(" ")} --help`,
19065
19066
  { encoding: "utf8", timeout: 3e4 },
19066
19067
  (_err, stdout, stderr) => {
19067
- resolve26(stdout || stderr || "");
19068
+ resolve27(stdout || stderr || "");
19068
19069
  }
19069
19070
  );
19070
19071
  });
@@ -19701,9 +19702,9 @@ function codexStatusFor(event, autoDecided) {
19701
19702
 
19702
19703
  // src/commands/codexHook/reportCodexStatus.ts
19703
19704
  async function reportCodexStatus(event, autoDecided) {
19704
- const report2 = codexStatusFor(event, autoDecided);
19705
- if (!report2) return;
19706
- await setSessionStatus(report2.status, { source: report2.source, ack: true });
19705
+ const report = codexStatusFor(event, autoDecided);
19706
+ if (!report) return;
19707
+ await setSessionStatus(report.status, { source: report.source, ack: true });
19707
19708
  }
19708
19709
 
19709
19710
  // src/commands/codexHook.ts
@@ -23578,8 +23579,8 @@ function printRepoAuthorBreakdown(repos2) {
23578
23579
  }
23579
23580
 
23580
23581
  // src/commands/github/printCommitsReport.ts
23581
- function printCommitsReport(report2) {
23582
- const { org, since, totalRepos, repos: repos2, committers, repoAuthors } = report2;
23582
+ function printCommitsReport(report) {
23583
+ const { org, since, totalRepos, repos: repos2, committers, repoAuthors } = report;
23583
23584
  const scope = repos2.length < totalRepos ? ` (top ${repos2.length} of ${totalRepos} repos)` : "";
23584
23585
  console.log(`Top repos by commits in ${org} since ${since}${scope}:
23585
23586
  `);
@@ -23608,7 +23609,7 @@ function commits(org, options2) {
23608
23609
  name: repo.name,
23609
23610
  authors: fetchRepoCommitAuthors(org, repo.name, since)
23610
23611
  }));
23611
- const report2 = {
23612
+ const report = {
23612
23613
  org,
23613
23614
  since: sinceDate,
23614
23615
  totalRepos: allRepos.length,
@@ -23617,11 +23618,11 @@ function commits(org, options2) {
23617
23618
  repoAuthors
23618
23619
  };
23619
23620
  if (options2.json) {
23620
- console.log(JSON.stringify(report2, null, 2));
23621
+ console.log(JSON.stringify(report, null, 2));
23621
23622
  } else if (repos2.length === 0) {
23622
23623
  console.log(`No commits found in ${org} since ${sinceDate}.`);
23623
23624
  } else {
23624
- printCommitsReport(report2);
23625
+ printCommitsReport(report);
23625
23626
  }
23626
23627
  }
23627
23628
 
@@ -25972,7 +25973,7 @@ function placedByDaemon() {
25972
25973
  function seed(worktreePath, clone) {
25973
25974
  console.log(`Preparing ${worktreePath}\u2026`);
25974
25975
  return new Promise(
25975
- (resolve26) => seedWorktree(worktreePath, clone, resolve26)
25976
+ (resolve27) => seedWorktree(worktreePath, clone, resolve27)
25976
25977
  );
25977
25978
  }
25978
25979
  async function moveToPrCheckoutTree() {
@@ -27149,25 +27150,25 @@ function isVisibleText(t) {
27149
27150
  return /[a-zA-Z]{3,}/.test(t);
27150
27151
  }
27151
27152
  var isHashtag = (t) => /^#[A-Za-z0-9_]+$/.test(t);
27152
- function collectRscText(v, resolve26, sink3, seen) {
27153
+ function collectRscText(v, resolve27, sink3, seen) {
27153
27154
  if (v == null) return;
27154
27155
  if (typeof v === "string") {
27155
27156
  if (isRscRef(v)) {
27156
27157
  if (!seen.has(v)) {
27157
27158
  seen.add(v);
27158
- collectRscText(resolve26(v), resolve26, sink3, seen);
27159
+ collectRscText(resolve27(v), resolve27, sink3, seen);
27159
27160
  }
27160
27161
  } else if (isHashtag(v)) sink3.hashtags.push(v);
27161
27162
  else if (isVisibleText(v)) sink3.text.push(v);
27162
27163
  return;
27163
27164
  }
27164
27165
  if (Array.isArray(v)) {
27165
- for (const x of v) collectRscText(x, resolve26, sink3, seen);
27166
+ for (const x of v) collectRscText(x, resolve27, sink3, seen);
27166
27167
  return;
27167
27168
  }
27168
27169
  if (typeof v === "object") {
27169
27170
  for (const val of Object.values(v)) {
27170
- collectRscText(val, resolve26, sink3, seen);
27171
+ collectRscText(val, resolve27, sink3, seen);
27171
27172
  }
27172
27173
  }
27173
27174
  }
@@ -27199,7 +27200,7 @@ function visitObjects(root2, fn) {
27199
27200
  }
27200
27201
  }
27201
27202
  }
27202
- function buildMentionMap(rows, resolve26) {
27203
+ function buildMentionMap(rows, resolve27) {
27203
27204
  const map = /* @__PURE__ */ new Map();
27204
27205
  visitObjects(rows, (o) => {
27205
27206
  const url = profileActionUrl(o);
@@ -27207,7 +27208,7 @@ function buildMentionMap(rows, resolve26) {
27207
27208
  const slug2 = slugFromProfileUrl(url);
27208
27209
  if (!slug2 || map.has(slug2)) return;
27209
27210
  const sink3 = { text: [], hashtags: [] };
27210
- collectRscText(o.children, resolve26, sink3, /* @__PURE__ */ new Set());
27211
+ collectRscText(o.children, resolve27, sink3, /* @__PURE__ */ new Set());
27211
27212
  const name = sink3.text.join(" ").replace(/\s+/g, " ").trim();
27212
27213
  map.set(slug2, name ? { slug: slug2, name, url } : { slug: slug2, url });
27213
27214
  });
@@ -27293,10 +27294,10 @@ function buildPost(raw, mentionMap, author) {
27293
27294
 
27294
27295
  // src/commands/netcap/walkPostRow.ts
27295
27296
  var isCommentary = (o) => asObject(o.viewTrackingSpecs)?.viewName === "feed-commentary";
27296
- function walkPostRow(v, resolve26, raw) {
27297
+ function walkPostRow(v, resolve27, raw) {
27297
27298
  if (v == null || typeof v !== "object") return;
27298
27299
  if (Array.isArray(v)) {
27299
- for (const x of v) walkPostRow(x, resolve26, raw);
27300
+ for (const x of v) walkPostRow(x, resolve27, raw);
27300
27301
  return;
27301
27302
  }
27302
27303
  const o = v;
@@ -27310,9 +27311,9 @@ function walkPostRow(v, resolve26, raw) {
27310
27311
  }
27311
27312
  if (isCommentary(o)) {
27312
27313
  const sink3 = { text: raw.text, hashtags: raw.hashtags };
27313
- collectRscText(o.children, resolve26, sink3, /* @__PURE__ */ new Set());
27314
+ collectRscText(o.children, resolve27, sink3, /* @__PURE__ */ new Set());
27314
27315
  }
27315
- for (const val of Object.values(o)) walkPostRow(val, resolve26, raw);
27316
+ for (const val of Object.values(o)) walkPostRow(val, resolve27, raw);
27316
27317
  }
27317
27318
 
27318
27319
  // src/commands/netcap/extractLinkedInPosts.ts
@@ -27326,8 +27327,8 @@ function findCommentaryRows(rows) {
27326
27327
  }
27327
27328
  function extractLinkedInPosts(flight, author = findAuthorSlug(flight)) {
27328
27329
  const rows = parseRscRows(flight);
27329
- const resolve26 = makeRscResolver(rows);
27330
- const mentionMap = buildMentionMap(rows, resolve26);
27330
+ const resolve27 = makeRscResolver(rows);
27331
+ const mentionMap = buildMentionMap(rows, resolve27);
27331
27332
  const posts = [];
27332
27333
  for (const id of findCommentaryRows(rows)) {
27333
27334
  const raw = {
@@ -27337,7 +27338,7 @@ function extractLinkedInPosts(flight, author = findAuthorSlug(flight)) {
27337
27338
  links: [],
27338
27339
  related: []
27339
27340
  };
27340
- walkPostRow(rows[id], resolve26, raw);
27341
+ walkPostRow(rows[id], resolve27, raw);
27341
27342
  const post = buildPost(raw, mentionMap, author);
27342
27343
  if (post) posts.push(post);
27343
27344
  }
@@ -28892,7 +28893,7 @@ function parseIncoming(line, type) {
28892
28893
  }
28893
28894
  }
28894
28895
  function requestSession(message3) {
28895
- return new Promise((resolve26, reject) => {
28896
+ return new Promise((resolve27, reject) => {
28896
28897
  connectToDaemon().then((socket) => {
28897
28898
  let settled = false;
28898
28899
  const finish2 = (error, sessionId) => {
@@ -28900,7 +28901,7 @@ function requestSession(message3) {
28900
28901
  settled = true;
28901
28902
  socket.destroy();
28902
28903
  if (error) reject(error);
28903
- else resolve26(sessionId);
28904
+ else resolve27(sessionId);
28904
28905
  };
28905
28906
  readSocketLines(socket, (line) => {
28906
28907
  const incoming = parseIncoming(line, message3.type);
@@ -29495,8 +29496,8 @@ function printPrStatus(pr) {
29495
29496
  }
29496
29497
 
29497
29498
  // src/commands/prs/status/printPrsStatus.ts
29498
- function printPrsStatus(report2) {
29499
- for (const repo of report2.repos) {
29499
+ function printPrsStatus(report) {
29500
+ for (const repo of report.repos) {
29500
29501
  const count8 = repo.pullRequests.length;
29501
29502
  console.log(`${chalk185.bold(repo.repo)} ${chalk185.dim(`(${count8} open)`)}`);
29502
29503
  for (const pr of repo.pullRequests) {
@@ -29505,9 +29506,9 @@ function printPrsStatus(report2) {
29505
29506
  if (count8 === 0) console.log(chalk185.dim(" no open pull requests"));
29506
29507
  console.log();
29507
29508
  }
29508
- if (report2.errors.length === 0) return;
29509
+ if (report.errors.length === 0) return;
29509
29510
  console.log(chalk185.bold("Errors"));
29510
- for (const failure of report2.errors) {
29511
+ for (const failure of report.errors) {
29511
29512
  console.log(` ${chalk185.red(failure.repo)}: ${failure.error}`);
29512
29513
  }
29513
29514
  console.log();
@@ -29515,12 +29516,12 @@ function printPrsStatus(report2) {
29515
29516
 
29516
29517
  // src/commands/prs/prsStatus.ts
29517
29518
  function prsStatus(repos2, options2) {
29518
- const report2 = buildPrsStatusReport(repos2);
29519
+ const report = buildPrsStatusReport(repos2);
29519
29520
  if (options2.json) {
29520
- console.log(JSON.stringify(report2, null, 2));
29521
+ console.log(JSON.stringify(report, null, 2));
29521
29522
  return;
29522
29523
  }
29523
- printPrsStatus(report2);
29524
+ printPrsStatus(report);
29524
29525
  }
29525
29526
 
29526
29527
  // src/commands/registerPrsStatus.ts
@@ -31354,7 +31355,7 @@ function getViolations(pattern2, options2 = {}, maxLines = DEFAULT_MAX_LINES2) {
31354
31355
 
31355
31356
  // src/commands/refactor/check.ts
31356
31357
  function runScript(script, cwd) {
31357
- return new Promise((resolve26) => {
31358
+ return new Promise((resolve27) => {
31358
31359
  const child = spawn7("npm", ["run", script], {
31359
31360
  stdio: "pipe",
31360
31361
  shell: true,
@@ -31368,7 +31369,7 @@ function runScript(script, cwd) {
31368
31369
  output += data.toString();
31369
31370
  });
31370
31371
  child.on("close", (code) => {
31371
- resolve26({ script, code: code ?? 1, output });
31372
+ resolve27({ script, code: code ?? 1, output });
31372
31373
  });
31373
31374
  });
31374
31375
  }
@@ -35676,12 +35677,12 @@ function onCloseResult(ctx, code) {
35676
35677
  return { ...closed, stderr: ctx.stderr.value, stdout: ctx.stdout.value };
35677
35678
  }
35678
35679
  function waitForChildExit(ctx) {
35679
- return new Promise((resolve26) => {
35680
+ return new Promise((resolve27) => {
35680
35681
  let settled = false;
35681
35682
  const settle = (result) => {
35682
35683
  if (settled) return;
35683
35684
  settled = true;
35684
- resolve26(result);
35685
+ resolve27(result);
35685
35686
  };
35686
35687
  ctx.child.on("error", (err) => settle(onErrorResult(ctx, err)));
35687
35688
  ctx.child.on("close", (code) => settle(onCloseResult(ctx, code)));
@@ -37053,11 +37054,11 @@ import { randomUUID as randomUUID20 } from "crypto";
37053
37054
  // src/commands/sessions/shared/sendShowPreview.ts
37054
37055
  async function sendShowPreview(request) {
37055
37056
  const socket = await connectToDaemon();
37056
- await new Promise((resolve26, reject) => {
37057
+ await new Promise((resolve27, reject) => {
37057
37058
  const finish2 = (error) => {
37058
37059
  socket.destroy();
37059
37060
  if (error) reject(error);
37060
- else resolve26();
37061
+ else resolve27();
37061
37062
  };
37062
37063
  readSocketLines(socket, (line) => {
37063
37064
  const reply2 = parseReply(line);
@@ -38320,9 +38321,9 @@ function createReadlineInterface() {
38320
38321
  });
38321
38322
  }
38322
38323
  function askQuestion(rl, question) {
38323
- return new Promise((resolve26) => {
38324
+ return new Promise((resolve27) => {
38324
38325
  rl.question(question, (answer) => {
38325
- resolve26(answer.trim());
38326
+ resolve27(answer.trim());
38326
38327
  });
38327
38328
  });
38328
38329
  }
@@ -39464,47 +39465,18 @@ function registerVerify(program2) {
39464
39465
  configHelp(verifyCommand, verifyConfigHelp);
39465
39466
  }
39466
39467
 
39467
- // src/commands/watch/decideLap.ts
39468
- var RELAUNCH_CODES = /* @__PURE__ */ new Set([0, 2, 4]);
39469
- function decideLap(end, interrupted) {
39470
- if (interrupted) return { kind: "exit", code: 130 };
39471
- if (end.code === null) return { kind: "relaunch" };
39472
- if (RELAUNCH_CODES.has(end.code)) return { kind: "relaunch" };
39473
- return { kind: "exit", code: end.code };
39474
- }
39475
-
39476
- // src/commands/watch/runWatchLap.ts
39477
- import { spawn as spawn9 } from "child_process";
39478
- var WATCH_LAP_ARGS = ["watch", "wait", "--pull", "--build"];
39479
- function runWatchLap() {
39480
- return new Promise((resolve26, reject) => {
39481
- const assistFromPath = spawn9("assist", WATCH_LAP_ARGS, {
39482
- stdio: "inherit",
39483
- shell: process.platform === "win32"
39484
- });
39485
- assistFromPath.on("close", (code, signal) => resolve26({ code, signal }));
39486
- assistFromPath.on("error", reject);
39487
- });
39488
- }
39468
+ // src/commands/watch/simulateDivergence.ts
39469
+ import { writeFileSync as writeFileSync52 } from "fs";
39489
39470
 
39490
- // src/commands/watch/watchLoop.ts
39491
- async function watchLoop() {
39492
- let interrupted = false;
39493
- const recordInterruptAndLetLapFinish = () => {
39494
- interrupted = true;
39495
- };
39496
- process.on("SIGINT", recordInterruptAndLetLapFinish);
39497
- for (let lap = 1; ; lap++) {
39498
- console.log(`lap ${lap}: assist ${WATCH_LAP_ARGS.join(" ")}`);
39499
- const end = await runWatchLap();
39500
- const decision = decideLap(end, interrupted);
39501
- const how = end.signal ? `killed by ${end.signal}` : `exited ${end.code}`;
39502
- if (decision.kind === "exit") {
39503
- console.error(`lap ${lap} ${how} \u2014 stopping`);
39504
- return process.exit(decision.code);
39505
- }
39506
- console.log(`lap ${lap} ${how} \u2014 relaunching`);
39471
+ // src/commands/watch/gitFailureReason.ts
39472
+ function gitFailureReason(error) {
39473
+ const streams = error;
39474
+ for (const stream of [streams?.stderr, streams?.stdout]) {
39475
+ const text17 = stream == null ? "" : String(stream).trim();
39476
+ if (text17) return text17;
39507
39477
  }
39478
+ const message3 = error instanceof Error ? error.message : String(error);
39479
+ return message3.trim() || "git failed without reporting a reason";
39508
39480
  }
39509
39481
 
39510
39482
  // src/commands/watch/resolveUpstream.ts
@@ -39547,6 +39519,71 @@ function resolveUpstream(cwd) {
39547
39519
  }
39548
39520
  }
39549
39521
 
39522
+ // src/commands/watch/simulatedDivergencePath.ts
39523
+ import { resolve as resolve24 } from "path";
39524
+ function simulatedDivergencePath(cwd) {
39525
+ return resolve24(
39526
+ cwd ?? process.cwd(),
39527
+ runGit3(["rev-parse", "--git-path", "assist-simulate-divergence"], cwd)
39528
+ );
39529
+ }
39530
+
39531
+ // src/commands/watch/simulateDivergence.ts
39532
+ function simulateDivergence() {
39533
+ try {
39534
+ writeFileSync52(simulatedDivergencePath(), "");
39535
+ console.log(
39536
+ `the next assist watch wait poll in ${runGit3(["rev-parse", "--show-toplevel"])} will exit 3 as a simulated divergence`
39537
+ );
39538
+ } catch (error) {
39539
+ console.error(`cannot simulate a divergence: ${gitFailureReason(error)}`);
39540
+ process.exit(1);
39541
+ }
39542
+ }
39543
+
39544
+ // src/commands/watch/decideLap.ts
39545
+ var RELAUNCH_CODES = /* @__PURE__ */ new Set([0, 2, 4]);
39546
+ function decideLap(end, interrupted) {
39547
+ if (interrupted) return { kind: "exit", code: 130 };
39548
+ if (end.code === null) return { kind: "relaunch" };
39549
+ if (RELAUNCH_CODES.has(end.code)) return { kind: "relaunch" };
39550
+ return { kind: "exit", code: end.code };
39551
+ }
39552
+
39553
+ // src/commands/watch/runWatchLap.ts
39554
+ import { spawn as spawn9 } from "child_process";
39555
+ var WATCH_LAP_ARGS = ["watch", "wait", "--pull", "--build"];
39556
+ function runWatchLap() {
39557
+ return new Promise((resolve27, reject) => {
39558
+ const assistFromPath = spawn9("assist", WATCH_LAP_ARGS, {
39559
+ stdio: "inherit",
39560
+ shell: process.platform === "win32"
39561
+ });
39562
+ assistFromPath.on("close", (code, signal) => resolve27({ code, signal }));
39563
+ assistFromPath.on("error", reject);
39564
+ });
39565
+ }
39566
+
39567
+ // src/commands/watch/watchLoop.ts
39568
+ async function watchLoop() {
39569
+ let interrupted = false;
39570
+ const recordInterruptAndLetLapFinish = () => {
39571
+ interrupted = true;
39572
+ };
39573
+ process.on("SIGINT", recordInterruptAndLetLapFinish);
39574
+ for (let lap = 1; ; lap++) {
39575
+ console.log(`lap ${lap}: assist ${WATCH_LAP_ARGS.join(" ")}`);
39576
+ const end = await runWatchLap();
39577
+ const decision = decideLap(end, interrupted);
39578
+ const how = end.signal ? `killed by ${end.signal}` : `exited ${end.code}`;
39579
+ if (decision.kind === "exit") {
39580
+ console.error(`lap ${lap} ${how} \u2014 stopping`);
39581
+ return process.exit(decision.code);
39582
+ }
39583
+ console.log(`lap ${lap} ${how} \u2014 relaunching`);
39584
+ }
39585
+ }
39586
+
39550
39587
  // src/commands/watch/changedPaths.ts
39551
39588
  function changedPaths(from, cwd) {
39552
39589
  return runGit3(["diff", "--name-only", `${from}..HEAD`], cwd).split("\n").filter((line) => line.length > 0);
@@ -39670,17 +39707,6 @@ function buildWatchReport(from, cwd) {
39670
39707
  });
39671
39708
  }
39672
39709
 
39673
- // src/commands/watch/gitFailureReason.ts
39674
- function gitFailureReason(error) {
39675
- const streams = error;
39676
- for (const stream of [streams?.stderr, streams?.stdout]) {
39677
- const text17 = stream == null ? "" : String(stream).trim();
39678
- if (text17) return text17;
39679
- }
39680
- const message3 = error instanceof Error ? error.message : String(error);
39681
- return message3.trim() || "git failed without reporting a reason";
39682
- }
39683
-
39684
39710
  // src/commands/watch/watchReport.ts
39685
39711
  function watchReport(options2) {
39686
39712
  try {
@@ -39705,6 +39731,11 @@ function describeOutcome(outcome) {
39705
39731
  exitCode: 2,
39706
39732
  message: `no movement on ${outcome.upstream} after ${outcome.timeout}`
39707
39733
  };
39734
+ case "simulated-divergence":
39735
+ return {
39736
+ exitCode: 3,
39737
+ message: `simulated divergence from ${outcome.upstream} (requested by assist watch simulate-divergence; nothing has actually diverged)`
39738
+ };
39708
39739
  case "unavailable":
39709
39740
  return { exitCode: 1, message: `cannot wait: ${outcome.reason}` };
39710
39741
  case "interrupted":
@@ -39712,19 +39743,9 @@ function describeOutcome(outcome) {
39712
39743
  }
39713
39744
  }
39714
39745
 
39715
- // src/commands/watch/describePull.ts
39716
- function describePull(result) {
39717
- if (result.kind === "fast-forwarded") {
39718
- return {
39719
- exitCode: 0,
39720
- message: `pulled --ff-only \u2192 ${result.sha.slice(0, 7)}`
39721
- };
39722
- }
39723
- return {
39724
- exitCode: 3,
39725
- message: `pull was not a fast-forward:
39726
- ${result.reason}`
39727
- };
39746
+ // src/commands/watch/emitWatchState.ts
39747
+ function emitWatchState(watchState) {
39748
+ emitActivity({ kind: "command", name: "watch", watchState });
39728
39749
  }
39729
39750
 
39730
39751
  // src/commands/watch/parseDuration.ts
@@ -39759,6 +39780,21 @@ function parseWatchDurations(interval, timeout) {
39759
39780
  };
39760
39781
  }
39761
39782
 
39783
+ // src/commands/watch/describePull.ts
39784
+ function describePull(result) {
39785
+ if (result.kind === "fast-forwarded") {
39786
+ return {
39787
+ exitCode: 0,
39788
+ message: `pulled --ff-only \u2192 ${result.sha.slice(0, 7)}`
39789
+ };
39790
+ }
39791
+ return {
39792
+ exitCode: 3,
39793
+ message: `pull was not a fast-forward:
39794
+ ${result.reason}`
39795
+ };
39796
+ }
39797
+
39762
39798
  // src/commands/watch/pullFastForward.ts
39763
39799
  var STASH_MESSAGE = "assist watch";
39764
39800
  function attemptGit(args, cwd) {
@@ -39891,7 +39927,7 @@ function resolveParams(params, cliArgs) {
39891
39927
 
39892
39928
  // src/commands/run/resolveRunCwd.ts
39893
39929
  import { existsSync as existsSync80 } from "fs";
39894
- import { resolve as resolve24 } from "path";
39930
+ import { resolve as resolve25 } from "path";
39895
39931
  var MissingRunCwdError = class extends Error {
39896
39932
  constructor(runName, cwd) {
39897
39933
  super(`run config "${runName}": cwd ${cwd} does not exist`);
@@ -39902,7 +39938,7 @@ var MissingRunCwdError = class extends Error {
39902
39938
  };
39903
39939
  function resolveRunCwd(config, baseDir = runConfigBaseDir()) {
39904
39940
  if (!config.cwd) return void 0;
39905
- const cwd = resolve24(baseDir, config.cwd);
39941
+ const cwd = resolve25(baseDir, config.cwd);
39906
39942
  if (!existsSync80(cwd)) throw new MissingRunCwdError(config.name, cwd);
39907
39943
  return cwd;
39908
39944
  }
@@ -39971,6 +40007,12 @@ async function reportBuildOrExit(entry) {
39971
40007
  process.exit(4);
39972
40008
  }
39973
40009
 
40010
+ // src/commands/watch/reportOutcome.ts
40011
+ function reportOutcome({ exitCode, message: message3 }) {
40012
+ if (exitCode === 0) console.log(message3);
40013
+ else console.error(message3);
40014
+ }
40015
+
39974
40016
  // src/commands/watch/runPostBuildSync.ts
39975
40017
  async function runPostBuildSync() {
39976
40018
  return toBuildOutcome(
@@ -39996,6 +40038,39 @@ async function reportSyncOrExit() {
39996
40038
  process.exit(4);
39997
40039
  }
39998
40040
 
40041
+ // src/commands/watch/pullAndBuild.ts
40042
+ var DEFAULT_BUILD_ENTRY = "auto-build";
40043
+ async function pullAndBuild(from, build2) {
40044
+ emitWatchState("updating");
40045
+ const pullResult = pullFastForward();
40046
+ const pullReport = describePull(pullResult);
40047
+ reportOutcome(pullReport);
40048
+ if (pullResult.kind !== "fast-forwarded")
40049
+ return process.exit(pullReport.exitCode);
40050
+ console.log(`
40051
+ ${buildWatchReport(from)}`);
40052
+ if (build2) {
40053
+ await reportBuildOrExit(
40054
+ typeof build2 === "string" ? build2 : DEFAULT_BUILD_ENTRY
40055
+ );
40056
+ if (syncAdvice(changedPaths(from)).length > 0) await reportSyncOrExit();
40057
+ }
40058
+ process.exit(0);
40059
+ }
40060
+
40061
+ // src/commands/watch/consumeSimulatedDivergence.ts
40062
+ import { existsSync as existsSync81, rmSync as rmSync6 } from "fs";
40063
+ function consumeSimulatedDivergence(cwd) {
40064
+ try {
40065
+ const path106 = simulatedDivergencePath(cwd);
40066
+ if (!existsSync81(path106)) return false;
40067
+ rmSync6(path106);
40068
+ return true;
40069
+ } catch {
40070
+ return false;
40071
+ }
40072
+ }
40073
+
39999
40074
  // src/commands/watch/fetchQuietly.ts
40000
40075
  import { execFileSync as execFileSync22 } from "child_process";
40001
40076
  var MIN_FETCH_TIMEOUT_MS = 6e4;
@@ -40032,7 +40107,7 @@ function readMovement(cwd) {
40032
40107
  // src/commands/watch/pollForMovement.ts
40033
40108
  function pollForMovement(options2) {
40034
40109
  const { upstream, intervalMs, timeoutMs, timeout, cwd } = options2;
40035
- return new Promise((resolve26) => {
40110
+ return new Promise((resolve27) => {
40036
40111
  let settled = false;
40037
40112
  const finish2 = (outcome) => {
40038
40113
  if (settled) return;
@@ -40040,10 +40115,12 @@ function pollForMovement(options2) {
40040
40115
  clearInterval(ticker);
40041
40116
  clearTimeout(deadline);
40042
40117
  process.off("SIGINT", onInterrupt);
40043
- resolve26(outcome);
40118
+ resolve27(outcome);
40044
40119
  };
40045
40120
  const onInterrupt = () => finish2({ kind: "interrupted" });
40046
40121
  const ticker = setInterval(() => {
40122
+ if (consumeSimulatedDivergence(cwd))
40123
+ return finish2({ kind: "simulated-divergence", upstream });
40047
40124
  fetchQuietly(cwd, intervalMs);
40048
40125
  const found = readMovement(cwd);
40049
40126
  if (found) finish2({ kind: "moved", upstream, ...found });
@@ -40069,6 +40146,8 @@ function waitForUpstream(options2) {
40069
40146
  });
40070
40147
  }
40071
40148
  onStart?.(upstream);
40149
+ if (consumeSimulatedDivergence(cwd))
40150
+ return Promise.resolve({ kind: "simulated-divergence", upstream });
40072
40151
  fetchQuietly(cwd, intervalMs);
40073
40152
  const moved = readMovement(cwd);
40074
40153
  if (moved) return Promise.resolve({ kind: "moved", upstream, ...moved });
@@ -40076,11 +40155,6 @@ function waitForUpstream(options2) {
40076
40155
  }
40077
40156
 
40078
40157
  // src/commands/watch/watchWait.ts
40079
- var DEFAULT_BUILD_ENTRY = "auto-build";
40080
- function report({ exitCode, message: message3 }) {
40081
- if (exitCode === 0) console.log(message3);
40082
- else console.error(message3);
40083
- }
40084
40158
  async function watchWait(options2) {
40085
40159
  const { intervalMs, timeoutMs } = parseWatchDurations(
40086
40160
  options2.interval,
@@ -40090,27 +40164,16 @@ async function watchWait(options2) {
40090
40164
  intervalMs,
40091
40165
  timeoutMs,
40092
40166
  timeout: options2.timeout,
40093
- onStart: (upstream) => console.log(`waiting on ${upstream} \u2026`)
40167
+ onStart: (upstream) => {
40168
+ emitWatchState("waiting");
40169
+ console.log(`waiting on ${upstream} \u2026`);
40170
+ }
40094
40171
  });
40095
40172
  const waitReport = describeOutcome(outcome);
40096
- report(waitReport);
40173
+ reportOutcome(waitReport);
40097
40174
  if (outcome.kind !== "moved" || !options2.pull)
40098
40175
  return process.exit(waitReport.exitCode);
40099
- const pullResult = pullFastForward();
40100
- const pullReport = describePull(pullResult);
40101
- report(pullReport);
40102
- if (pullResult.kind !== "fast-forwarded")
40103
- return process.exit(pullReport.exitCode);
40104
- console.log(`
40105
- ${buildWatchReport(outcome.from)}`);
40106
- if (options2.build) {
40107
- await reportBuildOrExit(
40108
- typeof options2.build === "string" ? options2.build : DEFAULT_BUILD_ENTRY
40109
- );
40110
- if (syncAdvice(changedPaths(outcome.from)).length > 0)
40111
- await reportSyncOrExit();
40112
- }
40113
- process.exit(0);
40176
+ await pullAndBuild(outcome.from, options2.build);
40114
40177
  }
40115
40178
 
40116
40179
  // src/commands/registerWatch.ts
@@ -40138,6 +40201,9 @@ function registerWatch(program2) {
40138
40201
  watchCommand.command("loop").description(
40139
40202
  "Run assist watch wait --pull --build as a fresh child per lap, relaunching after exit 0, 2 or 4 or a signal kill, and exit with the child's code on 1, 3 or 130"
40140
40203
  ).action(() => watchLoop());
40204
+ watchCommand.command("simulate-divergence").description(
40205
+ "Make the next assist watch wait poll in this repo exit 3 as if the branch had diverged, to test the watcher's divergence escalation"
40206
+ ).action(() => simulateDivergence());
40141
40207
  watchCommand.command("report").description(
40142
40208
  "Print the built version, the last 10 commits as a markdown table, the restarts the new commits make necessary, and whether ~/.claude needs a sync"
40143
40209
  ).option(
@@ -40169,7 +40235,7 @@ function extractCode(url, expectedState) {
40169
40235
  return code;
40170
40236
  }
40171
40237
  function waitForCallback(port, expectedState) {
40172
- return new Promise((resolve26, reject) => {
40238
+ return new Promise((resolve27, reject) => {
40173
40239
  const timeout = setTimeout(() => {
40174
40240
  server.close();
40175
40241
  reject(new Error("Authorization timed out after 120 seconds"));
@@ -40186,7 +40252,7 @@ function waitForCallback(port, expectedState) {
40186
40252
  const code = extractCode(url, expectedState);
40187
40253
  respondHtml(res, 200, "Authorization successful!");
40188
40254
  server.close();
40189
- resolve26(code);
40255
+ resolve27(code);
40190
40256
  } catch (error) {
40191
40257
  respondHtml(res, 400, error.message);
40192
40258
  server.close();
@@ -40469,7 +40535,7 @@ async function run3(name, args) {
40469
40535
  }
40470
40536
 
40471
40537
  // src/commands/run/add.ts
40472
- import { mkdirSync as mkdirSync33, writeFileSync as writeFileSync52 } from "fs";
40538
+ import { mkdirSync as mkdirSync33, writeFileSync as writeFileSync53 } from "fs";
40473
40539
  import { join as join95 } from "path";
40474
40540
 
40475
40541
  // src/commands/run/extractOption.ts
@@ -40540,7 +40606,7 @@ description: Run ${name}
40540
40606
  Run \`assist run ${name} $ARGUMENTS 2>&1\`.
40541
40607
  `;
40542
40608
  const filePath = join95(dir, `${name}.md`);
40543
- writeFileSync52(filePath, content);
40609
+ writeFileSync53(filePath, content);
40544
40610
  console.log(`Created command file: ${filePath}`);
40545
40611
  }
40546
40612
  function add4() {
@@ -40595,7 +40661,7 @@ function link2() {
40595
40661
  }
40596
40662
 
40597
40663
  // src/commands/run/remove.ts
40598
- import { existsSync as existsSync81, unlinkSync as unlinkSync21 } from "fs";
40664
+ import { existsSync as existsSync82, unlinkSync as unlinkSync21 } from "fs";
40599
40665
  import { join as join96 } from "path";
40600
40666
  function findRemoveIndex() {
40601
40667
  const idx = process.argv.indexOf("remove");
@@ -40612,7 +40678,7 @@ function parseRemoveName() {
40612
40678
  }
40613
40679
  function deleteCommandFile(name) {
40614
40680
  const filePath = join96(".claude", "commands", `${name}.md`);
40615
- if (existsSync81(filePath)) {
40681
+ if (existsSync82(filePath)) {
40616
40682
  unlinkSync21(filePath);
40617
40683
  console.log(`Deleted command file: ${filePath}`);
40618
40684
  }
@@ -40691,10 +40757,10 @@ var STATUS_TIMEOUT_MS2 = 5e3;
40691
40757
  function queryDaemon(socket) {
40692
40758
  socket.write(`${JSON.stringify({ type: "ping" })}
40693
40759
  `);
40694
- return new Promise((resolve26) => {
40760
+ return new Promise((resolve27) => {
40695
40761
  const result = { sessions: [] };
40696
40762
  const pending = /* @__PURE__ */ new Set(["sessions", "pong"]);
40697
- const timer = setTimeout(() => resolve26(result), STATUS_TIMEOUT_MS2);
40763
+ const timer = setTimeout(() => resolve27(result), STATUS_TIMEOUT_MS2);
40698
40764
  const lines2 = createInterface8({ input: socket });
40699
40765
  lines2.on("error", () => {
40700
40766
  });
@@ -40702,7 +40768,7 @@ function queryDaemon(socket) {
40702
40768
  applyLine(result, pending, line);
40703
40769
  if (pending.size === 0) {
40704
40770
  clearTimeout(timer);
40705
- resolve26(result);
40771
+ resolve27(result);
40706
40772
  }
40707
40773
  });
40708
40774
  });
@@ -40802,11 +40868,11 @@ function clearPersistedSessionsOnDrain() {
40802
40868
 
40803
40869
  // src/commands/sessions/daemon/readDaemonMessage.ts
40804
40870
  function readDaemonMessage(lines2, timeoutMs, fallback, match) {
40805
- return new Promise((resolve26) => {
40871
+ return new Promise((resolve27) => {
40806
40872
  const finish2 = (value) => {
40807
40873
  clearTimeout(timer);
40808
40874
  lines2.off("line", onLine);
40809
- resolve26(value);
40875
+ resolve27(value);
40810
40876
  };
40811
40877
  const timer = setTimeout(() => finish2(fallback), timeoutMs);
40812
40878
  const onLine = (line) => {
@@ -40993,12 +41059,12 @@ function toSessionRunInfo({
40993
41059
  }
40994
41060
 
40995
41061
  // src/commands/sessions/daemon/worktree/joinRefusal.ts
40996
- import { existsSync as existsSync82 } from "fs";
41062
+ import { existsSync as existsSync83 } from "fs";
40997
41063
  function joinRefusal(session) {
40998
41064
  if (session.commandType === "run") return "a server run has no agent stream";
40999
41065
  if (session.closing === true) return "the session is closing";
41000
41066
  if (!session.cwd) return "the session has no working directory";
41001
- if (!existsSync82(session.cwd))
41067
+ if (!existsSync83(session.cwd))
41002
41068
  return "the session's workspace no longer exists";
41003
41069
  return void 0;
41004
41070
  }
@@ -41373,11 +41439,11 @@ function sessionBase(id, status2) {
41373
41439
  }
41374
41440
 
41375
41441
  // src/commands/sessions/daemon/spawnPty.ts
41376
- import { existsSync as existsSync84 } from "fs";
41442
+ import { existsSync as existsSync85 } from "fs";
41377
41443
  import * as pty from "node-pty";
41378
41444
 
41379
41445
  // src/commands/sessions/daemon/ensureSpawnHelperExecutable.ts
41380
- import { chmodSync, existsSync as existsSync83, statSync as statSync13 } from "fs";
41446
+ import { chmodSync, existsSync as existsSync84, statSync as statSync13 } from "fs";
41381
41447
  import { createRequire as createRequire3 } from "module";
41382
41448
  import path102 from "path";
41383
41449
  var require4 = createRequire3(import.meta.url);
@@ -41392,7 +41458,7 @@ function ensureSpawnHelperExecutable() {
41392
41458
  `${process.platform}-${process.arch}`,
41393
41459
  "spawn-helper"
41394
41460
  );
41395
- if (!existsSync83(helper)) return;
41461
+ if (!existsSync84(helper)) return;
41396
41462
  const mode = statSync13(helper).mode;
41397
41463
  if ((mode & 73) === 0) chmodSync(helper, mode | 493);
41398
41464
  }
@@ -41428,7 +41494,7 @@ function spawnPty(args, cwd, sessionId, extraEnv) {
41428
41494
  });
41429
41495
  }
41430
41496
  function refuseMissingCwd(cwd, sessionId) {
41431
- if (!cwd || existsSync84(cwd)) return;
41497
+ if (!cwd || existsSync85(cwd)) return;
41432
41498
  daemonLog(
41433
41499
  `${sessionId ? `session ${sessionId}` : "pty"} not spawned: working directory ${cwd} no longer exists`
41434
41500
  );
@@ -41621,11 +41687,11 @@ function setStatus2(session, newStatus) {
41621
41687
  }
41622
41688
 
41623
41689
  // src/commands/sessions/daemon/worktree/reapWorktree.ts
41624
- import { existsSync as existsSync86 } from "fs";
41690
+ import { existsSync as existsSync87 } from "fs";
41625
41691
  import { basename as basename27 } from "path";
41626
41692
 
41627
41693
  // src/commands/sessions/daemon/worktree/deleteStrandedTree.ts
41628
- import { existsSync as existsSync85 } from "fs";
41694
+ import { existsSync as existsSync86 } from "fs";
41629
41695
  import { join as join99 } from "path";
41630
41696
 
41631
41697
  // src/commands/sessions/daemon/worktree/deleteTreeDirectly.ts
@@ -41695,7 +41761,7 @@ async function deleteStrandedTree(clone, worktreePath, cause) {
41695
41761
  );
41696
41762
  }
41697
41763
  function strandedReason(worktreePath, cause) {
41698
- if (!existsSync85(join99(worktreePath, ".git")))
41764
+ if (!existsSync86(join99(worktreePath, ".git")))
41699
41765
  return "its .git link is already gone";
41700
41766
  if (/not a working tree|not a git repository/i.test(reason2(cause)))
41701
41767
  return "git no longer recognises it as a working tree";
@@ -41747,7 +41813,7 @@ function reason3(error) {
41747
41813
 
41748
41814
  // src/commands/sessions/daemon/worktree/reapWorktree.ts
41749
41815
  async function reapWorktree(worktreePath, force = false) {
41750
- if (!existsSync86(worktreePath)) {
41816
+ if (!existsSync87(worktreePath)) {
41751
41817
  forgetWorktree(worktreePath);
41752
41818
  daemonLog(
41753
41819
  `worktree ${worktreePath} already gone; its record was forgotten`
@@ -41772,7 +41838,7 @@ async function reapWorktree(worktreePath, force = false) {
41772
41838
  }
41773
41839
  function owningClone(worktreePath) {
41774
41840
  const recorded = worktreeAttributionIncludingReaped(worktreePath)?.clone;
41775
- if (recorded && existsSync86(recorded)) return recorded;
41841
+ if (recorded && existsSync87(recorded)) return recorded;
41776
41842
  const detected = mainWorktree(worktreePath);
41777
41843
  if (detected) return detected;
41778
41844
  daemonLog(
@@ -41969,12 +42035,12 @@ function processCwd(link3) {
41969
42035
  var POLL_MS = 500;
41970
42036
  var GRACE_MS = 5e3;
41971
42037
  function awaitTreeVacated(session, treePath) {
41972
- return new Promise((resolve26) => {
42038
+ return new Promise((resolve27) => {
41973
42039
  let ticks = GRACE_MS / POLL_MS;
41974
42040
  const settle = (outcome) => {
41975
42041
  clearTimeout(timer);
41976
42042
  session.closeGrace = void 0;
41977
- resolve26(outcome);
42043
+ resolve27(outcome);
41978
42044
  };
41979
42045
  const tick = () => {
41980
42046
  if (liveProcessesInTree(treePath).length === 0) settle("vacated");
@@ -42010,12 +42076,12 @@ async function closeBlockReason(sessionId, tree) {
42010
42076
  }
42011
42077
 
42012
42078
  // src/commands/sessions/daemon/worktree/watchGitState.ts
42013
- import { existsSync as existsSync87, watch } from "fs";
42079
+ import { existsSync as existsSync88, watch } from "fs";
42014
42080
  var DEBOUNCE_MS = 500;
42015
42081
  var POLL_MS2 = 3e4;
42016
42082
  function watchGitState(cwd, onChange) {
42017
42083
  const common = gitCommonDir(cwd);
42018
- if (!common || !existsSync87(common)) return void 0;
42084
+ if (!common || !existsSync88(common)) return void 0;
42019
42085
  const watchers = [
42020
42086
  watchGitDir(common, onChange),
42021
42087
  pollGitState(cwd, onChange)
@@ -42562,10 +42628,10 @@ function emitSessionOutput(session, clients, data) {
42562
42628
  }
42563
42629
 
42564
42630
  // src/commands/sessions/daemon/exitReason.ts
42565
- import { existsSync as existsSync88 } from "fs";
42566
- import { resolve as resolve25 } from "path";
42631
+ import { existsSync as existsSync89 } from "fs";
42632
+ import { resolve as resolve26 } from "path";
42567
42633
  function exitDetail(session) {
42568
- if (session.cwd && !existsSync88(session.cwd))
42634
+ if (session.cwd && !existsSync89(session.cwd))
42569
42635
  return `working directory ${session.cwd} no longer exists`;
42570
42636
  return missingRunConfigCwd(session);
42571
42637
  }
@@ -42578,8 +42644,8 @@ function missingRunConfigCwd(session) {
42578
42644
  const dir = session.cwd ?? process.cwd();
42579
42645
  const config = resolveRunConfig(session.runName, dir);
42580
42646
  if (!config?.cwd) return void 0;
42581
- const configured = resolve25(runConfigBaseDirFrom(dir), config.cwd);
42582
- if (existsSync88(configured)) return void 0;
42647
+ const configured = resolve26(runConfigBaseDirFrom(dir), config.cwd);
42648
+ if (existsSync89(configured)) return void 0;
42583
42649
  return `run config "${config.name}": cwd ${configured} does not exist`;
42584
42650
  }
42585
42651
 
@@ -42627,7 +42693,7 @@ function handleRefusedRun(session, exitCode, onStatusChange) {
42627
42693
  }
42628
42694
 
42629
42695
  // src/commands/sessions/daemon/watchActivity.ts
42630
- import { existsSync as existsSync89, mkdirSync as mkdirSync34, watch as watch2 } from "fs";
42696
+ import { existsSync as existsSync90, mkdirSync as mkdirSync34, watch as watch2 } from "fs";
42631
42697
  import { dirname as dirname41 } from "path";
42632
42698
 
42633
42699
  // src/commands/sessions/daemon/applyActivityToSession.ts
@@ -42713,7 +42779,7 @@ function watchActivity(session, notify2, onClaudeSessionId) {
42713
42779
  if (timer) clearTimeout(timer);
42714
42780
  timer = setTimeout(read3, DEBOUNCE_MS2);
42715
42781
  });
42716
- if (existsSync89(path106)) read3();
42782
+ if (existsSync90(path106)) read3();
42717
42783
  }
42718
42784
  function refreshActivity(session) {
42719
42785
  if (session.commandType !== "assist" || !session.cwd) return;
@@ -44129,16 +44195,16 @@ function rebindClaudeSession(session, claudeSessionId, notify2, onStatusChange)
44129
44195
  }
44130
44196
 
44131
44197
  // src/commands/sessions/daemon/setStatusFromHook.ts
44132
- function setStatusFromHook(sessions, report2, notify2, onStatusChange) {
44198
+ function setStatusFromHook(sessions, report, notify2, onStatusChange) {
44133
44199
  applySetStatus(
44134
44200
  sessions,
44135
- report2.id,
44136
- report2.status,
44137
- report2.source,
44201
+ report.id,
44202
+ report.status,
44203
+ report.source,
44138
44204
  onStatusChange,
44139
44205
  (session) => rebindClaudeSession(
44140
44206
  session,
44141
- report2.claudeSessionId,
44207
+ report.claudeSessionId,
44142
44208
  notify2,
44143
44209
  onStatusChange
44144
44210
  )
@@ -44919,7 +44985,7 @@ function rearmStoppedSessions(sessions, notify2) {
44919
44985
  }
44920
44986
 
44921
44987
  // src/commands/sessions/daemon/worktree/reconcileWorktreesOnRestore.ts
44922
- import { existsSync as existsSync92 } from "fs";
44988
+ import { existsSync as existsSync93 } from "fs";
44923
44989
  import { basename as basename29 } from "path";
44924
44990
 
44925
44991
  // src/commands/sessions/daemon/worktree/accountedTrees.ts
@@ -44940,9 +45006,9 @@ function accountedTrees(sessions) {
44940
45006
  }
44941
45007
 
44942
45008
  // src/commands/sessions/daemon/worktree/reclaimVanishedWorktrees.ts
44943
- import { existsSync as existsSync91 } from "fs";
45009
+ import { existsSync as existsSync92 } from "fs";
44944
45010
  async function reclaimVanishedWorktrees(clone, paths) {
44945
- if (!existsSync91(clone)) {
45011
+ if (!existsSync92(clone)) {
44946
45012
  for (const { path: path106 } of paths) forgetWorktree(path106);
44947
45013
  daemonLog(
44948
45014
  `clone ${clone} is gone; forgot ${paths.length} worktree record(s) it owned`
@@ -45108,7 +45174,7 @@ async function recoverOrphanedWorktrees(sessions, spawnWith, notify2) {
45108
45174
  );
45109
45175
  continue;
45110
45176
  }
45111
- if (!existsSync92(path106)) {
45177
+ if (!existsSync93(path106)) {
45112
45178
  logVanishedTree(sessions, path106);
45113
45179
  vanished.set(clone, [
45114
45180
  ...vanished.get(clone) ?? [],
@@ -45524,7 +45590,7 @@ function failPendingCreators(state, message3) {
45524
45590
  }
45525
45591
  function resetRelayState(state, reason4) {
45526
45592
  failPendingCreators(state, reason4);
45527
- for (const resolve26 of state.historyWaiters) resolve26([]);
45593
+ for (const resolve27 of state.historyWaiters) resolve27([]);
45528
45594
  state.historyWaiters = [];
45529
45595
  state.sessions = [];
45530
45596
  state.lastSnapshot = void 0;
@@ -45965,16 +46031,16 @@ var HISTORY_TIMEOUT_MS = 5e3;
45965
46031
  function requestLinkHistory(ctx) {
45966
46032
  if (!ctx.greeted) return Promise.resolve([]);
45967
46033
  const waiters = ctx.relay.historyWaiters;
45968
- return new Promise((resolve26) => {
46034
+ return new Promise((resolve27) => {
45969
46035
  const settle = (sessions) => {
45970
46036
  clearTimeout(timer);
45971
- resolve26(sessions);
46037
+ resolve27(sessions);
45972
46038
  };
45973
46039
  const timer = setTimeout(() => {
45974
46040
  const index2 = waiters.indexOf(settle);
45975
46041
  if (index2 !== -1) waiters.splice(index2, 1);
45976
46042
  daemonLog(`link ${ctx.spec.name} ws: history timed out`);
45977
- resolve26(ctx.relay.lastHistory ?? []);
46043
+ resolve27(ctx.relay.lastHistory ?? []);
45978
46044
  }, HISTORY_TIMEOUT_MS);
45979
46045
  timer.unref?.();
45980
46046
  waiters.push(settle);
@@ -46198,7 +46264,7 @@ function spawnAssistInTree(ctx, assistArgs, cwd, meta, context) {
46198
46264
  }
46199
46265
 
46200
46266
  // src/commands/sessions/daemon/worktree/resumeInTree.ts
46201
- import { existsSync as existsSync95 } from "fs";
46267
+ import { existsSync as existsSync96 } from "fs";
46202
46268
 
46203
46269
  // src/commands/sessions/daemon/resumeSession.ts
46204
46270
  function resumeSession(id, sessionId, cwd, name, holdPty, harness) {
@@ -46229,10 +46295,10 @@ function resumeSession(id, sessionId, cwd, name, holdPty, harness) {
46229
46295
  }
46230
46296
 
46231
46297
  // src/commands/sessions/daemon/worktree/resumeInReplacementTree.ts
46232
- import { existsSync as existsSync94 } from "fs";
46298
+ import { existsSync as existsSync95 } from "fs";
46233
46299
 
46234
46300
  // src/commands/sessions/daemon/worktree/carryTranscriptToTree.ts
46235
- import { copyFileSync as copyFileSync5, existsSync as existsSync93, mkdirSync as mkdirSync36 } from "fs";
46301
+ import { copyFileSync as copyFileSync5, existsSync as existsSync94, mkdirSync as mkdirSync36 } from "fs";
46236
46302
  import { join as join101 } from "path";
46237
46303
  function carryTranscriptToTree(claudeSessionId, fromCwd, toCwd) {
46238
46304
  const dir = projectDirForCwd(toCwd);
@@ -46243,7 +46309,7 @@ function carryTranscriptToTree(claudeSessionId, fromCwd, toCwd) {
46243
46309
  return;
46244
46310
  }
46245
46311
  const dest = join101(dir, `${claudeSessionId}.jsonl`);
46246
- if (existsSync93(dest)) {
46312
+ if (existsSync94(dest)) {
46247
46313
  daemonLog(`transcript ${claudeSessionId} already present in ${dir}`);
46248
46314
  return;
46249
46315
  }
@@ -46294,7 +46360,7 @@ function resumeInReplacementTree(ctx, claudeSessionId, missingCwd, name, harness
46294
46360
  }
46295
46361
  function cloneForReapedTree(missingCwd) {
46296
46362
  const clone = worktreeAttributionIncludingReaped(missingCwd)?.clone;
46297
- if (!clone || !existsSync94(clone))
46363
+ if (!clone || !existsSync95(clone))
46298
46364
  throw new Error(
46299
46365
  `working directory no longer exists and no clone is recorded to re-allocate from: ${missingCwd}`
46300
46366
  );
@@ -46303,7 +46369,7 @@ function cloneForReapedTree(missingCwd) {
46303
46369
 
46304
46370
  // src/commands/sessions/daemon/worktree/resumeInTree.ts
46305
46371
  function resumeInTree(ctx, sessionId, cwd, name, harness) {
46306
- if (!existsSync95(cwd))
46372
+ if (!existsSync96(cwd))
46307
46373
  return resumeInReplacementTree(ctx, sessionId, cwd, name, harness);
46308
46374
  const id = ctx.spawnWith(
46309
46375
  (sid) => resumeSession(sid, sessionId, cwd, name, void 0, harness)
@@ -46438,8 +46504,8 @@ var SessionManager = class {
46438
46504
  update(mutate) {
46439
46505
  if (mutate(this.sessions)) this.notify();
46440
46506
  }
46441
- setStatus(report2) {
46442
- setStatusFromHook(this.sessions, report2, this.notify, this.onStatusChange);
46507
+ setStatus(report) {
46508
+ setStatusFromHook(this.sessions, report, this.notify, this.onStatusChange);
46443
46509
  }
46444
46510
  /* why: the status line relays token totals keyed by Claude's session id; join
46445
46511
  * it to the running backlog phase so the spend accumulates against that row. */
@@ -47125,7 +47191,7 @@ function handleConnection(socket, manager) {
47125
47191
  }
47126
47192
 
47127
47193
  // src/commands/sessions/daemon/onListening.ts
47128
- import { unlinkSync as unlinkSync22, writeFileSync as writeFileSync53 } from "fs";
47194
+ import { unlinkSync as unlinkSync22, writeFileSync as writeFileSync54 } from "fs";
47129
47195
 
47130
47196
  // src/commands/sessions/daemon/startPidFileWatchdog.ts
47131
47197
  import { readFileSync as readFileSync65 } from "fs";
@@ -47147,7 +47213,7 @@ function ownsPidFile() {
47147
47213
 
47148
47214
  // src/commands/sessions/daemon/onListening.ts
47149
47215
  function onListening(manager, checkAutoExit) {
47150
- writeFileSync53(daemonPaths.pid, String(process.pid));
47216
+ writeFileSync54(daemonPaths.pid, String(process.pid));
47151
47217
  startPidFileWatchdog(() => {
47152
47218
  daemonLog("lost daemon.pid ownership; shutting down sessions and exiting");
47153
47219
  void manager.flushActiveMs().finally(() => {
@@ -47308,17 +47374,17 @@ async function findUnlinkedWindowsNode(health2, platform = detectPlatform()) {
47308
47374
 
47309
47375
  // src/commands/sessions/nodes/printReport.ts
47310
47376
  import chalk254 from "chalk";
47311
- function printReport(report2) {
47312
- if (report2.links.length === 0) {
47313
- console.log(`${report2.local} has no links`);
47314
- if (report2.suggestion)
47377
+ function printReport(report) {
47378
+ if (report.links.length === 0) {
47379
+ console.log(`${report.local} has no links`);
47380
+ if (report.suggestion)
47315
47381
  console.log(
47316
- `A Windows node (${report2.suggestion.nodeName}) answers on ${report2.suggestion.url} but is not linked. Link it with:
47317
- ${report2.suggestion.command}`
47382
+ `A Windows node (${report.suggestion.nodeName}) answers on ${report.suggestion.url} but is not linked. Link it with:
47383
+ ${report.suggestion.command}`
47318
47384
  );
47319
47385
  return;
47320
47386
  }
47321
- for (const diagnosis of report2.links) printDiagnosis(diagnosis);
47387
+ for (const diagnosis of report.links) printDiagnosis(diagnosis);
47322
47388
  }
47323
47389
  function printDiagnosis(diagnosis) {
47324
47390
  console.log(`${chalk254.bold(diagnosis.name)} ${chalk254.dim(diagnosis.url)}`);
@@ -47335,13 +47401,13 @@ async function doctorNodes(name, options2) {
47335
47401
  if (name && specs.length === 0)
47336
47402
  throw new Error(`No link named ${name}; see assist sessions nodes`);
47337
47403
  const probes = buildDoctorProbes(await queryNodes());
47338
- const report2 = { local: resolveNodeName(), links: [] };
47339
- for (const spec of specs) report2.links.push(await diagnoseLink(spec, probes));
47404
+ const report = { local: resolveNodeName(), links: [] };
47405
+ for (const spec of specs) report.links.push(await diagnoseLink(spec, probes));
47340
47406
  if (specs.length === 0)
47341
- report2.suggestion = await findUnlinkedWindowsNode(probes.health);
47342
- if (report2.links.some((l) => !l.ok)) process.exitCode = 1;
47343
- if (options2.json) console.log(JSON.stringify(report2, null, 2));
47344
- else printReport(report2);
47407
+ report.suggestion = await findUnlinkedWindowsNode(probes.health);
47408
+ if (report.links.some((l) => !l.ok)) process.exitCode = 1;
47409
+ if (options2.json) console.log(JSON.stringify(report, null, 2));
47410
+ else printReport(report);
47345
47411
  }
47346
47412
 
47347
47413
  // src/commands/sessions/nodes/listNodes.ts
@@ -47357,16 +47423,16 @@ async function nodesReport() {
47357
47423
  };
47358
47424
  }
47359
47425
  async function listNodes(options2) {
47360
- const report2 = await nodesReport();
47426
+ const report = await nodesReport();
47361
47427
  if (options2.json) {
47362
- console.log(JSON.stringify(report2, null, 2));
47428
+ console.log(JSON.stringify(report, null, 2));
47363
47429
  return;
47364
47430
  }
47365
- console.log(`${report2.local} ${chalk255.dim("(this node)")}`);
47366
- if (!report2.daemonRunning)
47431
+ console.log(`${report.local} ${chalk255.dim("(this node)")}`);
47432
+ if (!report.daemonRunning)
47367
47433
  console.log(chalk255.dim(" daemon not running; showing configured links"));
47368
- if (report2.links.length === 0) console.log(chalk255.dim(" no links"));
47369
- for (const link3 of report2.links) console.log(formatLink(link3));
47434
+ if (report.links.length === 0) console.log(chalk255.dim(" no links"));
47435
+ for (const link3 of report.links) console.log(formatLink(link3));
47370
47436
  }
47371
47437
 
47372
47438
  // src/commands/sessions/nodes/nodeLogs.ts