@staff0rd/assist 0.324.1 → 0.325.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
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.324.1",
9
+ version: "0.325.1",
10
10
  type: "module",
11
11
  main: "dist/index.js",
12
12
  bin: {
@@ -6011,8 +6011,10 @@ function extractPath(rest) {
6011
6011
  const arrow = rest.indexOf(" -> ");
6012
6012
  return arrow === -1 ? rest : rest.slice(arrow + 4);
6013
6013
  }
6014
+ var UNMERGED_STATES = /* @__PURE__ */ new Set(["DD", "AU", "UD", "UA", "DU", "AA", "UU"]);
6014
6015
  function categorize(xy) {
6015
6016
  if (xy === "??") return "new";
6017
+ if (UNMERGED_STATES.has(xy)) return "modified";
6016
6018
  const codes = xy.replace(/ /g, "");
6017
6019
  if (codes.includes("A")) return "new";
6018
6020
  if (codes.includes("D")) return "deleted";
@@ -9295,16 +9297,180 @@ function registerCliHook(program2) {
9295
9297
  registerDeny(cmd);
9296
9298
  }
9297
9299
 
9300
+ // src/commands/codeComment/codeCommentConfirm.ts
9301
+ import { existsSync as existsSync27, readFileSync as readFileSync22, unlinkSync as unlinkSync8, writeFileSync as writeFileSync22 } from "fs";
9302
+ import chalk92 from "chalk";
9303
+
9304
+ // src/commands/codeComment/getRestrictedDir.ts
9305
+ import { homedir as homedir11 } from "os";
9306
+ import { join as join25 } from "path";
9307
+ function getRestrictedDir() {
9308
+ return join25(homedir11(), ".assist", "restricted");
9309
+ }
9310
+ function getPinStatePath(pin) {
9311
+ return join25(getRestrictedDir(), `code-comment-${pin}.json`);
9312
+ }
9313
+
9314
+ // src/commands/codeComment/sweepRestrictedDir.ts
9315
+ import { readdirSync, statSync as statSync2, unlinkSync as unlinkSync7 } from "fs";
9316
+ import { join as join26 } from "path";
9317
+ var STALE_AFTER_MS = 30 * 60 * 1e3;
9318
+ function sweepRestrictedDir(dir = getRestrictedDir()) {
9319
+ let entries;
9320
+ try {
9321
+ entries = readdirSync(dir);
9322
+ } catch {
9323
+ return;
9324
+ }
9325
+ const cutoff = Date.now() - STALE_AFTER_MS;
9326
+ for (const entry of entries) {
9327
+ const path57 = join26(dir, entry);
9328
+ try {
9329
+ if (statSync2(path57).mtimeMs < cutoff) unlinkSync7(path57);
9330
+ } catch {
9331
+ continue;
9332
+ }
9333
+ }
9334
+ }
9335
+
9336
+ // src/commands/codeComment/codeCommentConfirm.ts
9337
+ function readPinState(pin) {
9338
+ const path57 = getPinStatePath(pin);
9339
+ if (!existsSync27(path57)) return void 0;
9340
+ try {
9341
+ const state = JSON.parse(readFileSync22(path57, "utf8"));
9342
+ if (state.pin !== pin) return void 0;
9343
+ return state;
9344
+ } catch {
9345
+ return void 0;
9346
+ }
9347
+ }
9348
+ function codeCommentConfirm(pin) {
9349
+ sweepRestrictedDir();
9350
+ const state = readPinState(pin);
9351
+ if (!state) {
9352
+ console.error(chalk92.red(`No pending comment for pin: ${pin}`));
9353
+ process.exitCode = 1;
9354
+ return;
9355
+ }
9356
+ if (!existsSync27(state.file)) {
9357
+ console.error(chalk92.red(`Target file no longer exists: ${state.file}`));
9358
+ process.exitCode = 1;
9359
+ return;
9360
+ }
9361
+ const original = readFileSync22(state.file, "utf8");
9362
+ const lines = original.split("\n");
9363
+ const index3 = state.line - 1;
9364
+ if (index3 > lines.length) {
9365
+ console.error(
9366
+ chalk92.red(
9367
+ `Line ${state.line} is beyond the end of ${state.file} (${lines.length} lines).`
9368
+ )
9369
+ );
9370
+ process.exitCode = 1;
9371
+ return;
9372
+ }
9373
+ const indentSource = lines[index3] ?? "";
9374
+ const indent2 = indentSource.match(/^\s*/)?.[0] ?? "";
9375
+ lines.splice(index3, 0, `${indent2}// ${state.text}`);
9376
+ writeFileSync22(state.file, lines.join("\n"));
9377
+ unlinkSync8(getPinStatePath(pin));
9378
+ console.log(
9379
+ chalk92.green(`Inserted "// ${state.text}" at ${state.file}:${state.line}`)
9380
+ );
9381
+ }
9382
+
9383
+ // src/commands/codeComment/codeCommentSet.ts
9384
+ import { mkdirSync as mkdirSync11, writeFileSync as writeFileSync23 } from "fs";
9385
+ import { randomBytes } from "crypto";
9386
+ import chalk93 from "chalk";
9387
+
9388
+ // src/commands/codeComment/validateCommentText.ts
9389
+ var MAX_COMMENT_LENGTH = 50;
9390
+ function validateCommentText(raw) {
9391
+ const text6 = raw.replace(/^\/\/\s?/, "");
9392
+ if (/[\r\n]/.test(text6)) {
9393
+ return {
9394
+ ok: false,
9395
+ reason: "Comment must be a single line \u2014 multi-line comments are not allowed."
9396
+ };
9397
+ }
9398
+ if (text6.includes("/*") || text6.includes("*/")) {
9399
+ return {
9400
+ ok: false,
9401
+ reason: "Block comments (/* */) are not allowed \u2014 only single-line // comments."
9402
+ };
9403
+ }
9404
+ if (text6.length > MAX_COMMENT_LENGTH) {
9405
+ return {
9406
+ ok: false,
9407
+ reason: `Comment text is ${text6.length} chars; the cap is ${MAX_COMMENT_LENGTH}. Make it shorter or, better, make the code self-documenting.`
9408
+ };
9409
+ }
9410
+ return { ok: true, text: text6 };
9411
+ }
9412
+
9413
+ // src/commands/codeComment/codeCommentSet.ts
9414
+ function generatePin() {
9415
+ return randomBytes(4).toString("hex");
9416
+ }
9417
+ function codeCommentSet(file, line, text6) {
9418
+ const lineNumber = Number.parseInt(line, 10);
9419
+ if (!Number.isInteger(lineNumber) || lineNumber < 1) {
9420
+ console.error(chalk93.red(`Invalid line number: ${line}`));
9421
+ process.exitCode = 1;
9422
+ return;
9423
+ }
9424
+ const validation = validateCommentText(text6);
9425
+ if (!validation.ok) {
9426
+ console.error(chalk93.red(`Refused: ${validation.reason}`));
9427
+ console.error(chalk93.red("No pin issued."));
9428
+ process.exitCode = 1;
9429
+ return;
9430
+ }
9431
+ console.error(
9432
+ chalk93.yellow.bold(
9433
+ "Think hard. Comments are a last resort, not a habit.\nAlmost every comment you reach for is a sign the code should be clearer instead.\nBefore you confirm this pin, ask whether a better name, a smaller function, or a\ntest would make the comment redundant. If you are still sure this one line earns\nits keep, run the confirm step below."
9434
+ )
9435
+ );
9436
+ const pin = generatePin();
9437
+ mkdirSync11(getRestrictedDir(), { recursive: true });
9438
+ sweepRestrictedDir();
9439
+ writeFileSync23(
9440
+ getPinStatePath(pin),
9441
+ JSON.stringify({ pin, file, line: lineNumber, text: validation.text })
9442
+ );
9443
+ console.log(
9444
+ `${chalk93.green(`Pin issued: ${pin}`)}
9445
+ To insert "// ${validation.text}" at ${file}:${lineNumber}, run:
9446
+ ${chalk93.cyan(` assist code-comment confirm ${pin}`)}`
9447
+ );
9448
+ }
9449
+
9450
+ // src/commands/registerCodeComment.ts
9451
+ function registerCodeComment(parent) {
9452
+ const codeComment = parent.command("code-comment").description(
9453
+ "Escape hatch for the rare code comment that genuinely belongs"
9454
+ );
9455
+ codeComment.command("set").description(
9456
+ "Validate a single-line comment and issue a pin to confirm its insertion"
9457
+ ).argument("<file>", "File the comment belongs in").argument("<line>", "1-based line number to insert the comment at").argument(
9458
+ "<text>",
9459
+ "Single-line comment text (max 50 chars, no block comments)"
9460
+ ).action(codeCommentSet);
9461
+ codeComment.command("confirm").description("Confirm a pin to insert its comment and clear the pin state").argument("<pin>", "Pin issued by 'code-comment set'").action(codeCommentConfirm);
9462
+ }
9463
+
9298
9464
  // src/commands/complexity/analyze.ts
9299
- import chalk100 from "chalk";
9465
+ import chalk102 from "chalk";
9300
9466
 
9301
9467
  // src/commands/complexity/cyclomatic.ts
9302
- import chalk93 from "chalk";
9468
+ import chalk95 from "chalk";
9303
9469
 
9304
9470
  // src/commands/complexity/shared/index.ts
9305
9471
  import fs16 from "fs";
9306
9472
  import path21 from "path";
9307
- import chalk92 from "chalk";
9473
+ import chalk94 from "chalk";
9308
9474
  import ts5 from "typescript";
9309
9475
 
9310
9476
  // src/commands/complexity/findSourceFiles.ts
@@ -9555,7 +9721,7 @@ function createSourceFromFile(filePath) {
9555
9721
  function withSourceFiles(pattern2, callback, extraIgnore = []) {
9556
9722
  const files = findSourceFiles2(pattern2, ".", extraIgnore);
9557
9723
  if (files.length === 0) {
9558
- console.log(chalk92.yellow("No files found matching pattern"));
9724
+ console.log(chalk94.yellow("No files found matching pattern"));
9559
9725
  return void 0;
9560
9726
  }
9561
9727
  return callback(files);
@@ -9588,11 +9754,11 @@ async function cyclomatic(pattern2 = "**/*.ts", options2 = {}) {
9588
9754
  results.sort((a, b) => b.complexity - a.complexity);
9589
9755
  for (const { file, name, complexity } of results) {
9590
9756
  const exceedsThreshold = options2.threshold !== void 0 && complexity > options2.threshold;
9591
- const color = exceedsThreshold ? chalk93.red : chalk93.white;
9592
- console.log(`${color(`${file}:${name}`)} \u2192 ${chalk93.cyan(complexity)}`);
9757
+ const color = exceedsThreshold ? chalk95.red : chalk95.white;
9758
+ console.log(`${color(`${file}:${name}`)} \u2192 ${chalk95.cyan(complexity)}`);
9593
9759
  }
9594
9760
  console.log(
9595
- chalk93.dim(
9761
+ chalk95.dim(
9596
9762
  `
9597
9763
  Analyzed ${results.length} functions across ${files.length} files`
9598
9764
  )
@@ -9604,7 +9770,7 @@ Analyzed ${results.length} functions across ${files.length} files`
9604
9770
  }
9605
9771
 
9606
9772
  // src/commands/complexity/halstead.ts
9607
- import chalk94 from "chalk";
9773
+ import chalk96 from "chalk";
9608
9774
  async function halstead(pattern2 = "**/*.ts", options2 = {}) {
9609
9775
  withSourceFiles(pattern2, (files) => {
9610
9776
  const results = [];
@@ -9619,13 +9785,13 @@ async function halstead(pattern2 = "**/*.ts", options2 = {}) {
9619
9785
  results.sort((a, b) => b.metrics.effort - a.metrics.effort);
9620
9786
  for (const { file, name, metrics } of results) {
9621
9787
  const exceedsThreshold = options2.threshold !== void 0 && metrics.volume > options2.threshold;
9622
- const color = exceedsThreshold ? chalk94.red : chalk94.white;
9788
+ const color = exceedsThreshold ? chalk96.red : chalk96.white;
9623
9789
  console.log(
9624
- `${color(`${file}:${name}`)} \u2192 volume: ${chalk94.cyan(metrics.volume.toFixed(1))}, difficulty: ${chalk94.yellow(metrics.difficulty.toFixed(1))}, effort: ${chalk94.magenta(metrics.effort.toFixed(1))}`
9790
+ `${color(`${file}:${name}`)} \u2192 volume: ${chalk96.cyan(metrics.volume.toFixed(1))}, difficulty: ${chalk96.yellow(metrics.difficulty.toFixed(1))}, effort: ${chalk96.magenta(metrics.effort.toFixed(1))}`
9625
9791
  );
9626
9792
  }
9627
9793
  console.log(
9628
- chalk94.dim(
9794
+ chalk96.dim(
9629
9795
  `
9630
9796
  Analyzed ${results.length} functions across ${files.length} files`
9631
9797
  )
@@ -9637,27 +9803,27 @@ Analyzed ${results.length} functions across ${files.length} files`
9637
9803
  }
9638
9804
 
9639
9805
  // src/commands/complexity/maintainability/displayMaintainabilityResults.ts
9640
- import chalk97 from "chalk";
9806
+ import chalk99 from "chalk";
9641
9807
 
9642
9808
  // src/commands/complexity/maintainability/formatResultLine.ts
9643
- import chalk95 from "chalk";
9809
+ import chalk97 from "chalk";
9644
9810
  function formatResultLine(entry, failing) {
9645
9811
  const { file, avgMaintainability, minMaintainability, override } = entry;
9646
- const name = failing ? chalk95.red(file) : chalk95.white(file);
9647
- const suffix = override !== void 0 ? chalk95.magenta(` (override: ${override})`) : "";
9648
- return `${name} \u2192 avg: ${chalk95.cyan(avgMaintainability.toFixed(1))}, min: ${chalk95.yellow(minMaintainability.toFixed(1))}${suffix}`;
9812
+ const name = failing ? chalk97.red(file) : chalk97.white(file);
9813
+ const suffix = override !== void 0 ? chalk97.magenta(` (override: ${override})`) : "";
9814
+ return `${name} \u2192 avg: ${chalk97.cyan(avgMaintainability.toFixed(1))}, min: ${chalk97.yellow(minMaintainability.toFixed(1))}${suffix}`;
9649
9815
  }
9650
9816
 
9651
9817
  // src/commands/complexity/maintainability/printMaintainabilityFailure.ts
9652
- import chalk96 from "chalk";
9818
+ import chalk98 from "chalk";
9653
9819
  function printMaintainabilityFailure(failingCount, threshold) {
9654
9820
  const thresholdLabel = threshold !== void 0 ? ` ${threshold}` : "";
9655
9821
  console.error(
9656
- chalk96.red(
9822
+ chalk98.red(
9657
9823
  `
9658
9824
  Fail: ${failingCount} file(s) below threshold${thresholdLabel} (files marked "(override: N)" were judged against their own marker). Maintainability index (0\u2013100) is derived from Halstead volume, cyclomatic complexity, and lines of code.
9659
9825
 
9660
- \u26A0\uFE0F ${chalk96.bold("Diagnose and fix one file at a time")} \u2014 do not investigate or fix multiple files in parallel.
9826
+ \u26A0\uFE0F ${chalk98.bold("Diagnose and fix one file at a time")} \u2014 do not investigate or fix multiple files in parallel.
9661
9827
 
9662
9828
  The score is a property of the whole file, not your diff: any existing logic counts, so the fix is to shrink the file \u2014 not to revert or micro-optimize the lines you just changed. Identify the largest cohesive responsibility (often the biggest function, or a related group of functions) and move it to a new file with 'assist refactor extract'. Run 'assist complexity <file>' for per-function metrics only to locate that responsibility, not to tweak individual lines.`
9663
9829
  )
@@ -9669,7 +9835,7 @@ function displayMaintainabilityResults(results, threshold) {
9669
9835
  const gating = threshold !== void 0 || results.some((r) => r.override !== void 0);
9670
9836
  if (!gating) {
9671
9837
  for (const entry of results) console.log(formatResultLine(entry, false));
9672
- console.log(chalk97.dim(`
9838
+ console.log(chalk99.dim(`
9673
9839
  Analyzed ${results.length} files`));
9674
9840
  return;
9675
9841
  }
@@ -9678,7 +9844,7 @@ Analyzed ${results.length} files`));
9678
9844
  return limit !== void 0 && r.minMaintainability < limit;
9679
9845
  });
9680
9846
  if (failing.length === 0) {
9681
- console.log(chalk97.green("All files pass maintainability threshold"));
9847
+ console.log(chalk99.green("All files pass maintainability threshold"));
9682
9848
  } else {
9683
9849
  for (const entry of failing) console.log(formatResultLine(entry, true));
9684
9850
  }
@@ -9687,7 +9853,7 @@ Analyzed ${results.length} files`));
9687
9853
  );
9688
9854
  for (const entry of passingOverrides)
9689
9855
  console.log(formatResultLine(entry, false));
9690
- console.log(chalk97.dim(`
9856
+ console.log(chalk99.dim(`
9691
9857
  Analyzed ${results.length} files`));
9692
9858
  if (failing.length > 0) {
9693
9859
  printMaintainabilityFailure(failing.length, threshold);
@@ -9696,10 +9862,10 @@ Analyzed ${results.length} files`));
9696
9862
  }
9697
9863
 
9698
9864
  // src/commands/complexity/maintainability/printMaintainabilityFormula.ts
9699
- import chalk98 from "chalk";
9865
+ import chalk100 from "chalk";
9700
9866
  var MI_FORMULA = "171 - 5.2*ln(HalsteadVolume) - 0.23*CyclomaticComplexity - 16.2*ln(SLOC), clamped 0-100";
9701
9867
  function printMaintainabilityFormula() {
9702
- console.log(chalk98.dim(MI_FORMULA));
9868
+ console.log(chalk100.dim(MI_FORMULA));
9703
9869
  }
9704
9870
 
9705
9871
  // src/commands/complexity/maintainability/collectFileMetrics.ts
@@ -9775,7 +9941,7 @@ async function maintainability(pattern2 = "**/*.ts", options2 = {}) {
9775
9941
 
9776
9942
  // src/commands/complexity/sloc.ts
9777
9943
  import fs18 from "fs";
9778
- import chalk99 from "chalk";
9944
+ import chalk101 from "chalk";
9779
9945
  async function sloc(pattern2 = "**/*.ts", options2 = {}) {
9780
9946
  withSourceFiles(pattern2, (files) => {
9781
9947
  const results = [];
@@ -9791,12 +9957,12 @@ async function sloc(pattern2 = "**/*.ts", options2 = {}) {
9791
9957
  results.sort((a, b) => b.lines - a.lines);
9792
9958
  for (const { file, lines } of results) {
9793
9959
  const exceedsThreshold = options2.threshold !== void 0 && lines > options2.threshold;
9794
- const color = exceedsThreshold ? chalk99.red : chalk99.white;
9795
- console.log(`${color(file)} \u2192 ${chalk99.cyan(lines)} lines`);
9960
+ const color = exceedsThreshold ? chalk101.red : chalk101.white;
9961
+ console.log(`${color(file)} \u2192 ${chalk101.cyan(lines)} lines`);
9796
9962
  }
9797
9963
  const total = results.reduce((sum, r) => sum + r.lines, 0);
9798
9964
  console.log(
9799
- chalk99.dim(`
9965
+ chalk101.dim(`
9800
9966
  Total: ${total} lines across ${files.length} files`)
9801
9967
  );
9802
9968
  if (hasViolation) {
@@ -9810,25 +9976,25 @@ async function analyze(pattern2) {
9810
9976
  const searchPattern = pattern2.includes("*") || pattern2.includes("/") ? pattern2 : `**/${pattern2}`;
9811
9977
  const files = findSourceFiles2(searchPattern);
9812
9978
  if (files.length === 0) {
9813
- console.log(chalk100.yellow("No files found matching pattern"));
9979
+ console.log(chalk102.yellow("No files found matching pattern"));
9814
9980
  return;
9815
9981
  }
9816
9982
  if (files.length === 1) {
9817
9983
  const file = files[0];
9818
- console.log(chalk100.bold.underline("SLOC"));
9984
+ console.log(chalk102.bold.underline("SLOC"));
9819
9985
  await sloc(file);
9820
9986
  console.log();
9821
- console.log(chalk100.bold.underline("Cyclomatic Complexity"));
9987
+ console.log(chalk102.bold.underline("Cyclomatic Complexity"));
9822
9988
  await cyclomatic(file);
9823
9989
  console.log();
9824
- console.log(chalk100.bold.underline("Halstead Metrics"));
9990
+ console.log(chalk102.bold.underline("Halstead Metrics"));
9825
9991
  await halstead(file);
9826
9992
  console.log();
9827
- console.log(chalk100.bold.underline("Maintainability Index"));
9993
+ console.log(chalk102.bold.underline("Maintainability Index"));
9828
9994
  await maintainability(file);
9829
9995
  console.log();
9830
9996
  console.log(
9831
- chalk100.dim(
9997
+ chalk102.dim(
9832
9998
  "To improve the maintainability index, extract functions and logic out of this file into separate, smaller modules. Collapsing whitespace or removing comments is not the goal."
9833
9999
  )
9834
10000
  );
@@ -9862,7 +10028,7 @@ function registerComplexity(program2) {
9862
10028
  }
9863
10029
 
9864
10030
  // src/commands/config/index.ts
9865
- import chalk101 from "chalk";
10031
+ import chalk103 from "chalk";
9866
10032
  import { stringify as stringifyYaml2 } from "yaml";
9867
10033
 
9868
10034
  // src/commands/config/setNestedValue.ts
@@ -9925,7 +10091,7 @@ function formatIssuePath(issue, key) {
9925
10091
  function printValidationErrors(issues, key) {
9926
10092
  for (const issue of issues) {
9927
10093
  console.error(
9928
- chalk101.red(`${formatIssuePath(issue, key)}: ${issue.message}`)
10094
+ chalk103.red(`${formatIssuePath(issue, key)}: ${issue.message}`)
9929
10095
  );
9930
10096
  }
9931
10097
  }
@@ -9942,7 +10108,7 @@ var GLOBAL_ONLY_KEYS = ["sync.autoConfirm"];
9942
10108
  function assertNotGlobalOnly(key, global) {
9943
10109
  if (!global && GLOBAL_ONLY_KEYS.some((k) => key.startsWith(k))) {
9944
10110
  console.error(
9945
- chalk101.red(
10111
+ chalk103.red(
9946
10112
  `"${key}" is a global-only key. Use --global to set it in ~/.assist.yml`
9947
10113
  )
9948
10114
  );
@@ -9965,7 +10131,7 @@ function configSet(key, value, options2 = {}) {
9965
10131
  applyConfigSet(key, coerced, options2.global ?? false);
9966
10132
  const target = options2.global ? "global" : "project";
9967
10133
  console.log(
9968
- chalk101.green(`Set ${key} = ${JSON.stringify(coerced)} (${target})`)
10134
+ chalk103.green(`Set ${key} = ${JSON.stringify(coerced)} (${target})`)
9969
10135
  );
9970
10136
  }
9971
10137
  function configList() {
@@ -9974,7 +10140,7 @@ function configList() {
9974
10140
  }
9975
10141
 
9976
10142
  // src/commands/config/configGet.ts
9977
- import chalk102 from "chalk";
10143
+ import chalk104 from "chalk";
9978
10144
 
9979
10145
  // src/commands/config/getNestedValue.ts
9980
10146
  function isTraversable(value) {
@@ -10006,7 +10172,7 @@ function requireNestedValue(config, key) {
10006
10172
  return value;
10007
10173
  }
10008
10174
  function exitKeyNotSet(key) {
10009
- console.error(chalk102.red(`Key "${key}" is not set`));
10175
+ console.error(chalk104.red(`Key "${key}" is not set`));
10010
10176
  process.exit(1);
10011
10177
  }
10012
10178
 
@@ -10019,8 +10185,8 @@ function registerConfig(program2) {
10019
10185
  }
10020
10186
 
10021
10187
  // src/commands/deploy/redirect.ts
10022
- import { existsSync as existsSync27, readFileSync as readFileSync22, writeFileSync as writeFileSync22 } from "fs";
10023
- import chalk103 from "chalk";
10188
+ import { existsSync as existsSync28, readFileSync as readFileSync23, writeFileSync as writeFileSync24 } from "fs";
10189
+ import chalk105 from "chalk";
10024
10190
  var TRAILING_SLASH_SCRIPT = ` <script>
10025
10191
  if (!window.location.pathname.endsWith('/')) {
10026
10192
  window.location.href = \`\${window.location.pathname}/\${window.location.search}\${window.location.hash}\`;
@@ -10028,24 +10194,24 @@ var TRAILING_SLASH_SCRIPT = ` <script>
10028
10194
  </script>`;
10029
10195
  function redirect() {
10030
10196
  const indexPath = "index.html";
10031
- if (!existsSync27(indexPath)) {
10032
- console.log(chalk103.yellow("No index.html found"));
10197
+ if (!existsSync28(indexPath)) {
10198
+ console.log(chalk105.yellow("No index.html found"));
10033
10199
  return;
10034
10200
  }
10035
- const content = readFileSync22(indexPath, "utf8");
10201
+ const content = readFileSync23(indexPath, "utf8");
10036
10202
  if (content.includes("window.location.pathname.endsWith('/')")) {
10037
- console.log(chalk103.dim("Trailing slash script already present"));
10203
+ console.log(chalk105.dim("Trailing slash script already present"));
10038
10204
  return;
10039
10205
  }
10040
10206
  const headCloseIndex = content.indexOf("</head>");
10041
10207
  if (headCloseIndex === -1) {
10042
- console.log(chalk103.red("Could not find </head> tag in index.html"));
10208
+ console.log(chalk105.red("Could not find </head> tag in index.html"));
10043
10209
  return;
10044
10210
  }
10045
10211
  const newContent = `${content.slice(0, headCloseIndex) + TRAILING_SLASH_SCRIPT}
10046
10212
  ${content.slice(headCloseIndex)}`;
10047
- writeFileSync22(indexPath, newContent);
10048
- console.log(chalk103.green("Added trailing slash redirect to index.html"));
10213
+ writeFileSync24(indexPath, newContent);
10214
+ console.log(chalk105.green("Added trailing slash redirect to index.html"));
10049
10215
  }
10050
10216
 
10051
10217
  // src/commands/registerDeploy.ts
@@ -10060,11 +10226,11 @@ import { execFileSync as execFileSync2 } from "child_process";
10060
10226
  import { basename as basename4 } from "path";
10061
10227
 
10062
10228
  // src/commands/devlog/loadBlogSkipDays.ts
10063
- import { homedir as homedir11 } from "os";
10064
- import { join as join25 } from "path";
10065
- var BLOG_REPO_ROOT = join25(homedir11(), "git/blog");
10229
+ import { homedir as homedir12 } from "os";
10230
+ import { join as join27 } from "path";
10231
+ var BLOG_REPO_ROOT = join27(homedir12(), "git/blog");
10066
10232
  function loadBlogSkipDays(repoName) {
10067
- const config = loadRawYaml(join25(BLOG_REPO_ROOT, "assist.yml"));
10233
+ const config = loadRawYaml(join27(BLOG_REPO_ROOT, "assist.yml"));
10068
10234
  const devlog = config.devlog;
10069
10235
  const skip2 = devlog?.skip;
10070
10236
  return new Set(skip2?.[repoName]);
@@ -10072,20 +10238,20 @@ function loadBlogSkipDays(repoName) {
10072
10238
 
10073
10239
  // src/commands/devlog/shared.ts
10074
10240
  import { execSync as execSync23 } from "child_process";
10075
- import chalk104 from "chalk";
10241
+ import chalk106 from "chalk";
10076
10242
 
10077
10243
  // src/shared/getRepoName.ts
10078
- import { existsSync as existsSync28, readFileSync as readFileSync23 } from "fs";
10079
- import { basename as basename3, join as join26 } from "path";
10244
+ import { existsSync as existsSync29, readFileSync as readFileSync24 } from "fs";
10245
+ import { basename as basename3, join as join28 } from "path";
10080
10246
  function getRepoName() {
10081
10247
  const config = loadConfig();
10082
10248
  if (config.devlog?.name) {
10083
10249
  return config.devlog.name;
10084
10250
  }
10085
- const packageJsonPath = join26(process.cwd(), "package.json");
10086
- if (existsSync28(packageJsonPath)) {
10251
+ const packageJsonPath = join28(process.cwd(), "package.json");
10252
+ if (existsSync29(packageJsonPath)) {
10087
10253
  try {
10088
- const content = readFileSync23(packageJsonPath, "utf8");
10254
+ const content = readFileSync24(packageJsonPath, "utf8");
10089
10255
  const pkg = JSON.parse(content);
10090
10256
  if (pkg.name) {
10091
10257
  return pkg.name;
@@ -10097,9 +10263,9 @@ function getRepoName() {
10097
10263
  }
10098
10264
 
10099
10265
  // src/commands/devlog/loadDevlogEntries.ts
10100
- import { readdirSync, readFileSync as readFileSync24 } from "fs";
10101
- import { join as join27 } from "path";
10102
- var DEVLOG_DIR = join27(BLOG_REPO_ROOT, "src/content/devlog");
10266
+ import { readdirSync as readdirSync2, readFileSync as readFileSync25 } from "fs";
10267
+ import { join as join29 } from "path";
10268
+ var DEVLOG_DIR = join29(BLOG_REPO_ROOT, "src/content/devlog");
10103
10269
  function extractFrontmatter(content) {
10104
10270
  const fm = content.match(/^---\n([\s\S]*?)\n---/);
10105
10271
  return fm?.[1] ?? null;
@@ -10125,9 +10291,9 @@ function parseFrontmatter(content, filename) {
10125
10291
  }
10126
10292
  function readDevlogFiles(callback) {
10127
10293
  try {
10128
- const files = readdirSync(DEVLOG_DIR).filter((f) => f.endsWith(".md"));
10294
+ const files = readdirSync2(DEVLOG_DIR).filter((f) => f.endsWith(".md"));
10129
10295
  for (const file of files) {
10130
- const content = readFileSync24(join27(DEVLOG_DIR, file), "utf8");
10296
+ const content = readFileSync25(join29(DEVLOG_DIR, file), "utf8");
10131
10297
  const parsed = parseFrontmatter(content, file);
10132
10298
  if (parsed) callback(parsed);
10133
10299
  }
@@ -10181,13 +10347,13 @@ function shouldIgnoreCommit(files, ignorePaths) {
10181
10347
  }
10182
10348
  function printCommitsWithFiles(commits2, ignore2, verbose) {
10183
10349
  for (const commit2 of commits2) {
10184
- console.log(` ${chalk104.yellow(commit2.hash)} ${commit2.message}`);
10350
+ console.log(` ${chalk106.yellow(commit2.hash)} ${commit2.message}`);
10185
10351
  if (verbose) {
10186
10352
  const visibleFiles = commit2.files.filter(
10187
10353
  (file) => !ignore2.some((p) => file.startsWith(p))
10188
10354
  );
10189
10355
  for (const file of visibleFiles) {
10190
- console.log(` ${chalk104.dim(file)}`);
10356
+ console.log(` ${chalk106.dim(file)}`);
10191
10357
  }
10192
10358
  }
10193
10359
  }
@@ -10212,15 +10378,15 @@ function parseGitLogCommits(output, ignore2, afterDate) {
10212
10378
  }
10213
10379
 
10214
10380
  // src/commands/devlog/list/printDateHeader.ts
10215
- import chalk105 from "chalk";
10381
+ import chalk107 from "chalk";
10216
10382
  function printDateHeader(date, isSkipped, entries) {
10217
10383
  if (isSkipped) {
10218
- console.log(`${chalk105.bold.blue(date)} ${chalk105.dim("skipped")}`);
10384
+ console.log(`${chalk107.bold.blue(date)} ${chalk107.dim("skipped")}`);
10219
10385
  } else if (entries && entries.length > 0) {
10220
- const entryInfo = entries.map((e) => `${chalk105.green(e.version)} ${e.title}`).join(" | ");
10221
- console.log(`${chalk105.bold.blue(date)} ${entryInfo}`);
10386
+ const entryInfo = entries.map((e) => `${chalk107.green(e.version)} ${e.title}`).join(" | ");
10387
+ console.log(`${chalk107.bold.blue(date)} ${entryInfo}`);
10222
10388
  } else {
10223
- console.log(`${chalk105.bold.blue(date)} ${chalk105.red("\u26A0 devlog missing")}`);
10389
+ console.log(`${chalk107.bold.blue(date)} ${chalk107.red("\u26A0 devlog missing")}`);
10224
10390
  }
10225
10391
  }
10226
10392
 
@@ -10324,24 +10490,24 @@ function bumpVersion(version2, type) {
10324
10490
 
10325
10491
  // src/commands/devlog/next/displayNextEntry/index.ts
10326
10492
  import { execFileSync as execFileSync4 } from "child_process";
10327
- import chalk107 from "chalk";
10493
+ import chalk109 from "chalk";
10328
10494
 
10329
10495
  // src/commands/devlog/next/displayNextEntry/displayVersion.ts
10330
- import chalk106 from "chalk";
10496
+ import chalk108 from "chalk";
10331
10497
  function displayVersion(conventional, firstHash, patchVersion, minorVersion) {
10332
10498
  if (conventional && firstHash) {
10333
10499
  const version2 = getVersionAtCommit(firstHash);
10334
10500
  if (version2) {
10335
- console.log(`${chalk106.bold("version:")} ${stripToMinor(version2)}`);
10501
+ console.log(`${chalk108.bold("version:")} ${stripToMinor(version2)}`);
10336
10502
  } else {
10337
- console.log(`${chalk106.bold("version:")} ${chalk106.red("unknown")}`);
10503
+ console.log(`${chalk108.bold("version:")} ${chalk108.red("unknown")}`);
10338
10504
  }
10339
10505
  } else if (patchVersion && minorVersion) {
10340
10506
  console.log(
10341
- `${chalk106.bold("version:")} ${patchVersion} (patch) or ${minorVersion} (minor)`
10507
+ `${chalk108.bold("version:")} ${patchVersion} (patch) or ${minorVersion} (minor)`
10342
10508
  );
10343
10509
  } else {
10344
- console.log(`${chalk106.bold("version:")} v0.1 (initial)`);
10510
+ console.log(`${chalk108.bold("version:")} v0.1 (initial)`);
10345
10511
  }
10346
10512
  }
10347
10513
 
@@ -10389,16 +10555,16 @@ function noCommitsMessage(hasLastInfo) {
10389
10555
  return hasLastInfo ? "No commits after last versioned entry" : "No commits found";
10390
10556
  }
10391
10557
  function logName(repoName) {
10392
- console.log(`${chalk107.bold("name:")} ${repoName}`);
10558
+ console.log(`${chalk109.bold("name:")} ${repoName}`);
10393
10559
  }
10394
10560
  function displayNextEntry(ctx, targetDate, commits2) {
10395
10561
  logName(ctx.repoName);
10396
10562
  printVersionInfo(ctx.config, ctx.lastInfo, commits2[0]?.hash);
10397
- console.log(chalk107.bold.blue(targetDate));
10563
+ console.log(chalk109.bold.blue(targetDate));
10398
10564
  printCommitsWithFiles(commits2, ctx.ignore, ctx.verbose);
10399
10565
  }
10400
10566
  function logNoCommits(lastInfo) {
10401
- console.log(chalk107.dim(noCommitsMessage(!!lastInfo)));
10567
+ console.log(chalk109.dim(noCommitsMessage(!!lastInfo)));
10402
10568
  }
10403
10569
 
10404
10570
  // src/commands/devlog/next/index.ts
@@ -10439,11 +10605,11 @@ function next2(options2) {
10439
10605
  import { execSync as execSync25 } from "child_process";
10440
10606
 
10441
10607
  // src/commands/devlog/repos/printReposTable.ts
10442
- import chalk108 from "chalk";
10608
+ import chalk110 from "chalk";
10443
10609
  function colorStatus(status2) {
10444
- if (status2 === "missing") return chalk108.red(status2);
10445
- if (status2 === "outdated") return chalk108.yellow(status2);
10446
- return chalk108.green(status2);
10610
+ if (status2 === "missing") return chalk110.red(status2);
10611
+ if (status2 === "outdated") return chalk110.yellow(status2);
10612
+ return chalk110.green(status2);
10447
10613
  }
10448
10614
  function formatRow(row, nameWidth) {
10449
10615
  const devlog = (row.lastDevlog ?? "-").padEnd(11);
@@ -10457,8 +10623,8 @@ function printReposTable(rows) {
10457
10623
  "Last Devlog".padEnd(11),
10458
10624
  "Status"
10459
10625
  ].join(" ");
10460
- console.log(chalk108.dim(header));
10461
- console.log(chalk108.dim("-".repeat(header.length)));
10626
+ console.log(chalk110.dim(header));
10627
+ console.log(chalk110.dim("-".repeat(header.length)));
10462
10628
  for (const row of rows) {
10463
10629
  console.log(formatRow(row, nameWidth));
10464
10630
  }
@@ -10514,16 +10680,16 @@ function repos(options2) {
10514
10680
  }
10515
10681
 
10516
10682
  // src/commands/devlog/skip.ts
10517
- import { writeFileSync as writeFileSync23 } from "fs";
10518
- import { join as join28 } from "path";
10519
- import chalk109 from "chalk";
10683
+ import { writeFileSync as writeFileSync25 } from "fs";
10684
+ import { join as join30 } from "path";
10685
+ import chalk111 from "chalk";
10520
10686
  import { stringify as stringifyYaml3 } from "yaml";
10521
10687
  function getBlogConfigPath() {
10522
- return join28(BLOG_REPO_ROOT, "assist.yml");
10688
+ return join30(BLOG_REPO_ROOT, "assist.yml");
10523
10689
  }
10524
10690
  function skip(date) {
10525
10691
  if (!/^\d{4}-\d{2}-\d{2}$/.test(date)) {
10526
- console.log(chalk109.red("Invalid date format. Use YYYY-MM-DD"));
10692
+ console.log(chalk111.red("Invalid date format. Use YYYY-MM-DD"));
10527
10693
  process.exit(1);
10528
10694
  }
10529
10695
  const repoName = getRepoName();
@@ -10534,7 +10700,7 @@ function skip(date) {
10534
10700
  const skipDays = skip2[repoName] ?? [];
10535
10701
  if (skipDays.includes(date)) {
10536
10702
  console.log(
10537
- chalk109.yellow(`${date} is already in skip list for ${repoName}`)
10703
+ chalk111.yellow(`${date} is already in skip list for ${repoName}`)
10538
10704
  );
10539
10705
  return;
10540
10706
  }
@@ -10543,21 +10709,21 @@ function skip(date) {
10543
10709
  skip2[repoName] = skipDays;
10544
10710
  devlog.skip = skip2;
10545
10711
  config.devlog = devlog;
10546
- writeFileSync23(configPath, stringifyYaml3(config, { lineWidth: 0 }));
10547
- console.log(chalk109.green(`Added ${date} to skip list for ${repoName}`));
10712
+ writeFileSync25(configPath, stringifyYaml3(config, { lineWidth: 0 }));
10713
+ console.log(chalk111.green(`Added ${date} to skip list for ${repoName}`));
10548
10714
  }
10549
10715
 
10550
10716
  // src/commands/devlog/version.ts
10551
- import chalk110 from "chalk";
10717
+ import chalk112 from "chalk";
10552
10718
  function version() {
10553
10719
  const config = loadConfig();
10554
10720
  const name = getRepoName();
10555
10721
  const lastInfo = getLastVersionInfo(name, config);
10556
10722
  const lastVersion = lastInfo?.version ?? null;
10557
10723
  const nextVersion = lastVersion ? bumpVersion(lastVersion, "patch") : null;
10558
- console.log(`${chalk110.bold("name:")} ${name}`);
10559
- console.log(`${chalk110.bold("last:")} ${lastVersion ?? chalk110.dim("none")}`);
10560
- console.log(`${chalk110.bold("next:")} ${nextVersion ?? chalk110.dim("none")}`);
10724
+ console.log(`${chalk112.bold("name:")} ${name}`);
10725
+ console.log(`${chalk112.bold("last:")} ${lastVersion ?? chalk112.dim("none")}`);
10726
+ console.log(`${chalk112.bold("next:")} ${nextVersion ?? chalk112.dim("none")}`);
10561
10727
  }
10562
10728
 
10563
10729
  // src/commands/registerDevlog.ts
@@ -10579,17 +10745,17 @@ function registerDevlog(program2) {
10579
10745
  }
10580
10746
 
10581
10747
  // src/commands/dotnet/checkBuildLocks.ts
10582
- import { closeSync as closeSync2, openSync as openSync2, readdirSync as readdirSync2 } from "fs";
10583
- import { join as join29 } from "path";
10584
- import chalk111 from "chalk";
10748
+ import { closeSync as closeSync2, openSync as openSync2, readdirSync as readdirSync3 } from "fs";
10749
+ import { join as join31 } from "path";
10750
+ import chalk113 from "chalk";
10585
10751
 
10586
10752
  // src/shared/findRepoRoot.ts
10587
- import { existsSync as existsSync29 } from "fs";
10753
+ import { existsSync as existsSync30 } from "fs";
10588
10754
  import path22 from "path";
10589
10755
  function findRepoRoot(dir) {
10590
10756
  let current = dir;
10591
10757
  while (current !== path22.dirname(current)) {
10592
- if (existsSync29(path22.join(current, ".git"))) {
10758
+ if (existsSync30(path22.join(current, ".git"))) {
10593
10759
  return current;
10594
10760
  }
10595
10761
  current = path22.dirname(current);
@@ -10602,13 +10768,13 @@ var SKIP_DIRS = /* @__PURE__ */ new Set(["node_modules", ".git", "packages"]);
10602
10768
  function isLockedDll(debugDir) {
10603
10769
  let files;
10604
10770
  try {
10605
- files = readdirSync2(debugDir, { recursive: true });
10771
+ files = readdirSync3(debugDir, { recursive: true });
10606
10772
  } catch {
10607
10773
  return null;
10608
10774
  }
10609
10775
  for (const file of files) {
10610
10776
  if (!file.toLowerCase().endsWith(".dll")) continue;
10611
- const dllPath = join29(debugDir, file);
10777
+ const dllPath = join31(debugDir, file);
10612
10778
  try {
10613
10779
  const fd = openSync2(dllPath, "r+");
10614
10780
  closeSync2(fd);
@@ -10621,18 +10787,18 @@ function isLockedDll(debugDir) {
10621
10787
  function findFirstLockedDll(dir) {
10622
10788
  let entries;
10623
10789
  try {
10624
- entries = readdirSync2(dir);
10790
+ entries = readdirSync3(dir);
10625
10791
  } catch {
10626
10792
  return null;
10627
10793
  }
10628
10794
  if (entries.includes("bin")) {
10629
- const locked = isLockedDll(join29(dir, "bin", "Debug"));
10795
+ const locked = isLockedDll(join31(dir, "bin", "Debug"));
10630
10796
  if (locked) return locked;
10631
10797
  }
10632
10798
  for (const entry of entries) {
10633
10799
  if (SKIP_DIRS.has(entry) || entry === "bin" || entry.startsWith("."))
10634
10800
  continue;
10635
- const found = findFirstLockedDll(join29(dir, entry));
10801
+ const found = findFirstLockedDll(join31(dir, entry));
10636
10802
  if (found) return found;
10637
10803
  }
10638
10804
  return null;
@@ -10644,22 +10810,22 @@ function checkBuildLocks(startDir) {
10644
10810
  const locked = findFirstLockedDll(startDir ?? getSearchRoot());
10645
10811
  if (locked) {
10646
10812
  console.error(
10647
- chalk111.red("Build output locked (is VS debugging?): ") + locked
10813
+ chalk113.red("Build output locked (is VS debugging?): ") + locked
10648
10814
  );
10649
10815
  process.exit(1);
10650
10816
  }
10651
10817
  }
10652
10818
  async function checkBuildLocksCommand() {
10653
10819
  checkBuildLocks();
10654
- console.log(chalk111.green("No build locks detected"));
10820
+ console.log(chalk113.green("No build locks detected"));
10655
10821
  }
10656
10822
 
10657
10823
  // src/commands/dotnet/buildTree.ts
10658
- import { readFileSync as readFileSync25 } from "fs";
10824
+ import { readFileSync as readFileSync26 } from "fs";
10659
10825
  import path23 from "path";
10660
10826
  var PROJECT_REF_RE = /<ProjectReference\s+Include="([^"]+)"/g;
10661
10827
  function getProjectRefs(csprojPath) {
10662
- const content = readFileSync25(csprojPath, "utf8");
10828
+ const content = readFileSync26(csprojPath, "utf8");
10663
10829
  const refs = [];
10664
10830
  for (const match of content.matchAll(PROJECT_REF_RE)) {
10665
10831
  refs.push(match[1].replace(/\\/g, "/"));
@@ -10676,7 +10842,7 @@ function buildTree(csprojPath, repoRoot, visited = /* @__PURE__ */ new Set()) {
10676
10842
  for (const ref of getProjectRefs(abs)) {
10677
10843
  const childAbs = path23.resolve(dir, ref);
10678
10844
  try {
10679
- readFileSync25(childAbs);
10845
+ readFileSync26(childAbs);
10680
10846
  node.children.push(buildTree(childAbs, repoRoot, visited));
10681
10847
  } catch {
10682
10848
  node.children.push({
@@ -10701,14 +10867,14 @@ function collectAllDeps(node) {
10701
10867
  }
10702
10868
 
10703
10869
  // src/commands/dotnet/findContainingSolutions.ts
10704
- import { readdirSync as readdirSync3, readFileSync as readFileSync26, statSync as statSync2 } from "fs";
10870
+ import { readdirSync as readdirSync4, readFileSync as readFileSync27, statSync as statSync3 } from "fs";
10705
10871
  import path24 from "path";
10706
10872
  function findSlnFiles(dir, maxDepth, depth = 0) {
10707
10873
  if (depth > maxDepth) return [];
10708
10874
  const results = [];
10709
10875
  let entries;
10710
10876
  try {
10711
- entries = readdirSync3(dir);
10877
+ entries = readdirSync4(dir);
10712
10878
  } catch {
10713
10879
  return results;
10714
10880
  }
@@ -10717,7 +10883,7 @@ function findSlnFiles(dir, maxDepth, depth = 0) {
10717
10883
  continue;
10718
10884
  const full = path24.join(dir, entry);
10719
10885
  try {
10720
- const stat2 = statSync2(full);
10886
+ const stat2 = statSync3(full);
10721
10887
  if (stat2.isFile() && entry.endsWith(".sln")) {
10722
10888
  results.push(full);
10723
10889
  } else if (stat2.isDirectory()) {
@@ -10736,7 +10902,7 @@ function findContainingSolutions(csprojPath, repoRoot) {
10736
10902
  const pattern2 = new RegExp(`[\\\\"/]${escapeRegex(csprojBasename)}"`);
10737
10903
  for (const sln of slnFiles) {
10738
10904
  try {
10739
- const content = readFileSync26(sln, "utf8");
10905
+ const content = readFileSync27(sln, "utf8");
10740
10906
  if (pattern2.test(content)) {
10741
10907
  matches.push(path24.relative(repoRoot, sln));
10742
10908
  }
@@ -10750,30 +10916,30 @@ function escapeRegex(s) {
10750
10916
  }
10751
10917
 
10752
10918
  // src/commands/dotnet/printTree.ts
10753
- import chalk112 from "chalk";
10919
+ import chalk114 from "chalk";
10754
10920
  function printNodes(nodes, prefix2) {
10755
10921
  for (let i = 0; i < nodes.length; i++) {
10756
10922
  const isLast = i === nodes.length - 1;
10757
10923
  const connector = isLast ? "\u2514\u2500\u2500 " : "\u251C\u2500\u2500 ";
10758
10924
  const childPrefix = isLast ? " " : "\u2502 ";
10759
10925
  const isMissing = nodes[i].relativePath.startsWith("[MISSING]");
10760
- const label2 = isMissing ? chalk112.red(nodes[i].relativePath) : nodes[i].relativePath;
10926
+ const label2 = isMissing ? chalk114.red(nodes[i].relativePath) : nodes[i].relativePath;
10761
10927
  console.log(`${prefix2}${connector}${label2}`);
10762
10928
  printNodes(nodes[i].children, prefix2 + childPrefix);
10763
10929
  }
10764
10930
  }
10765
10931
  function printTree(tree, totalCount, solutions) {
10766
- console.log(chalk112.bold("\nProject Dependency Tree"));
10767
- console.log(chalk112.cyan(tree.relativePath));
10932
+ console.log(chalk114.bold("\nProject Dependency Tree"));
10933
+ console.log(chalk114.cyan(tree.relativePath));
10768
10934
  printNodes(tree.children, "");
10769
- console.log(chalk112.dim(`
10935
+ console.log(chalk114.dim(`
10770
10936
  ${totalCount} projects total (including root)`));
10771
- console.log(chalk112.bold("\nSolution Membership"));
10937
+ console.log(chalk114.bold("\nSolution Membership"));
10772
10938
  if (solutions.length === 0) {
10773
- console.log(chalk112.yellow(" Not found in any .sln"));
10939
+ console.log(chalk114.yellow(" Not found in any .sln"));
10774
10940
  } else {
10775
10941
  for (const sln of solutions) {
10776
- console.log(` ${chalk112.green(sln)}`);
10942
+ console.log(` ${chalk114.green(sln)}`);
10777
10943
  }
10778
10944
  }
10779
10945
  console.log();
@@ -10800,18 +10966,18 @@ function printJson(tree, totalCount, solutions) {
10800
10966
  }
10801
10967
 
10802
10968
  // src/commands/dotnet/resolveCsproj.ts
10803
- import { existsSync as existsSync30 } from "fs";
10969
+ import { existsSync as existsSync31 } from "fs";
10804
10970
  import path25 from "path";
10805
- import chalk113 from "chalk";
10971
+ import chalk115 from "chalk";
10806
10972
  function resolveCsproj(csprojPath) {
10807
10973
  const resolved = path25.resolve(csprojPath);
10808
- if (!existsSync30(resolved)) {
10809
- console.error(chalk113.red(`File not found: ${resolved}`));
10974
+ if (!existsSync31(resolved)) {
10975
+ console.error(chalk115.red(`File not found: ${resolved}`));
10810
10976
  process.exit(1);
10811
10977
  }
10812
10978
  const repoRoot = findRepoRoot(path25.dirname(resolved));
10813
10979
  if (!repoRoot) {
10814
- console.error(chalk113.red("Could not find git repository root"));
10980
+ console.error(chalk115.red("Could not find git repository root"));
10815
10981
  process.exit(1);
10816
10982
  }
10817
10983
  return { resolved, repoRoot };
@@ -10861,12 +11027,12 @@ function getChangedCsFiles(scope) {
10861
11027
  }
10862
11028
 
10863
11029
  // src/commands/dotnet/inSln.ts
10864
- import chalk114 from "chalk";
11030
+ import chalk116 from "chalk";
10865
11031
  async function inSln(csprojPath) {
10866
11032
  const { resolved, repoRoot } = resolveCsproj(csprojPath);
10867
11033
  const solutions = findContainingSolutions(resolved, repoRoot);
10868
11034
  if (solutions.length === 0) {
10869
- console.log(chalk114.yellow("Not found in any .sln file"));
11035
+ console.log(chalk116.yellow("Not found in any .sln file"));
10870
11036
  process.exit(1);
10871
11037
  }
10872
11038
  for (const sln of solutions) {
@@ -10875,7 +11041,7 @@ async function inSln(csprojPath) {
10875
11041
  }
10876
11042
 
10877
11043
  // src/commands/dotnet/inspect.ts
10878
- import chalk120 from "chalk";
11044
+ import chalk122 from "chalk";
10879
11045
 
10880
11046
  // src/shared/formatElapsed.ts
10881
11047
  function formatElapsed(ms) {
@@ -10887,12 +11053,12 @@ function formatElapsed(ms) {
10887
11053
  }
10888
11054
 
10889
11055
  // src/commands/dotnet/displayIssues.ts
10890
- import chalk115 from "chalk";
11056
+ import chalk117 from "chalk";
10891
11057
  var SEVERITY_COLOR = {
10892
- ERROR: chalk115.red,
10893
- WARNING: chalk115.yellow,
10894
- SUGGESTION: chalk115.cyan,
10895
- HINT: chalk115.dim
11058
+ ERROR: chalk117.red,
11059
+ WARNING: chalk117.yellow,
11060
+ SUGGESTION: chalk117.cyan,
11061
+ HINT: chalk117.dim
10896
11062
  };
10897
11063
  function groupByFile(issues) {
10898
11064
  const byFile = /* @__PURE__ */ new Map();
@@ -10908,15 +11074,15 @@ function groupByFile(issues) {
10908
11074
  }
10909
11075
  function displayIssues(issues) {
10910
11076
  for (const [file, fileIssues] of groupByFile(issues)) {
10911
- console.log(chalk115.bold(file));
11077
+ console.log(chalk117.bold(file));
10912
11078
  for (const issue of fileIssues.sort((a, b) => a.line - b.line)) {
10913
- const color = SEVERITY_COLOR[issue.severity] ?? chalk115.white;
11079
+ const color = SEVERITY_COLOR[issue.severity] ?? chalk117.white;
10914
11080
  console.log(
10915
- ` ${chalk115.dim(`${issue.line}:`)} ${color(issue.severity)} [${issue.typeId}] ${issue.message}`
11081
+ ` ${chalk117.dim(`${issue.line}:`)} ${color(issue.severity)} [${issue.typeId}] ${issue.message}`
10916
11082
  );
10917
11083
  }
10918
11084
  }
10919
- console.log(chalk115.dim(`
11085
+ console.log(chalk117.dim(`
10920
11086
  ${issues.length} issue(s) found`));
10921
11087
  }
10922
11088
 
@@ -10973,17 +11139,17 @@ function filterIssues(issues, all, cliOnly, cliSuppress) {
10973
11139
  }
10974
11140
 
10975
11141
  // src/commands/dotnet/resolveSolution.ts
10976
- import { existsSync as existsSync31 } from "fs";
11142
+ import { existsSync as existsSync32 } from "fs";
10977
11143
  import path26 from "path";
10978
- import chalk117 from "chalk";
11144
+ import chalk119 from "chalk";
10979
11145
 
10980
11146
  // src/commands/dotnet/findSolution.ts
10981
- import { readdirSync as readdirSync4 } from "fs";
10982
- import { dirname as dirname18, join as join30 } from "path";
10983
- import chalk116 from "chalk";
11147
+ import { readdirSync as readdirSync5 } from "fs";
11148
+ import { dirname as dirname18, join as join32 } from "path";
11149
+ import chalk118 from "chalk";
10984
11150
  function findSlnInDir(dir) {
10985
11151
  try {
10986
- return readdirSync4(dir).filter((f) => f.endsWith(".sln")).map((f) => join30(dir, f));
11152
+ return readdirSync5(dir).filter((f) => f.endsWith(".sln")).map((f) => join32(dir, f));
10987
11153
  } catch {
10988
11154
  return [];
10989
11155
  }
@@ -10996,17 +11162,17 @@ function findSolution() {
10996
11162
  const slnFiles = findSlnInDir(current);
10997
11163
  if (slnFiles.length === 1) return slnFiles[0];
10998
11164
  if (slnFiles.length > 1) {
10999
- console.error(chalk116.red(`Multiple .sln files found in ${current}:`));
11165
+ console.error(chalk118.red(`Multiple .sln files found in ${current}:`));
11000
11166
  for (const f of slnFiles) console.error(` ${f}`);
11001
11167
  console.error(
11002
- chalk116.yellow("Specify which one: assist dotnet inspect <sln>")
11168
+ chalk118.yellow("Specify which one: assist dotnet inspect <sln>")
11003
11169
  );
11004
11170
  process.exit(1);
11005
11171
  }
11006
11172
  if (current === ceiling) break;
11007
11173
  current = dirname18(current);
11008
11174
  }
11009
- console.error(chalk116.red("No .sln file found between cwd and repo root"));
11175
+ console.error(chalk118.red("No .sln file found between cwd and repo root"));
11010
11176
  process.exit(1);
11011
11177
  }
11012
11178
 
@@ -11014,8 +11180,8 @@ function findSolution() {
11014
11180
  function resolveSolution(sln) {
11015
11181
  if (sln) {
11016
11182
  const resolved = path26.resolve(sln);
11017
- if (!existsSync31(resolved)) {
11018
- console.error(chalk117.red(`Solution file not found: ${resolved}`));
11183
+ if (!existsSync32(resolved)) {
11184
+ console.error(chalk119.red(`Solution file not found: ${resolved}`));
11019
11185
  process.exit(1);
11020
11186
  }
11021
11187
  return resolved;
@@ -11054,17 +11220,17 @@ function parseInspectReport(json) {
11054
11220
 
11055
11221
  // src/commands/dotnet/runInspectCode.ts
11056
11222
  import { execSync as execSync27 } from "child_process";
11057
- import { existsSync as existsSync32, readFileSync as readFileSync27, unlinkSync as unlinkSync7 } from "fs";
11223
+ import { existsSync as existsSync33, readFileSync as readFileSync28, unlinkSync as unlinkSync9 } from "fs";
11058
11224
  import { tmpdir as tmpdir3 } from "os";
11059
11225
  import path27 from "path";
11060
- import chalk118 from "chalk";
11226
+ import chalk120 from "chalk";
11061
11227
  function assertJbInstalled() {
11062
11228
  try {
11063
11229
  execSync27("jb inspectcode --version", { stdio: "pipe" });
11064
11230
  } catch {
11065
- console.error(chalk118.red("jb is not installed. Install with:"));
11231
+ console.error(chalk120.red("jb is not installed. Install with:"));
11066
11232
  console.error(
11067
- chalk118.yellow(" dotnet tool install -g JetBrains.ReSharper.GlobalTools")
11233
+ chalk120.yellow(" dotnet tool install -g JetBrains.ReSharper.GlobalTools")
11068
11234
  );
11069
11235
  process.exit(1);
11070
11236
  }
@@ -11082,21 +11248,21 @@ function runInspectCode(slnPath, include, swea) {
11082
11248
  if (error && typeof error === "object" && "stderr" in error) {
11083
11249
  process.stderr.write(error.stderr);
11084
11250
  }
11085
- console.error(chalk118.red("jb inspectcode failed"));
11251
+ console.error(chalk120.red("jb inspectcode failed"));
11086
11252
  process.exit(1);
11087
11253
  }
11088
- if (!existsSync32(reportPath)) {
11089
- console.error(chalk118.red("Report file not generated"));
11254
+ if (!existsSync33(reportPath)) {
11255
+ console.error(chalk120.red("Report file not generated"));
11090
11256
  process.exit(1);
11091
11257
  }
11092
- const xml = readFileSync27(reportPath, "utf8");
11093
- unlinkSync7(reportPath);
11258
+ const xml = readFileSync28(reportPath, "utf8");
11259
+ unlinkSync9(reportPath);
11094
11260
  return xml;
11095
11261
  }
11096
11262
 
11097
11263
  // src/commands/dotnet/runRoslynInspect.ts
11098
11264
  import { execSync as execSync28 } from "child_process";
11099
- import chalk119 from "chalk";
11265
+ import chalk121 from "chalk";
11100
11266
  function resolveMsbuildPath() {
11101
11267
  const { run: run4 } = loadConfig();
11102
11268
  const configs = resolveRunConfigs(run4, getConfigDir());
@@ -11108,9 +11274,9 @@ function assertMsbuildInstalled() {
11108
11274
  try {
11109
11275
  execSync28(`"${msbuild}" -version`, { stdio: "pipe" });
11110
11276
  } catch {
11111
- console.error(chalk119.red(`msbuild not found at: ${msbuild}`));
11277
+ console.error(chalk121.red(`msbuild not found at: ${msbuild}`));
11112
11278
  console.error(
11113
- chalk119.yellow(
11279
+ chalk121.yellow(
11114
11280
  "Configure it via a 'build' run entry in .claude/assist.yml or add msbuild to PATH."
11115
11281
  )
11116
11282
  );
@@ -11157,17 +11323,17 @@ function runEngine(resolved, changedFiles, options2) {
11157
11323
  // src/commands/dotnet/inspect.ts
11158
11324
  function logScope(changedFiles) {
11159
11325
  if (changedFiles === null) {
11160
- console.log(chalk120.dim("Inspecting full solution..."));
11326
+ console.log(chalk122.dim("Inspecting full solution..."));
11161
11327
  } else {
11162
11328
  console.log(
11163
- chalk120.dim(`Inspecting ${changedFiles.length} changed file(s)...`)
11329
+ chalk122.dim(`Inspecting ${changedFiles.length} changed file(s)...`)
11164
11330
  );
11165
11331
  }
11166
11332
  }
11167
11333
  function reportResults(issues, elapsed) {
11168
11334
  if (issues.length > 0) displayIssues(issues);
11169
- else console.log(chalk120.green("No issues found"));
11170
- console.log(chalk120.dim(`Completed in ${formatElapsed(elapsed)}`));
11335
+ else console.log(chalk122.green("No issues found"));
11336
+ console.log(chalk122.dim(`Completed in ${formatElapsed(elapsed)}`));
11171
11337
  if (issues.length > 0) process.exit(1);
11172
11338
  }
11173
11339
  async function inspect(sln, options2) {
@@ -11178,7 +11344,7 @@ async function inspect(sln, options2) {
11178
11344
  const scope = parseScope(options2.scope);
11179
11345
  const changedFiles = getChangedCsFiles(scope);
11180
11346
  if (changedFiles !== null && changedFiles.length === 0) {
11181
- console.log(chalk120.green("No changed .cs files found"));
11347
+ console.log(chalk122.green("No changed .cs files found"));
11182
11348
  return;
11183
11349
  }
11184
11350
  logScope(changedFiles);
@@ -11206,8 +11372,94 @@ function registerDotnet(program2) {
11206
11372
  // src/commands/editHook/index.ts
11207
11373
  import fs19 from "fs";
11208
11374
 
11375
+ // src/commands/editHook/extractComments.ts
11376
+ var SOURCE_EXTENSIONS2 = [
11377
+ ".ts",
11378
+ ".tsx",
11379
+ ".cts",
11380
+ ".mts",
11381
+ ".js",
11382
+ ".jsx",
11383
+ ".cjs",
11384
+ ".mjs"
11385
+ ];
11386
+ function isSourceFile(filePath) {
11387
+ if (!filePath) return false;
11388
+ return SOURCE_EXTENSIONS2.some((ext) => filePath.endsWith(ext));
11389
+ }
11390
+ function blankNonNewline(text6) {
11391
+ return text6.replace(/[^\n]/g, " ");
11392
+ }
11393
+ function extractComments(text6) {
11394
+ const comments3 = [];
11395
+ let work = text6.replace(
11396
+ /"(?:[^"\\]|\\.)*"|'(?:[^'\\]|\\.)*'|`(?:[^`\\]|\\.)*`/g,
11397
+ blankNonNewline
11398
+ );
11399
+ work = work.replace(/\/\*[\s\S]*?\*\//g, (match) => {
11400
+ comments3.push(match);
11401
+ return blankNonNewline(match);
11402
+ });
11403
+ for (const match of work.matchAll(/\/\/.*/g)) {
11404
+ comments3.push(match[0]);
11405
+ }
11406
+ return comments3.map((comment3) => comment3.replace(/\s+/g, " ").trim()).filter((comment3) => comment3.length > 0).filter((comment3) => !isCommentExempt(comment3));
11407
+ }
11408
+
11409
+ // src/commands/editHook/decideCommentGuard.ts
11410
+ var DENY_REASON = 'This edit introduces a code comment, which is blocked by the comment gate. Comments are a last resort \u2014 prefer a clearer name, a smaller function, or a test that makes the comment unnecessary. The comment must not appear in your edit itself. If this one line genuinely earns its keep, use the escape hatch: run `assist code-comment set <file> <line> "<text>"` (single line, max 50 chars, no block comments) to get a pin, then `assist code-comment confirm <pin>` to insert it.';
11411
+ function defined(values) {
11412
+ return values.filter((value) => value != null);
11413
+ }
11414
+ function partitionStrings(input, existingContent) {
11415
+ const { tool_name, tool_input } = input;
11416
+ switch (tool_name) {
11417
+ case "Edit":
11418
+ return {
11419
+ added: defined([tool_input.new_string]),
11420
+ removed: defined([tool_input.old_string])
11421
+ };
11422
+ case "MultiEdit": {
11423
+ const edits = tool_input.edits ?? [];
11424
+ return {
11425
+ added: defined(edits.map((e) => e.new_string)),
11426
+ removed: defined(edits.map((e) => e.old_string))
11427
+ };
11428
+ }
11429
+ case "Write":
11430
+ return {
11431
+ added: defined([tool_input.content]),
11432
+ removed: defined([existingContent])
11433
+ };
11434
+ default:
11435
+ return { added: [], removed: [] };
11436
+ }
11437
+ }
11438
+ function introducedComments(added, removed) {
11439
+ const counts = /* @__PURE__ */ new Map();
11440
+ for (const comment3 of removed) {
11441
+ counts.set(comment3, (counts.get(comment3) ?? 0) + 1);
11442
+ }
11443
+ const introduced = [];
11444
+ for (const comment3 of added) {
11445
+ const remaining = counts.get(comment3) ?? 0;
11446
+ if (remaining > 0) counts.set(comment3, remaining - 1);
11447
+ else introduced.push(comment3);
11448
+ }
11449
+ return introduced;
11450
+ }
11451
+ function decideCommentGuard(input, existingContent) {
11452
+ if (!isSourceFile(input.tool_input.file_path)) return void 0;
11453
+ const { added, removed } = partitionStrings(input, existingContent);
11454
+ const introduced = introducedComments(
11455
+ added.flatMap(extractComments),
11456
+ removed.flatMap(extractComments)
11457
+ );
11458
+ return introduced.length > 0 ? DENY_REASON : void 0;
11459
+ }
11460
+
11209
11461
  // src/commands/editHook/decideOverrideGuard.ts
11210
- var DENY_REASON = `Edits touching the '${MAINTAINABILITY_OVERRIDE_MARKER}' marker are blocked. This marker is a human-managed maintainability gate exception \u2014 an agent may not add, change, or remove it. If a file genuinely needs a different threshold, raise it with a human.`;
11462
+ var DENY_REASON2 = `Edits touching the '${MAINTAINABILITY_OVERRIDE_MARKER}' marker are blocked. This marker is a human-managed maintainability gate exception \u2014 an agent may not add, change, or remove it. If a file genuinely needs a different threshold, raise it with a human.`;
11211
11463
  function candidateStrings(input, existingContent) {
11212
11464
  const { tool_name, tool_input } = input;
11213
11465
  switch (tool_name) {
@@ -11233,7 +11485,7 @@ function decideOverrideGuard(input, existingContent) {
11233
11485
  const touchesMarker = candidateStrings(input, existingContent).some(
11234
11486
  (s) => s.includes(MAINTAINABILITY_OVERRIDE_MARKER)
11235
11487
  );
11236
- return touchesMarker ? DENY_REASON : void 0;
11488
+ return touchesMarker ? DENY_REASON2 : void 0;
11237
11489
  }
11238
11490
 
11239
11491
  // src/commands/editHook/index.ts
@@ -11259,7 +11511,7 @@ async function editHook() {
11259
11511
  const input = tryParseInput2(await readStdin());
11260
11512
  if (!input) return;
11261
11513
  const existing = input.tool_name === "Write" ? readExisting(input.tool_input.file_path) : void 0;
11262
- const reason = decideOverrideGuard(input, existing);
11514
+ const reason = decideOverrideGuard(input, existing) ?? decideCommentGuard(input, existing);
11263
11515
  if (!reason) return;
11264
11516
  console.log(
11265
11517
  JSON.stringify({
@@ -11275,7 +11527,7 @@ async function editHook() {
11275
11527
  // src/commands/registerEditHook.ts
11276
11528
  function registerEditHook(program2) {
11277
11529
  program2.command("edit-hook").description(
11278
- "PreToolUse hook that blocks edits to the maintainability override marker"
11530
+ "PreToolUse hook that blocks edits to the maintainability override marker and edits that introduce code comments"
11279
11531
  ).action(() => {
11280
11532
  editHook();
11281
11533
  });
@@ -11294,9 +11546,9 @@ function aggregateCommitters(authorLists) {
11294
11546
 
11295
11547
  // src/shared/runGhGraphql.ts
11296
11548
  import { spawnSync as spawnSync3 } from "child_process";
11297
- import { unlinkSync as unlinkSync8, writeFileSync as writeFileSync24 } from "fs";
11549
+ import { unlinkSync as unlinkSync10, writeFileSync as writeFileSync26 } from "fs";
11298
11550
  import { tmpdir as tmpdir4 } from "os";
11299
- import { join as join31 } from "path";
11551
+ import { join as join33 } from "path";
11300
11552
  function buildArgs2(queryFile, vars) {
11301
11553
  const args = ["api", "graphql", "-F", `query=@${queryFile}`];
11302
11554
  for (const [key, value] of Object.entries(vars)) {
@@ -11321,8 +11573,8 @@ function throwOnGraphqlErrors(stdout) {
11321
11573
  throw new Error(messages || "GraphQL request returned errors");
11322
11574
  }
11323
11575
  function runGhGraphql(mutation, vars) {
11324
- const queryFile = join31(tmpdir4(), `gh-query-${Date.now()}.graphql`);
11325
- writeFileSync24(queryFile, mutation);
11576
+ const queryFile = join33(tmpdir4(), `gh-query-${Date.now()}.graphql`);
11577
+ writeFileSync26(queryFile, mutation);
11326
11578
  try {
11327
11579
  const result = spawnSync3("gh", buildArgs2(queryFile, vars), {
11328
11580
  encoding: "utf8"
@@ -11331,7 +11583,7 @@ function runGhGraphql(mutation, vars) {
11331
11583
  throwOnGraphqlErrors(result.stdout);
11332
11584
  return result.stdout;
11333
11585
  } finally {
11334
- unlinkSync8(queryFile);
11586
+ unlinkSync10(queryFile);
11335
11587
  }
11336
11588
  }
11337
11589
 
@@ -11385,25 +11637,25 @@ function fetchRepoCommitAuthors(org, repo, since) {
11385
11637
  }
11386
11638
 
11387
11639
  // src/commands/github/printCountTable.ts
11388
- import chalk121 from "chalk";
11640
+ import chalk123 from "chalk";
11389
11641
  function printCountTable(labelHeader, rows) {
11390
11642
  const labelWidth = Math.max(
11391
11643
  labelHeader.length,
11392
11644
  ...rows.map((row) => row.label.length)
11393
11645
  );
11394
11646
  const header = `${labelHeader.padEnd(labelWidth)} Commits`;
11395
- console.log(chalk121.dim(header));
11396
- console.log(chalk121.dim("-".repeat(header.length)));
11647
+ console.log(chalk123.dim(header));
11648
+ console.log(chalk123.dim("-".repeat(header.length)));
11397
11649
  for (const row of rows) {
11398
11650
  console.log(`${row.label.padEnd(labelWidth)} ${row.count}`);
11399
11651
  }
11400
11652
  }
11401
11653
 
11402
11654
  // src/commands/github/printRepoAuthorBreakdown.ts
11403
- import chalk122 from "chalk";
11655
+ import chalk124 from "chalk";
11404
11656
  function printRepoAuthorBreakdown(repos2) {
11405
11657
  for (const repo of repos2) {
11406
- console.log(chalk122.bold(repo.name));
11658
+ console.log(chalk124.bold(repo.name));
11407
11659
  const authorWidth = Math.max(
11408
11660
  0,
11409
11661
  ...repo.authors.map((a) => a.author.length)
@@ -11508,24 +11760,24 @@ async function countPendingHandovers(orm, origin) {
11508
11760
 
11509
11761
  // src/commands/handover/migrateDiskHandovers.ts
11510
11762
  import {
11511
- existsSync as existsSync33,
11512
- readdirSync as readdirSync5,
11513
- readFileSync as readFileSync28,
11763
+ existsSync as existsSync34,
11764
+ readdirSync as readdirSync6,
11765
+ readFileSync as readFileSync29,
11514
11766
  rmSync as rmSync2,
11515
- statSync as statSync3
11767
+ statSync as statSync4
11516
11768
  } from "fs";
11517
- import { basename as basename5, join as join34 } from "path";
11769
+ import { basename as basename5, join as join36 } from "path";
11518
11770
 
11519
11771
  // src/commands/handover/getHandoverPath.ts
11520
- import { join as join32 } from "path";
11772
+ import { join as join34 } from "path";
11521
11773
  function getHandoverPath(cwd = process.cwd()) {
11522
- return join32(cwd, ".assist", "HANDOVER.md");
11774
+ return join34(cwd, ".assist", "HANDOVER.md");
11523
11775
  }
11524
11776
 
11525
11777
  // src/commands/handover/getHandoversDir.ts
11526
- import { join as join33 } from "path";
11778
+ import { join as join35 } from "path";
11527
11779
  function getHandoversDir(cwd = process.cwd()) {
11528
- return join33(cwd, ".assist", "handovers");
11780
+ return join35(cwd, ".assist", "handovers");
11529
11781
  }
11530
11782
 
11531
11783
  // src/commands/handover/parseArchiveTimestamp.ts
@@ -11563,17 +11815,17 @@ function summariseHandoverContent(content) {
11563
11815
 
11564
11816
  // src/commands/handover/migrateDiskHandovers.ts
11565
11817
  function collectMarkdown(dir) {
11566
- if (!existsSync33(dir)) return [];
11818
+ if (!existsSync34(dir)) return [];
11567
11819
  const out = [];
11568
- for (const entry of readdirSync5(dir, { withFileTypes: true })) {
11569
- const full = join34(dir, entry.name);
11820
+ for (const entry of readdirSync6(dir, { withFileTypes: true })) {
11821
+ const full = join36(dir, entry.name);
11570
11822
  if (entry.isDirectory()) out.push(...collectMarkdown(full));
11571
11823
  else if (entry.isFile() && entry.name.endsWith(".md")) out.push(full);
11572
11824
  }
11573
11825
  return out;
11574
11826
  }
11575
11827
  async function migrateFile(orm, origin, file, createdAt) {
11576
- const content = readFileSync28(file, "utf8");
11828
+ const content = readFileSync29(file, "utf8");
11577
11829
  await saveHandover(orm, {
11578
11830
  origin,
11579
11831
  summary: summariseHandoverContent(content),
@@ -11585,13 +11837,13 @@ async function migrateFile(orm, origin, file, createdAt) {
11585
11837
  async function migrateDiskHandovers(orm, origin, cwd = process.cwd()) {
11586
11838
  let migrated = 0;
11587
11839
  for (const file of collectMarkdown(getHandoversDir(cwd))) {
11588
- const createdAt = parseArchiveTimestamp(basename5(file)) ?? statSync3(file).mtime;
11840
+ const createdAt = parseArchiveTimestamp(basename5(file)) ?? statSync4(file).mtime;
11589
11841
  await migrateFile(orm, origin, file, createdAt);
11590
11842
  migrated++;
11591
11843
  }
11592
11844
  const handoverPath = getHandoverPath(cwd);
11593
- if (existsSync33(handoverPath)) {
11594
- await migrateFile(orm, origin, handoverPath, statSync3(handoverPath).mtime);
11845
+ if (existsSync34(handoverPath)) {
11846
+ await migrateFile(orm, origin, handoverPath, statSync4(handoverPath).mtime);
11595
11847
  migrated++;
11596
11848
  }
11597
11849
  return migrated;
@@ -11721,7 +11973,7 @@ function registerHandover(program2) {
11721
11973
  }
11722
11974
 
11723
11975
  // src/commands/jira/acceptanceCriteria.ts
11724
- import chalk124 from "chalk";
11976
+ import chalk126 from "chalk";
11725
11977
 
11726
11978
  // src/commands/jira/adfToText.ts
11727
11979
  function renderInline(node) {
@@ -11782,7 +12034,7 @@ function adfToText(doc) {
11782
12034
 
11783
12035
  // src/commands/jira/fetchIssue.ts
11784
12036
  import { execSync as execSync29 } from "child_process";
11785
- import chalk123 from "chalk";
12037
+ import chalk125 from "chalk";
11786
12038
  function fetchIssue(issueKey, fields) {
11787
12039
  let result;
11788
12040
  try {
@@ -11795,15 +12047,15 @@ function fetchIssue(issueKey, fields) {
11795
12047
  const stderr = error.stderr;
11796
12048
  if (stderr.includes("unauthorized")) {
11797
12049
  console.error(
11798
- chalk123.red("Jira authentication expired."),
12050
+ chalk125.red("Jira authentication expired."),
11799
12051
  "Run",
11800
- chalk123.cyan("assist jira auth"),
12052
+ chalk125.cyan("assist jira auth"),
11801
12053
  "to re-authenticate."
11802
12054
  );
11803
12055
  process.exit(1);
11804
12056
  }
11805
12057
  }
11806
- console.error(chalk123.red(`Failed to fetch ${issueKey}.`));
12058
+ console.error(chalk125.red(`Failed to fetch ${issueKey}.`));
11807
12059
  process.exit(1);
11808
12060
  }
11809
12061
  return JSON.parse(result);
@@ -11817,7 +12069,7 @@ function acceptanceCriteria(issueKey) {
11817
12069
  const parsed = fetchIssue(issueKey, field);
11818
12070
  const acValue = parsed?.fields?.[field];
11819
12071
  if (!acValue) {
11820
- console.log(chalk124.yellow(`No acceptance criteria found on ${issueKey}.`));
12072
+ console.log(chalk126.yellow(`No acceptance criteria found on ${issueKey}.`));
11821
12073
  return;
11822
12074
  }
11823
12075
  if (typeof acValue === "string") {
@@ -11835,20 +12087,20 @@ function acceptanceCriteria(issueKey) {
11835
12087
  import { execSync as execSync30 } from "child_process";
11836
12088
 
11837
12089
  // src/shared/loadJson.ts
11838
- import { existsSync as existsSync34, mkdirSync as mkdirSync11, readFileSync as readFileSync29, writeFileSync as writeFileSync25 } from "fs";
11839
- import { homedir as homedir12 } from "os";
11840
- import { join as join35 } from "path";
12090
+ import { existsSync as existsSync35, mkdirSync as mkdirSync12, readFileSync as readFileSync30, writeFileSync as writeFileSync27 } from "fs";
12091
+ import { homedir as homedir13 } from "os";
12092
+ import { join as join37 } from "path";
11841
12093
  function getStoreDir() {
11842
- return join35(homedir12(), ".assist");
12094
+ return join37(homedir13(), ".assist");
11843
12095
  }
11844
12096
  function getStorePath(filename) {
11845
- return join35(getStoreDir(), filename);
12097
+ return join37(getStoreDir(), filename);
11846
12098
  }
11847
12099
  function loadJson(filename) {
11848
12100
  const path57 = getStorePath(filename);
11849
- if (existsSync34(path57)) {
12101
+ if (existsSync35(path57)) {
11850
12102
  try {
11851
- return JSON.parse(readFileSync29(path57, "utf8"));
12103
+ return JSON.parse(readFileSync30(path57, "utf8"));
11852
12104
  } catch {
11853
12105
  return {};
11854
12106
  }
@@ -11857,10 +12109,10 @@ function loadJson(filename) {
11857
12109
  }
11858
12110
  function saveJson(filename, data) {
11859
12111
  const dir = getStoreDir();
11860
- if (!existsSync34(dir)) {
11861
- mkdirSync11(dir, { recursive: true });
12112
+ if (!existsSync35(dir)) {
12113
+ mkdirSync12(dir, { recursive: true });
11862
12114
  }
11863
- writeFileSync25(getStorePath(filename), JSON.stringify(data, null, 2));
12115
+ writeFileSync27(getStorePath(filename), JSON.stringify(data, null, 2));
11864
12116
  }
11865
12117
 
11866
12118
  // src/shared/promptInput.ts
@@ -11912,14 +12164,14 @@ async function jiraAuth() {
11912
12164
  }
11913
12165
 
11914
12166
  // src/commands/jira/viewIssue.ts
11915
- import chalk125 from "chalk";
12167
+ import chalk127 from "chalk";
11916
12168
  function viewIssue(issueKey) {
11917
12169
  const parsed = fetchIssue(issueKey, "summary,description");
11918
12170
  const fields = parsed?.fields;
11919
12171
  const summary = fields?.summary;
11920
12172
  const description = fields?.description;
11921
12173
  if (summary) {
11922
- console.log(chalk125.bold(summary));
12174
+ console.log(chalk127.bold(summary));
11923
12175
  }
11924
12176
  if (description) {
11925
12177
  if (summary) console.log();
@@ -11933,7 +12185,7 @@ function viewIssue(issueKey) {
11933
12185
  }
11934
12186
  if (!summary && !description) {
11935
12187
  console.log(
11936
- chalk125.yellow(`No summary or description found on ${issueKey}.`)
12188
+ chalk127.yellow(`No summary or description found on ${issueKey}.`)
11937
12189
  );
11938
12190
  }
11939
12191
  }
@@ -11949,13 +12201,13 @@ function registerJira(program2) {
11949
12201
  // src/commands/reviewComments.ts
11950
12202
  import { execFileSync as execFileSync5 } from "child_process";
11951
12203
  import { randomUUID as randomUUID3 } from "crypto";
11952
- import chalk126 from "chalk";
12204
+ import chalk128 from "chalk";
11953
12205
  async function reviewComments(number) {
11954
12206
  if (number) {
11955
12207
  try {
11956
12208
  execFileSync5("gh", ["pr", "checkout", number], { stdio: "inherit" });
11957
12209
  } catch {
11958
- console.error(chalk126.red(`gh pr checkout ${number} failed; aborting.`));
12210
+ console.error(chalk128.red(`gh pr checkout ${number} failed; aborting.`));
11959
12211
  process.exit(1);
11960
12212
  }
11961
12213
  }
@@ -11999,17 +12251,17 @@ function registerList(program2) {
11999
12251
  }
12000
12252
 
12001
12253
  // src/commands/mermaid/index.ts
12002
- import { mkdirSync as mkdirSync12, readdirSync as readdirSync6 } from "fs";
12254
+ import { mkdirSync as mkdirSync13, readdirSync as readdirSync7 } from "fs";
12003
12255
  import { resolve as resolve11 } from "path";
12004
- import chalk129 from "chalk";
12256
+ import chalk131 from "chalk";
12005
12257
 
12006
12258
  // src/commands/mermaid/exportFile.ts
12007
- import { readFileSync as readFileSync30, writeFileSync as writeFileSync26 } from "fs";
12259
+ import { readFileSync as readFileSync31, writeFileSync as writeFileSync28 } from "fs";
12008
12260
  import { basename as basename6, extname, resolve as resolve10 } from "path";
12009
- import chalk128 from "chalk";
12261
+ import chalk130 from "chalk";
12010
12262
 
12011
12263
  // src/commands/mermaid/renderBlock.ts
12012
- import chalk127 from "chalk";
12264
+ import chalk129 from "chalk";
12013
12265
  async function renderBlock(krokiUrl, source) {
12014
12266
  const response = await fetch(`${krokiUrl}/mermaid/svg`, {
12015
12267
  method: "POST",
@@ -12018,7 +12270,7 @@ async function renderBlock(krokiUrl, source) {
12018
12270
  });
12019
12271
  if (!response.ok) {
12020
12272
  console.error(
12021
- chalk127.red(
12273
+ chalk129.red(
12022
12274
  `Kroki request failed: ${response.status} ${response.statusText}`
12023
12275
  )
12024
12276
  );
@@ -12030,33 +12282,33 @@ async function renderBlock(krokiUrl, source) {
12030
12282
 
12031
12283
  // src/commands/mermaid/exportFile.ts
12032
12284
  async function exportFile(file, outDir, krokiUrl, onlyIndex) {
12033
- const content = readFileSync30(file, "utf8");
12285
+ const content = readFileSync31(file, "utf8");
12034
12286
  const blocks = extractMermaidBlocks(content);
12035
12287
  const stem = basename6(file, extname(file));
12036
12288
  if (onlyIndex !== void 0) {
12037
12289
  if (onlyIndex < 1 || onlyIndex > blocks.length) {
12038
12290
  console.error(
12039
- chalk128.red(
12291
+ chalk130.red(
12040
12292
  `${file}: --index ${onlyIndex} out of range (file has ${blocks.length} diagram(s))`
12041
12293
  )
12042
12294
  );
12043
12295
  process.exit(1);
12044
12296
  }
12045
12297
  console.log(
12046
- chalk128.gray(
12298
+ chalk130.gray(
12047
12299
  `${file} \u2014 rendering diagram ${onlyIndex} of ${blocks.length}`
12048
12300
  )
12049
12301
  );
12050
12302
  } else {
12051
- console.log(chalk128.gray(`${file} \u2014 ${blocks.length} diagram(s)`));
12303
+ console.log(chalk130.gray(`${file} \u2014 ${blocks.length} diagram(s)`));
12052
12304
  }
12053
12305
  for (const [i, source] of blocks.entries()) {
12054
12306
  const idx = i + 1;
12055
12307
  if (onlyIndex !== void 0 && idx !== onlyIndex) continue;
12056
12308
  const outPath = resolve10(outDir, `${stem}-${idx}.svg`);
12057
12309
  const svg = await renderBlock(krokiUrl, source);
12058
- writeFileSync26(outPath, svg, "utf8");
12059
- console.log(chalk128.green(` \u2192 ${outPath}`));
12310
+ writeFileSync28(outPath, svg, "utf8");
12311
+ console.log(chalk130.green(` \u2192 ${outPath}`));
12060
12312
  }
12061
12313
  }
12062
12314
  function extractMermaidBlocks(markdown) {
@@ -12068,22 +12320,22 @@ function extractMermaidBlocks(markdown) {
12068
12320
  async function mermaidExport(file, options2 = {}) {
12069
12321
  const { mermaid } = loadConfig();
12070
12322
  const outDir = resolve11(process.cwd(), options2.out ?? ".");
12071
- mkdirSync12(outDir, { recursive: true });
12323
+ mkdirSync13(outDir, { recursive: true });
12072
12324
  if (options2.index !== void 0) {
12073
12325
  if (!Number.isInteger(options2.index) || options2.index < 1) {
12074
12326
  console.error(
12075
- chalk129.red(`--index must be a positive integer (got ${options2.index})`)
12327
+ chalk131.red(`--index must be a positive integer (got ${options2.index})`)
12076
12328
  );
12077
12329
  process.exit(1);
12078
12330
  }
12079
12331
  if (!file) {
12080
- console.error(chalk129.red("--index requires a file argument"));
12332
+ console.error(chalk131.red("--index requires a file argument"));
12081
12333
  process.exit(1);
12082
12334
  }
12083
12335
  }
12084
- const files = file ? [file] : readdirSync6(process.cwd()).filter((name) => name.toLowerCase().endsWith(".md")).sort();
12336
+ const files = file ? [file] : readdirSync7(process.cwd()).filter((name) => name.toLowerCase().endsWith(".md")).sort();
12085
12337
  if (files.length === 0) {
12086
- console.log(chalk129.gray("No markdown files found in current directory."));
12338
+ console.log(chalk131.gray("No markdown files found in current directory."));
12087
12339
  return;
12088
12340
  }
12089
12341
  for (const f of files) {
@@ -12109,7 +12361,7 @@ function registerMermaid(program2) {
12109
12361
  import { mkdir as mkdir3 } from "fs/promises";
12110
12362
  import { createServer as createServer2 } from "http";
12111
12363
  import { dirname as dirname20 } from "path";
12112
- import chalk131 from "chalk";
12364
+ import chalk133 from "chalk";
12113
12365
 
12114
12366
  // src/commands/netcap/corsHeaders.ts
12115
12367
  var corsHeaders = {
@@ -12187,15 +12439,15 @@ function createNetcapHandler(options2) {
12187
12439
  // src/commands/netcap/prepareExtensionForLoad.ts
12188
12440
  import { cp, readFile as readFile2, writeFile as writeFile2 } from "fs/promises";
12189
12441
  import { networkInterfaces } from "os";
12190
- import { join as join37 } from "path";
12191
- import chalk130 from "chalk";
12442
+ import { join as join39 } from "path";
12443
+ import chalk132 from "chalk";
12192
12444
 
12193
12445
  // src/commands/netcap/netcapExtensionDir.ts
12194
- import { dirname as dirname19, join as join36 } from "path";
12446
+ import { dirname as dirname19, join as join38 } from "path";
12195
12447
  import { fileURLToPath as fileURLToPath5 } from "url";
12196
12448
  var moduleDir = dirname19(fileURLToPath5(import.meta.url));
12197
12449
  function netcapExtensionDir() {
12198
- return join36(moduleDir, "commands", "netcap", "netcap-extension");
12450
+ return join38(moduleDir, "commands", "netcap", "netcap-extension");
12199
12451
  }
12200
12452
 
12201
12453
  // src/commands/netcap/prepareExtensionForLoad.ts
@@ -12210,7 +12462,7 @@ function lanIPv4() {
12210
12462
  return void 0;
12211
12463
  }
12212
12464
  async function configureBackground(dir, host, port, filter) {
12213
- const file = join37(dir, "background.js");
12465
+ const file = join39(dir, "background.js");
12214
12466
  const source = await readFile2(file, "utf8");
12215
12467
  await writeFile2(
12216
12468
  file,
@@ -12232,7 +12484,7 @@ async function prepareExtensionForLoad(port, filter = "") {
12232
12484
  const host = lanIPv4();
12233
12485
  if (!host) {
12234
12486
  console.log(
12235
- chalk130.yellow("could not determine the WSL IP for the extension")
12487
+ chalk132.yellow("could not determine the WSL IP for the extension")
12236
12488
  );
12237
12489
  await configureBackground(source, "127.0.0.1", port, filter);
12238
12490
  return source;
@@ -12243,27 +12495,27 @@ async function prepareExtensionForLoad(port, filter = "") {
12243
12495
  return WSL_WINDOWS_PATH;
12244
12496
  } catch {
12245
12497
  console.log(
12246
- chalk130.yellow(`could not copy extension to ${WSL_WINDOWS_PATH}`)
12498
+ chalk132.yellow(`could not copy extension to ${WSL_WINDOWS_PATH}`)
12247
12499
  );
12248
12500
  return source;
12249
12501
  }
12250
12502
  }
12251
12503
 
12252
12504
  // src/commands/netcap/resolveNetcapOutPath.ts
12253
- import { isAbsolute, join as join39, resolve as resolve12 } from "path";
12505
+ import { isAbsolute, join as join41, resolve as resolve12 } from "path";
12254
12506
 
12255
12507
  // src/commands/netcap/defaultCapturePath.ts
12256
- import { homedir as homedir13 } from "os";
12257
- import { join as join38 } from "path";
12508
+ import { homedir as homedir14 } from "os";
12509
+ import { join as join40 } from "path";
12258
12510
  function defaultCapturePath() {
12259
- return join38(homedir13(), ".assist", "netcap", "capture.jsonl");
12511
+ return join40(homedir14(), ".assist", "netcap", "capture.jsonl");
12260
12512
  }
12261
12513
 
12262
12514
  // src/commands/netcap/resolveNetcapOutPath.ts
12263
12515
  function resolveNetcapOutPath(out) {
12264
12516
  if (!out) return defaultCapturePath();
12265
12517
  const dir = isAbsolute(out) ? out : resolve12(process.cwd(), out);
12266
- return join39(dir, "capture.jsonl");
12518
+ return join41(dir, "capture.jsonl");
12267
12519
  }
12268
12520
 
12269
12521
  // src/commands/netcap/netcap.ts
@@ -12276,30 +12528,30 @@ async function netcap(options2) {
12276
12528
  let count6 = 0;
12277
12529
  const handler = createNetcapHandler({
12278
12530
  outPath,
12279
- onPing: () => console.log(chalk131.dim("ping from extension")),
12531
+ onPing: () => console.log(chalk133.dim("ping from extension")),
12280
12532
  onCapture: (entry) => {
12281
12533
  count6 += 1;
12282
12534
  console.log(
12283
- chalk131.green(`captured #${count6}`),
12284
- chalk131.dim(`${entry.method ?? "?"} ${entry.url ?? "?"}`)
12535
+ chalk133.green(`captured #${count6}`),
12536
+ chalk133.dim(`${entry.method ?? "?"} ${entry.url ?? "?"}`)
12285
12537
  );
12286
12538
  }
12287
12539
  });
12288
12540
  const server = createServer2(handler);
12289
12541
  server.listen(port, () => {
12290
12542
  console.log(
12291
- chalk131.bold(`netcap receiver listening on http://127.0.0.1:${port}`)
12543
+ chalk133.bold(`netcap receiver listening on http://127.0.0.1:${port}`)
12292
12544
  );
12293
- console.log(chalk131.dim(`appending captures to ${outPath}`));
12545
+ console.log(chalk133.dim(`appending captures to ${outPath}`));
12294
12546
  if (filter)
12295
- console.log(chalk131.dim(`forwarding only URLs matching "${filter}"`));
12296
- console.log(chalk131.dim(`load the unpacked extension from ${extensionPath}`));
12297
- console.log(chalk131.dim("press Ctrl-C to stop"));
12547
+ console.log(chalk133.dim(`forwarding only URLs matching "${filter}"`));
12548
+ console.log(chalk133.dim(`load the unpacked extension from ${extensionPath}`));
12549
+ console.log(chalk133.dim("press Ctrl-C to stop"));
12298
12550
  });
12299
12551
  process.on("SIGINT", () => {
12300
12552
  server.close();
12301
12553
  console.log(
12302
- chalk131.bold(
12554
+ chalk133.bold(
12303
12555
  `
12304
12556
  netcap stopped \u2014 captured ${count6} ${count6 === 1 ? "entry" : "entries"} to ${outPath}`
12305
12557
  )
@@ -12309,12 +12561,12 @@ netcap stopped \u2014 captured ${count6} ${count6 === 1 ? "entry" : "entries"} t
12309
12561
  }
12310
12562
 
12311
12563
  // src/commands/netcap/netcapExtract.ts
12312
- import { writeFileSync as writeFileSync27 } from "fs";
12313
- import { join as join40 } from "path";
12314
- import chalk132 from "chalk";
12564
+ import { writeFileSync as writeFileSync29 } from "fs";
12565
+ import { join as join42 } from "path";
12566
+ import chalk134 from "chalk";
12315
12567
 
12316
12568
  // src/commands/netcap/extractPostsFromCapture.ts
12317
- import { readFileSync as readFileSync31 } from "fs";
12569
+ import { readFileSync as readFileSync32 } from "fs";
12318
12570
 
12319
12571
  // src/commands/netcap/parseRscRows.ts
12320
12572
  var isRscRef = (v) => typeof v === "string" && /^\$[0-9a-fL@]/.test(v);
@@ -12710,7 +12962,7 @@ function extractVoyagerPosts(body) {
12710
12962
 
12711
12963
  // src/commands/netcap/extractPostsFromCapture.ts
12712
12964
  function captureEntries(captureFile) {
12713
- const lines = readFileSync31(captureFile, "utf8").split("\n").filter(Boolean);
12965
+ const lines = readFileSync32(captureFile, "utf8").split("\n").filter(Boolean);
12714
12966
  const entries = [];
12715
12967
  for (const line of lines) {
12716
12968
  let entry;
@@ -12755,12 +13007,12 @@ function extractPostsFromCapture(captureFile) {
12755
13007
  function netcapExtract(file) {
12756
13008
  const captureFile = file ?? defaultCapturePath();
12757
13009
  const posts = extractPostsFromCapture(captureFile);
12758
- const outFile = join40(captureFile, "..", "posts.json");
12759
- writeFileSync27(outFile, `${JSON.stringify(posts, null, 2)}
13010
+ const outFile = join42(captureFile, "..", "posts.json");
13011
+ writeFileSync29(outFile, `${JSON.stringify(posts, null, 2)}
12760
13012
  `);
12761
13013
  console.log(
12762
- chalk132.green(`extracted ${posts.length} posts`),
12763
- chalk132.dim(`-> ${outFile}`)
13014
+ chalk134.green(`extracted ${posts.length} posts`),
13015
+ chalk134.dim(`-> ${outFile}`)
12764
13016
  );
12765
13017
  }
12766
13018
 
@@ -12781,7 +13033,7 @@ function registerNetcap(program2) {
12781
13033
  }
12782
13034
 
12783
13035
  // src/commands/news/add/index.ts
12784
- import chalk133 from "chalk";
13036
+ import chalk135 from "chalk";
12785
13037
  import enquirer8 from "enquirer";
12786
13038
  async function add2(url) {
12787
13039
  if (!url) {
@@ -12803,10 +13055,10 @@ async function add2(url) {
12803
13055
  const { orm } = await getReady();
12804
13056
  const added = await addFeed(orm, url);
12805
13057
  if (!added) {
12806
- console.log(chalk133.yellow("Feed already exists"));
13058
+ console.log(chalk135.yellow("Feed already exists"));
12807
13059
  return;
12808
13060
  }
12809
- console.log(chalk133.green(`Added feed: ${url}`));
13061
+ console.log(chalk135.green(`Added feed: ${url}`));
12810
13062
  }
12811
13063
 
12812
13064
  // src/commands/registerNews.ts
@@ -12816,7 +13068,7 @@ function registerNews(program2) {
12816
13068
  }
12817
13069
 
12818
13070
  // src/commands/prompts/printPromptsTable.ts
12819
- import chalk134 from "chalk";
13071
+ import chalk136 from "chalk";
12820
13072
  function truncate(str, max) {
12821
13073
  if (str.length <= max) return str;
12822
13074
  return `${str.slice(0, max - 1)}\u2026`;
@@ -12834,14 +13086,14 @@ function printPromptsTable(rows) {
12834
13086
  "Command".padEnd(commandWidth),
12835
13087
  "Repos"
12836
13088
  ].join(" ");
12837
- console.log(chalk134.dim(header));
12838
- console.log(chalk134.dim("-".repeat(header.length)));
13089
+ console.log(chalk136.dim(header));
13090
+ console.log(chalk136.dim("-".repeat(header.length)));
12839
13091
  for (const row of rows) {
12840
13092
  const count6 = String(row.count).padStart(countWidth);
12841
13093
  const tool = row.tool.padEnd(toolWidth);
12842
13094
  const command = truncate(row.command, 60).padEnd(commandWidth);
12843
13095
  console.log(
12844
- `${chalk134.yellow(count6)} ${tool} ${command} ${chalk134.dim(row.repos)}`
13096
+ `${chalk136.yellow(count6)} ${tool} ${command} ${chalk136.dim(row.repos)}`
12845
13097
  );
12846
13098
  }
12847
13099
  }
@@ -13189,29 +13441,29 @@ import { execSync as execSync35 } from "child_process";
13189
13441
 
13190
13442
  // src/commands/prs/resolveCommentWithReply.ts
13191
13443
  import { execSync as execSync34 } from "child_process";
13192
- import { unlinkSync as unlinkSync10, writeFileSync as writeFileSync28 } from "fs";
13444
+ import { unlinkSync as unlinkSync12, writeFileSync as writeFileSync30 } from "fs";
13193
13445
  import { tmpdir as tmpdir5 } from "os";
13194
- import { join as join42 } from "path";
13446
+ import { join as join44 } from "path";
13195
13447
 
13196
13448
  // src/commands/prs/loadCommentsCache.ts
13197
- import { existsSync as existsSync35, readFileSync as readFileSync32, unlinkSync as unlinkSync9 } from "fs";
13198
- import { join as join41 } from "path";
13449
+ import { existsSync as existsSync36, readFileSync as readFileSync33, unlinkSync as unlinkSync11 } from "fs";
13450
+ import { join as join43 } from "path";
13199
13451
  import { parse as parse2 } from "yaml";
13200
13452
  function getCachePath(prNumber) {
13201
- return join41(process.cwd(), ".assist", `pr-${prNumber}-comments.yaml`);
13453
+ return join43(process.cwd(), ".assist", `pr-${prNumber}-comments.yaml`);
13202
13454
  }
13203
13455
  function loadCommentsCache(prNumber) {
13204
13456
  const cachePath = getCachePath(prNumber);
13205
- if (!existsSync35(cachePath)) {
13457
+ if (!existsSync36(cachePath)) {
13206
13458
  return null;
13207
13459
  }
13208
- const content = readFileSync32(cachePath, "utf8");
13460
+ const content = readFileSync33(cachePath, "utf8");
13209
13461
  return parse2(content);
13210
13462
  }
13211
13463
  function deleteCommentsCache(prNumber) {
13212
13464
  const cachePath = getCachePath(prNumber);
13213
- if (existsSync35(cachePath)) {
13214
- unlinkSync9(cachePath);
13465
+ if (existsSync36(cachePath)) {
13466
+ unlinkSync11(cachePath);
13215
13467
  console.log("No more unresolved line comments. Cache dropped.");
13216
13468
  }
13217
13469
  }
@@ -13228,15 +13480,15 @@ function replyToComment(org, repo, prNumber, commentId, message) {
13228
13480
  // src/commands/prs/resolveCommentWithReply.ts
13229
13481
  function resolveThread(threadId) {
13230
13482
  const mutation = `mutation($threadId: ID!) { resolveReviewThread(input: {threadId: $threadId}) { thread { isResolved } } }`;
13231
- const queryFile = join42(tmpdir5(), `gh-mutation-${Date.now()}.graphql`);
13232
- writeFileSync28(queryFile, mutation);
13483
+ const queryFile = join44(tmpdir5(), `gh-mutation-${Date.now()}.graphql`);
13484
+ writeFileSync30(queryFile, mutation);
13233
13485
  try {
13234
13486
  execSync34(
13235
13487
  `gh api graphql -F query=@${queryFile} -f threadId="${threadId}"`,
13236
13488
  { stdio: ["inherit", "pipe", "inherit"] }
13237
13489
  );
13238
13490
  } finally {
13239
- unlinkSync10(queryFile);
13491
+ unlinkSync12(queryFile);
13240
13492
  }
13241
13493
  }
13242
13494
  function requireCache(prNumber) {
@@ -13310,19 +13562,19 @@ function fixed(commentId, sha) {
13310
13562
  }
13311
13563
 
13312
13564
  // src/commands/prs/listComments/index.ts
13313
- import { existsSync as existsSync36, mkdirSync as mkdirSync13, writeFileSync as writeFileSync30 } from "fs";
13314
- import { join as join44 } from "path";
13565
+ import { existsSync as existsSync37, mkdirSync as mkdirSync14, writeFileSync as writeFileSync32 } from "fs";
13566
+ import { join as join46 } from "path";
13315
13567
  import { stringify } from "yaml";
13316
13568
 
13317
13569
  // src/commands/prs/fetchThreadIds.ts
13318
13570
  import { execSync as execSync36 } from "child_process";
13319
- import { unlinkSync as unlinkSync11, writeFileSync as writeFileSync29 } from "fs";
13571
+ import { unlinkSync as unlinkSync13, writeFileSync as writeFileSync31 } from "fs";
13320
13572
  import { tmpdir as tmpdir6 } from "os";
13321
- import { join as join43 } from "path";
13573
+ import { join as join45 } from "path";
13322
13574
  var THREAD_QUERY = `query($owner: String!, $repo: String!, $prNumber: Int!) { repository(owner: $owner, name: $repo) { pullRequest(number: $prNumber) { reviewThreads(first: 100) { nodes { id isResolved comments(first: 100) { nodes { databaseId } } } } } } }`;
13323
13575
  function fetchThreadIds(org, repo, prNumber) {
13324
- const queryFile = join43(tmpdir6(), `gh-query-${Date.now()}.graphql`);
13325
- writeFileSync29(queryFile, THREAD_QUERY);
13576
+ const queryFile = join45(tmpdir6(), `gh-query-${Date.now()}.graphql`);
13577
+ writeFileSync31(queryFile, THREAD_QUERY);
13326
13578
  try {
13327
13579
  const result = execSync36(
13328
13580
  `gh api graphql -F query=@${queryFile} -F owner="${org}" -F repo="${repo}" -F prNumber=${prNumber}`,
@@ -13341,7 +13593,7 @@ function fetchThreadIds(org, repo, prNumber) {
13341
13593
  }
13342
13594
  return { threadMap, resolvedThreadIds };
13343
13595
  } finally {
13344
- unlinkSync11(queryFile);
13596
+ unlinkSync13(queryFile);
13345
13597
  }
13346
13598
  }
13347
13599
 
@@ -13390,20 +13642,20 @@ function fetchLineComments(org, repo, prNumber, threadInfo) {
13390
13642
  }
13391
13643
 
13392
13644
  // src/commands/prs/listComments/printComments.ts
13393
- import chalk135 from "chalk";
13645
+ import chalk137 from "chalk";
13394
13646
  function formatForHuman(comment3) {
13395
13647
  if (comment3.type === "review") {
13396
- const stateColor = comment3.state === "APPROVED" ? chalk135.green : comment3.state === "CHANGES_REQUESTED" ? chalk135.red : chalk135.yellow;
13648
+ const stateColor = comment3.state === "APPROVED" ? chalk137.green : comment3.state === "CHANGES_REQUESTED" ? chalk137.red : chalk137.yellow;
13397
13649
  return [
13398
- `${chalk135.cyan("Review")} by ${chalk135.bold(comment3.user)} ${stateColor(`[${comment3.state}]`)}`,
13650
+ `${chalk137.cyan("Review")} by ${chalk137.bold(comment3.user)} ${stateColor(`[${comment3.state}]`)}`,
13399
13651
  comment3.body,
13400
13652
  ""
13401
13653
  ].join("\n");
13402
13654
  }
13403
13655
  const location = comment3.line ? `:${comment3.line}` : "";
13404
13656
  return [
13405
- `${chalk135.cyan("Line comment")} by ${chalk135.bold(comment3.user)} on ${chalk135.dim(`${comment3.path}${location}`)}`,
13406
- chalk135.dim(comment3.diff_hunk.split("\n").slice(-3).join("\n")),
13657
+ `${chalk137.cyan("Line comment")} by ${chalk137.bold(comment3.user)} on ${chalk137.dim(`${comment3.path}${location}`)}`,
13658
+ chalk137.dim(comment3.diff_hunk.split("\n").slice(-3).join("\n")),
13407
13659
  comment3.body,
13408
13660
  ""
13409
13661
  ].join("\n");
@@ -13435,17 +13687,17 @@ function printComments2(result) {
13435
13687
 
13436
13688
  // src/commands/prs/listComments/index.ts
13437
13689
  function writeCommentsCache(prNumber, comments3) {
13438
- const assistDir = join44(process.cwd(), ".assist");
13439
- if (!existsSync36(assistDir)) {
13440
- mkdirSync13(assistDir, { recursive: true });
13690
+ const assistDir = join46(process.cwd(), ".assist");
13691
+ if (!existsSync37(assistDir)) {
13692
+ mkdirSync14(assistDir, { recursive: true });
13441
13693
  }
13442
13694
  const cacheData = {
13443
13695
  prNumber,
13444
13696
  fetchedAt: (/* @__PURE__ */ new Date()).toISOString(),
13445
13697
  comments: comments3
13446
13698
  };
13447
- const cachePath = join44(assistDir, `pr-${prNumber}-comments.yaml`);
13448
- writeFileSync30(cachePath, stringify(cacheData));
13699
+ const cachePath = join46(assistDir, `pr-${prNumber}-comments.yaml`);
13700
+ writeFileSync32(cachePath, stringify(cacheData));
13449
13701
  }
13450
13702
  function handleKnownErrors(error) {
13451
13703
  if (isGhNotInstalled(error)) {
@@ -13477,7 +13729,7 @@ async function listComments() {
13477
13729
  ];
13478
13730
  updateCache(prNumber, allComments);
13479
13731
  const hasLineComments = allComments.some((c) => c.type === "line");
13480
- const cachePath = hasLineComments ? join44(process.cwd(), ".assist", `pr-${prNumber}-comments.yaml`) : null;
13732
+ const cachePath = hasLineComments ? join46(process.cwd(), ".assist", `pr-${prNumber}-comments.yaml`) : null;
13481
13733
  return { comments: allComments, cachePath };
13482
13734
  } catch (error) {
13483
13735
  const handled = handleKnownErrors(error);
@@ -13493,13 +13745,13 @@ import { execSync as execSync38 } from "child_process";
13493
13745
  import enquirer9 from "enquirer";
13494
13746
 
13495
13747
  // src/commands/prs/prs/displayPaginated/printPr.ts
13496
- import chalk136 from "chalk";
13748
+ import chalk138 from "chalk";
13497
13749
  var STATUS_MAP = {
13498
- MERGED: (pr) => pr.mergedAt ? { label: chalk136.magenta("merged"), date: pr.mergedAt } : null,
13499
- CLOSED: (pr) => pr.closedAt ? { label: chalk136.red("closed"), date: pr.closedAt } : null
13750
+ MERGED: (pr) => pr.mergedAt ? { label: chalk138.magenta("merged"), date: pr.mergedAt } : null,
13751
+ CLOSED: (pr) => pr.closedAt ? { label: chalk138.red("closed"), date: pr.closedAt } : null
13500
13752
  };
13501
13753
  function defaultStatus(pr) {
13502
- return { label: chalk136.green("opened"), date: pr.createdAt };
13754
+ return { label: chalk138.green("opened"), date: pr.createdAt };
13503
13755
  }
13504
13756
  function getStatus2(pr) {
13505
13757
  return STATUS_MAP[pr.state]?.(pr) ?? defaultStatus(pr);
@@ -13508,11 +13760,11 @@ function formatDate(dateStr) {
13508
13760
  return new Date(dateStr).toISOString().split("T")[0];
13509
13761
  }
13510
13762
  function formatPrHeader(pr, status2) {
13511
- return `${chalk136.cyan(`#${pr.number}`)} ${pr.title} ${chalk136.dim(`(${pr.author.login},`)} ${status2.label} ${chalk136.dim(`${formatDate(status2.date)})`)}`;
13763
+ return `${chalk138.cyan(`#${pr.number}`)} ${pr.title} ${chalk138.dim(`(${pr.author.login},`)} ${status2.label} ${chalk138.dim(`${formatDate(status2.date)})`)}`;
13512
13764
  }
13513
13765
  function logPrDetails(pr) {
13514
13766
  console.log(
13515
- chalk136.dim(` ${pr.changedFiles.toLocaleString()} files | ${pr.url}`)
13767
+ chalk138.dim(` ${pr.changedFiles.toLocaleString()} files | ${pr.url}`)
13516
13768
  );
13517
13769
  console.log();
13518
13770
  }
@@ -13819,10 +14071,10 @@ function registerPrs(program2) {
13819
14071
  }
13820
14072
 
13821
14073
  // src/commands/ravendb/ravendbAuth.ts
13822
- import chalk142 from "chalk";
14074
+ import chalk144 from "chalk";
13823
14075
 
13824
14076
  // src/shared/createConnectionAuth.ts
13825
- import chalk137 from "chalk";
14077
+ import chalk139 from "chalk";
13826
14078
  function listConnections(connections, format2) {
13827
14079
  if (connections.length === 0) {
13828
14080
  console.log("No connections configured.");
@@ -13835,7 +14087,7 @@ function listConnections(connections, format2) {
13835
14087
  function removeConnection(connections, name, save) {
13836
14088
  const filtered = connections.filter((c) => c.name !== name);
13837
14089
  if (filtered.length === connections.length) {
13838
- console.error(chalk137.red(`Connection "${name}" not found.`));
14090
+ console.error(chalk139.red(`Connection "${name}" not found.`));
13839
14091
  process.exit(1);
13840
14092
  }
13841
14093
  save(filtered);
@@ -13881,15 +14133,15 @@ function saveConnections(connections) {
13881
14133
  }
13882
14134
 
13883
14135
  // src/commands/ravendb/promptConnection.ts
13884
- import chalk140 from "chalk";
14136
+ import chalk142 from "chalk";
13885
14137
 
13886
14138
  // src/commands/ravendb/selectOpSecret.ts
13887
- import chalk139 from "chalk";
14139
+ import chalk141 from "chalk";
13888
14140
  import Enquirer2 from "enquirer";
13889
14141
 
13890
14142
  // src/commands/ravendb/searchItems.ts
13891
14143
  import { execSync as execSync41 } from "child_process";
13892
- import chalk138 from "chalk";
14144
+ import chalk140 from "chalk";
13893
14145
  function opExec(args) {
13894
14146
  return execSync41(`op ${args}`, {
13895
14147
  encoding: "utf8",
@@ -13902,7 +14154,7 @@ function searchItems(search2) {
13902
14154
  items2 = JSON.parse(opExec("item list --format=json"));
13903
14155
  } catch {
13904
14156
  console.error(
13905
- chalk138.red(
14157
+ chalk140.red(
13906
14158
  "Failed to search 1Password. Ensure the CLI is installed and you are signed in."
13907
14159
  )
13908
14160
  );
@@ -13916,7 +14168,7 @@ function getItemFields(itemId) {
13916
14168
  const item = JSON.parse(opExec(`item get "${itemId}" --format=json`));
13917
14169
  return item.fields.filter((f) => f.reference && f.label);
13918
14170
  } catch {
13919
- console.error(chalk138.red("Failed to get item details from 1Password."));
14171
+ console.error(chalk140.red("Failed to get item details from 1Password."));
13920
14172
  process.exit(1);
13921
14173
  }
13922
14174
  }
@@ -13935,7 +14187,7 @@ async function selectOpSecret(searchTerm) {
13935
14187
  }).run();
13936
14188
  const items2 = searchItems(search2);
13937
14189
  if (items2.length === 0) {
13938
- console.error(chalk139.red(`No items found matching "${search2}".`));
14190
+ console.error(chalk141.red(`No items found matching "${search2}".`));
13939
14191
  process.exit(1);
13940
14192
  }
13941
14193
  const itemId = await selectOne(
@@ -13944,7 +14196,7 @@ async function selectOpSecret(searchTerm) {
13944
14196
  );
13945
14197
  const fields = getItemFields(itemId);
13946
14198
  if (fields.length === 0) {
13947
- console.error(chalk139.red("No fields with references found on this item."));
14199
+ console.error(chalk141.red("No fields with references found on this item."));
13948
14200
  process.exit(1);
13949
14201
  }
13950
14202
  const ref = await selectOne(
@@ -13958,7 +14210,7 @@ async function selectOpSecret(searchTerm) {
13958
14210
  async function promptConnection(existingNames) {
13959
14211
  const name = await promptInput("name", "Connection name:");
13960
14212
  if (existingNames.includes(name)) {
13961
- console.error(chalk140.red(`Connection "${name}" already exists.`));
14213
+ console.error(chalk142.red(`Connection "${name}" already exists.`));
13962
14214
  process.exit(1);
13963
14215
  }
13964
14216
  const url = await promptInput(
@@ -13967,22 +14219,22 @@ async function promptConnection(existingNames) {
13967
14219
  );
13968
14220
  const database = await promptInput("database", "Database name:");
13969
14221
  if (!name || !url || !database) {
13970
- console.error(chalk140.red("All fields are required."));
14222
+ console.error(chalk142.red("All fields are required."));
13971
14223
  process.exit(1);
13972
14224
  }
13973
14225
  const apiKeyRef = await selectOpSecret();
13974
- console.log(chalk140.dim(`Using: ${apiKeyRef}`));
14226
+ console.log(chalk142.dim(`Using: ${apiKeyRef}`));
13975
14227
  return { name, url, database, apiKeyRef };
13976
14228
  }
13977
14229
 
13978
14230
  // src/commands/ravendb/ravendbSetConnection.ts
13979
- import chalk141 from "chalk";
14231
+ import chalk143 from "chalk";
13980
14232
  function ravendbSetConnection(name) {
13981
14233
  const raw = loadGlobalConfigRaw();
13982
14234
  const ravendb = raw.ravendb ?? {};
13983
14235
  const connections = ravendb.connections ?? [];
13984
14236
  if (!connections.some((c) => c.name === name)) {
13985
- console.error(chalk141.red(`Connection "${name}" not found.`));
14237
+ console.error(chalk143.red(`Connection "${name}" not found.`));
13986
14238
  console.error(
13987
14239
  `Available: ${connections.map((c) => c.name).join(", ") || "(none)"}`
13988
14240
  );
@@ -13998,16 +14250,16 @@ function ravendbSetConnection(name) {
13998
14250
  var ravendbAuth = createConnectionAuth({
13999
14251
  load: loadConnections,
14000
14252
  save: saveConnections,
14001
- format: (c) => `${chalk142.bold(c.name)} ${c.url} db=${c.database} key=${c.apiKeyRef}`,
14253
+ format: (c) => `${chalk144.bold(c.name)} ${c.url} db=${c.database} key=${c.apiKeyRef}`,
14002
14254
  promptNew: promptConnection,
14003
14255
  onFirst: (c) => ravendbSetConnection(c.name)
14004
14256
  });
14005
14257
 
14006
14258
  // src/commands/ravendb/ravendbCollections.ts
14007
- import chalk146 from "chalk";
14259
+ import chalk148 from "chalk";
14008
14260
 
14009
14261
  // src/commands/ravendb/ravenFetch.ts
14010
- import chalk144 from "chalk";
14262
+ import chalk146 from "chalk";
14011
14263
 
14012
14264
  // src/commands/ravendb/getAccessToken.ts
14013
14265
  var OAUTH_URL = "https://amazon-useast-1-oauth.ravenhq.com/ApiKeys/OAuth/AccessToken";
@@ -14044,10 +14296,10 @@ ${errorText}`
14044
14296
 
14045
14297
  // src/commands/ravendb/resolveOpSecret.ts
14046
14298
  import { execSync as execSync42 } from "child_process";
14047
- import chalk143 from "chalk";
14299
+ import chalk145 from "chalk";
14048
14300
  function resolveOpSecret(reference) {
14049
14301
  if (!reference.startsWith("op://")) {
14050
- console.error(chalk143.red(`Invalid secret reference: must start with op://`));
14302
+ console.error(chalk145.red(`Invalid secret reference: must start with op://`));
14051
14303
  process.exit(1);
14052
14304
  }
14053
14305
  try {
@@ -14057,7 +14309,7 @@ function resolveOpSecret(reference) {
14057
14309
  }).trim();
14058
14310
  } catch {
14059
14311
  console.error(
14060
- chalk143.red(
14312
+ chalk145.red(
14061
14313
  "Failed to resolve secret reference. Ensure 1Password CLI is installed and you are signed in."
14062
14314
  )
14063
14315
  );
@@ -14084,7 +14336,7 @@ async function ravenFetch(connection, path57) {
14084
14336
  if (!response.ok) {
14085
14337
  const body = await response.text();
14086
14338
  console.error(
14087
- chalk144.red(`RavenDB error: ${response.status} ${response.statusText}`)
14339
+ chalk146.red(`RavenDB error: ${response.status} ${response.statusText}`)
14088
14340
  );
14089
14341
  console.error(body.substring(0, 500));
14090
14342
  process.exit(1);
@@ -14093,7 +14345,7 @@ async function ravenFetch(connection, path57) {
14093
14345
  }
14094
14346
 
14095
14347
  // src/commands/ravendb/resolveConnection.ts
14096
- import chalk145 from "chalk";
14348
+ import chalk147 from "chalk";
14097
14349
  function loadRavendb() {
14098
14350
  const raw = loadGlobalConfigRaw();
14099
14351
  const ravendb = raw.ravendb;
@@ -14107,7 +14359,7 @@ function resolveConnection(name) {
14107
14359
  const connectionName = name ?? defaultConnection;
14108
14360
  if (!connectionName) {
14109
14361
  console.error(
14110
- chalk145.red(
14362
+ chalk147.red(
14111
14363
  "No connection specified and no default set. Use assist ravendb set-connection <name> or pass a connection name."
14112
14364
  )
14113
14365
  );
@@ -14115,7 +14367,7 @@ function resolveConnection(name) {
14115
14367
  }
14116
14368
  const connection = connections.find((c) => c.name === connectionName);
14117
14369
  if (!connection) {
14118
- console.error(chalk145.red(`Connection "${connectionName}" not found.`));
14370
+ console.error(chalk147.red(`Connection "${connectionName}" not found.`));
14119
14371
  console.error(
14120
14372
  `Available: ${connections.map((c) => c.name).join(", ") || "(none)"}`
14121
14373
  );
@@ -14146,15 +14398,15 @@ async function ravendbCollections(connectionName) {
14146
14398
  return;
14147
14399
  }
14148
14400
  for (const c of collections) {
14149
- console.log(`${chalk146.bold(c.Name)} ${c.CountOfDocuments} docs`);
14401
+ console.log(`${chalk148.bold(c.Name)} ${c.CountOfDocuments} docs`);
14150
14402
  }
14151
14403
  }
14152
14404
 
14153
14405
  // src/commands/ravendb/ravendbQuery.ts
14154
- import chalk148 from "chalk";
14406
+ import chalk150 from "chalk";
14155
14407
 
14156
14408
  // src/commands/ravendb/fetchAllPages.ts
14157
- import chalk147 from "chalk";
14409
+ import chalk149 from "chalk";
14158
14410
 
14159
14411
  // src/commands/ravendb/buildQueryPath.ts
14160
14412
  function buildQueryPath(opts) {
@@ -14192,7 +14444,7 @@ async function fetchAllPages(connection, opts) {
14192
14444
  allResults.push(...results);
14193
14445
  start3 += results.length;
14194
14446
  process.stderr.write(
14195
- `\r${chalk147.dim(`Fetched ${allResults.length}/${totalResults}`)}`
14447
+ `\r${chalk149.dim(`Fetched ${allResults.length}/${totalResults}`)}`
14196
14448
  );
14197
14449
  if (start3 >= totalResults) break;
14198
14450
  if (opts.limit !== void 0 && allResults.length >= opts.limit) break;
@@ -14207,7 +14459,7 @@ async function fetchAllPages(connection, opts) {
14207
14459
  async function ravendbQuery(connectionName, collection, options2) {
14208
14460
  const resolved = resolveArgs(connectionName, collection);
14209
14461
  if (!resolved.collection && !options2.query) {
14210
- console.error(chalk148.red("Provide a collection name or --query filter."));
14462
+ console.error(chalk150.red("Provide a collection name or --query filter."));
14211
14463
  process.exit(1);
14212
14464
  }
14213
14465
  const { collection: col } = resolved;
@@ -14245,7 +14497,7 @@ import { spawn as spawn5 } from "child_process";
14245
14497
  import * as path28 from "path";
14246
14498
 
14247
14499
  // src/commands/refactor/logViolations.ts
14248
- import chalk149 from "chalk";
14500
+ import chalk151 from "chalk";
14249
14501
  var DEFAULT_MAX_LINES = 100;
14250
14502
  function logViolations(violations, maxLines = DEFAULT_MAX_LINES) {
14251
14503
  if (violations.length === 0) {
@@ -14254,43 +14506,43 @@ function logViolations(violations, maxLines = DEFAULT_MAX_LINES) {
14254
14506
  }
14255
14507
  return;
14256
14508
  }
14257
- console.error(chalk149.red(`
14509
+ console.error(chalk151.red(`
14258
14510
  Refactor check failed:
14259
14511
  `));
14260
- console.error(chalk149.red(` The following files exceed ${maxLines} lines:
14512
+ console.error(chalk151.red(` The following files exceed ${maxLines} lines:
14261
14513
  `));
14262
14514
  for (const violation of violations) {
14263
- console.error(chalk149.red(` ${violation.file} (${violation.lines} lines)`));
14515
+ console.error(chalk151.red(` ${violation.file} (${violation.lines} lines)`));
14264
14516
  }
14265
14517
  console.error(
14266
- chalk149.yellow(
14518
+ chalk151.yellow(
14267
14519
  `
14268
14520
  Each file needs to be sensibly refactored, or if there is no sensible
14269
14521
  way to refactor it, ignore it with:
14270
14522
  `
14271
14523
  )
14272
14524
  );
14273
- console.error(chalk149.gray(` assist refactor ignore <file>
14525
+ console.error(chalk151.gray(` assist refactor ignore <file>
14274
14526
  `));
14275
14527
  if (process.env.CLAUDECODE) {
14276
- console.error(chalk149.cyan(`
14528
+ console.error(chalk151.cyan(`
14277
14529
  ## Extracting Code to New Files
14278
14530
  `));
14279
14531
  console.error(
14280
- chalk149.cyan(
14532
+ chalk151.cyan(
14281
14533
  ` When extracting logic from one file to another, consider where the extracted code belongs:
14282
14534
  `
14283
14535
  )
14284
14536
  );
14285
14537
  console.error(
14286
- chalk149.cyan(
14538
+ chalk151.cyan(
14287
14539
  ` 1. Keep related logic together: If the extracted code is tightly coupled to the
14288
14540
  original file's domain, create a new folder containing both the original and extracted files.
14289
14541
  `
14290
14542
  )
14291
14543
  );
14292
14544
  console.error(
14293
- chalk149.cyan(
14545
+ chalk151.cyan(
14294
14546
  ` 2. Share common utilities: If the extracted code can be reused across multiple
14295
14547
  domains, move it to a common/shared folder.
14296
14548
  `
@@ -14446,7 +14698,7 @@ async function check(pattern2, options2) {
14446
14698
 
14447
14699
  // src/commands/refactor/extract/index.ts
14448
14700
  import path35 from "path";
14449
- import chalk152 from "chalk";
14701
+ import chalk154 from "chalk";
14450
14702
 
14451
14703
  // src/commands/refactor/extract/applyExtraction.ts
14452
14704
  import { SyntaxKind as SyntaxKind4 } from "ts-morph";
@@ -15021,23 +15273,23 @@ function buildPlan2(functionName, sourceFile, sourcePath, destPath, project) {
15021
15273
 
15022
15274
  // src/commands/refactor/extract/displayPlan.ts
15023
15275
  import path32 from "path";
15024
- import chalk150 from "chalk";
15276
+ import chalk152 from "chalk";
15025
15277
  function section(title) {
15026
15278
  return `
15027
- ${chalk150.cyan(title)}`;
15279
+ ${chalk152.cyan(title)}`;
15028
15280
  }
15029
15281
  function displayImporters(plan2, cwd) {
15030
15282
  if (plan2.importersToUpdate.length === 0) return;
15031
15283
  console.log(section("Update importers:"));
15032
15284
  for (const imp of plan2.importersToUpdate) {
15033
15285
  const rel = path32.relative(cwd, imp.file.getFilePath());
15034
- console.log(` ${chalk150.dim(rel)}: \u2192 import from "${imp.relPath}"`);
15286
+ console.log(` ${chalk152.dim(rel)}: \u2192 import from "${imp.relPath}"`);
15035
15287
  }
15036
15288
  }
15037
15289
  function displayPlan(functionName, relDest, plan2, cwd) {
15038
- console.log(chalk150.bold(`Extract: ${functionName} \u2192 ${relDest}
15290
+ console.log(chalk152.bold(`Extract: ${functionName} \u2192 ${relDest}
15039
15291
  `));
15040
- console.log(` ${chalk150.cyan("Functions to move:")}`);
15292
+ console.log(` ${chalk152.cyan("Functions to move:")}`);
15041
15293
  for (const name of plan2.extractedNames) {
15042
15294
  console.log(` ${name}`);
15043
15295
  }
@@ -15071,7 +15323,7 @@ function displayPlan(functionName, relDest, plan2, cwd) {
15071
15323
 
15072
15324
  // src/commands/refactor/extract/loadProjectFile.ts
15073
15325
  import path34 from "path";
15074
- import chalk151 from "chalk";
15326
+ import chalk153 from "chalk";
15075
15327
  import { Project as Project4 } from "ts-morph";
15076
15328
 
15077
15329
  // src/commands/refactor/extract/findTsConfig.ts
@@ -15131,7 +15383,7 @@ function loadProjectFile(file) {
15131
15383
  });
15132
15384
  const sourceFile = project.getSourceFile(sourcePath);
15133
15385
  if (!sourceFile) {
15134
- console.log(chalk151.red(`File not found in project: ${file}`));
15386
+ console.log(chalk153.red(`File not found in project: ${file}`));
15135
15387
  process.exit(1);
15136
15388
  }
15137
15389
  return { project, sourceFile };
@@ -15154,19 +15406,19 @@ async function extract(file, functionName, destination, options2 = {}) {
15154
15406
  displayPlan(functionName, relDest, plan2, cwd);
15155
15407
  if (options2.apply) {
15156
15408
  await applyExtraction(functionName, sourceFile, destPath, plan2, project);
15157
- console.log(chalk152.green("\nExtraction complete"));
15409
+ console.log(chalk154.green("\nExtraction complete"));
15158
15410
  } else {
15159
- console.log(chalk152.dim("\nDry run. Use --apply to execute."));
15411
+ console.log(chalk154.dim("\nDry run. Use --apply to execute."));
15160
15412
  }
15161
15413
  }
15162
15414
 
15163
15415
  // src/commands/refactor/ignore.ts
15164
15416
  import fs23 from "fs";
15165
- import chalk153 from "chalk";
15417
+ import chalk155 from "chalk";
15166
15418
  var REFACTOR_YML_PATH2 = "refactor.yml";
15167
15419
  function ignore(file) {
15168
15420
  if (!fs23.existsSync(file)) {
15169
- console.error(chalk153.red(`Error: File does not exist: ${file}`));
15421
+ console.error(chalk155.red(`Error: File does not exist: ${file}`));
15170
15422
  process.exit(1);
15171
15423
  }
15172
15424
  const content = fs23.readFileSync(file, "utf8");
@@ -15182,7 +15434,7 @@ function ignore(file) {
15182
15434
  fs23.writeFileSync(REFACTOR_YML_PATH2, entry);
15183
15435
  }
15184
15436
  console.log(
15185
- chalk153.green(
15437
+ chalk155.green(
15186
15438
  `Added ${file} to refactor ignore list (max ${maxLines} lines)`
15187
15439
  )
15188
15440
  );
@@ -15191,12 +15443,12 @@ function ignore(file) {
15191
15443
  // src/commands/refactor/rename/index.ts
15192
15444
  import fs26 from "fs";
15193
15445
  import path40 from "path";
15194
- import chalk156 from "chalk";
15446
+ import chalk158 from "chalk";
15195
15447
 
15196
15448
  // src/commands/refactor/rename/applyRename.ts
15197
15449
  import fs25 from "fs";
15198
15450
  import path37 from "path";
15199
- import chalk154 from "chalk";
15451
+ import chalk156 from "chalk";
15200
15452
 
15201
15453
  // src/commands/refactor/restructure/computeRewrites/index.ts
15202
15454
  import path36 from "path";
@@ -15301,13 +15553,13 @@ function applyRename(rewrites, sourcePath, destPath, cwd) {
15301
15553
  const updatedContents = applyRewrites(rewrites);
15302
15554
  for (const [file, content] of updatedContents) {
15303
15555
  fs25.writeFileSync(file, content, "utf8");
15304
- console.log(chalk154.cyan(` Updated imports in ${path37.relative(cwd, file)}`));
15556
+ console.log(chalk156.cyan(` Updated imports in ${path37.relative(cwd, file)}`));
15305
15557
  }
15306
15558
  const destDir = path37.dirname(destPath);
15307
15559
  if (!fs25.existsSync(destDir)) fs25.mkdirSync(destDir, { recursive: true });
15308
15560
  fs25.renameSync(sourcePath, destPath);
15309
15561
  console.log(
15310
- chalk154.white(
15562
+ chalk156.white(
15311
15563
  ` Moved ${path37.relative(cwd, sourcePath)} \u2192 ${path37.relative(cwd, destPath)}`
15312
15564
  )
15313
15565
  );
@@ -15394,16 +15646,16 @@ function computeRenameRewrites(sourcePath, destPath) {
15394
15646
 
15395
15647
  // src/commands/refactor/rename/printRenamePreview.ts
15396
15648
  import path39 from "path";
15397
- import chalk155 from "chalk";
15649
+ import chalk157 from "chalk";
15398
15650
  function printRenamePreview(rewrites, cwd) {
15399
15651
  for (const rewrite of rewrites) {
15400
15652
  console.log(
15401
- chalk155.dim(
15653
+ chalk157.dim(
15402
15654
  ` ${path39.relative(cwd, rewrite.file)}: ${rewrite.oldSpecifier} \u2192 ${rewrite.newSpecifier}`
15403
15655
  )
15404
15656
  );
15405
15657
  }
15406
- console.log(chalk155.dim("Dry run. Use --apply to execute."));
15658
+ console.log(chalk157.dim("Dry run. Use --apply to execute."));
15407
15659
  }
15408
15660
 
15409
15661
  // src/commands/refactor/rename/index.ts
@@ -15414,20 +15666,20 @@ async function rename(source, destination, options2 = {}) {
15414
15666
  const relSource = path40.relative(cwd, sourcePath);
15415
15667
  const relDest = path40.relative(cwd, destPath);
15416
15668
  if (!fs26.existsSync(sourcePath)) {
15417
- console.log(chalk156.red(`File not found: ${source}`));
15669
+ console.log(chalk158.red(`File not found: ${source}`));
15418
15670
  process.exit(1);
15419
15671
  }
15420
15672
  if (destPath !== sourcePath && fs26.existsSync(destPath)) {
15421
- console.log(chalk156.red(`Destination already exists: ${destination}`));
15673
+ console.log(chalk158.red(`Destination already exists: ${destination}`));
15422
15674
  process.exit(1);
15423
15675
  }
15424
- console.log(chalk156.bold(`Rename: ${relSource} \u2192 ${relDest}`));
15425
- console.log(chalk156.dim("Loading project..."));
15426
- console.log(chalk156.dim("Scanning imports across the project..."));
15676
+ console.log(chalk158.bold(`Rename: ${relSource} \u2192 ${relDest}`));
15677
+ console.log(chalk158.dim("Loading project..."));
15678
+ console.log(chalk158.dim("Scanning imports across the project..."));
15427
15679
  const rewrites = computeRenameRewrites(sourcePath, destPath);
15428
15680
  const affectedFiles = new Set(rewrites.map((r) => r.file)).size;
15429
15681
  console.log(
15430
- chalk156.dim(
15682
+ chalk158.dim(
15431
15683
  `${rewrites.length} import path(s) to update across ${affectedFiles} file(s)`
15432
15684
  )
15433
15685
  );
@@ -15436,11 +15688,11 @@ async function rename(source, destination, options2 = {}) {
15436
15688
  return;
15437
15689
  }
15438
15690
  applyRename(rewrites, sourcePath, destPath, cwd);
15439
- console.log(chalk156.green("Done"));
15691
+ console.log(chalk158.green("Done"));
15440
15692
  }
15441
15693
 
15442
15694
  // src/commands/refactor/renameSymbol/index.ts
15443
- import chalk157 from "chalk";
15695
+ import chalk159 from "chalk";
15444
15696
 
15445
15697
  // src/commands/refactor/renameSymbol/findSymbol.ts
15446
15698
  import { SyntaxKind as SyntaxKind14 } from "ts-morph";
@@ -15486,33 +15738,33 @@ async function renameSymbol(file, oldName, newName, options2 = {}) {
15486
15738
  const { project, sourceFile } = loadProjectFile(file);
15487
15739
  const symbol = findSymbol(sourceFile, oldName);
15488
15740
  if (!symbol) {
15489
- console.log(chalk157.red(`Symbol "${oldName}" not found in ${file}`));
15741
+ console.log(chalk159.red(`Symbol "${oldName}" not found in ${file}`));
15490
15742
  process.exit(1);
15491
15743
  }
15492
15744
  const grouped = groupReferences(symbol, cwd);
15493
15745
  const totalRefs = [...grouped.values()].reduce((s, l) => s + l.length, 0);
15494
15746
  console.log(
15495
- chalk157.bold(`Rename: ${oldName} \u2192 ${newName} (${totalRefs} references)
15747
+ chalk159.bold(`Rename: ${oldName} \u2192 ${newName} (${totalRefs} references)
15496
15748
  `)
15497
15749
  );
15498
15750
  for (const [refFile, lines] of grouped) {
15499
15751
  console.log(
15500
- ` ${chalk157.dim(refFile)}: lines ${chalk157.cyan(lines.join(", "))}`
15752
+ ` ${chalk159.dim(refFile)}: lines ${chalk159.cyan(lines.join(", "))}`
15501
15753
  );
15502
15754
  }
15503
15755
  if (options2.apply) {
15504
15756
  symbol.rename(newName);
15505
15757
  await project.save();
15506
- console.log(chalk157.green(`
15758
+ console.log(chalk159.green(`
15507
15759
  Renamed ${oldName} \u2192 ${newName}`));
15508
15760
  } else {
15509
- console.log(chalk157.dim("\nDry run. Use --apply to execute."));
15761
+ console.log(chalk159.dim("\nDry run. Use --apply to execute."));
15510
15762
  }
15511
15763
  }
15512
15764
 
15513
15765
  // src/commands/refactor/restructure/index.ts
15514
15766
  import path48 from "path";
15515
- import chalk160 from "chalk";
15767
+ import chalk162 from "chalk";
15516
15768
 
15517
15769
  // src/commands/refactor/restructure/clusterDirectories.ts
15518
15770
  import path42 from "path";
@@ -15591,50 +15843,50 @@ function clusterFiles(graph) {
15591
15843
 
15592
15844
  // src/commands/refactor/restructure/displayPlan.ts
15593
15845
  import path44 from "path";
15594
- import chalk158 from "chalk";
15846
+ import chalk160 from "chalk";
15595
15847
  function relPath(filePath) {
15596
15848
  return path44.relative(process.cwd(), filePath);
15597
15849
  }
15598
15850
  function displayMoves(plan2) {
15599
15851
  if (plan2.moves.length === 0) return;
15600
- console.log(chalk158.bold("\nFile moves:"));
15852
+ console.log(chalk160.bold("\nFile moves:"));
15601
15853
  for (const move of plan2.moves) {
15602
15854
  console.log(
15603
- ` ${chalk158.red(relPath(move.from))} \u2192 ${chalk158.green(relPath(move.to))}`
15855
+ ` ${chalk160.red(relPath(move.from))} \u2192 ${chalk160.green(relPath(move.to))}`
15604
15856
  );
15605
- console.log(chalk158.dim(` ${move.reason}`));
15857
+ console.log(chalk160.dim(` ${move.reason}`));
15606
15858
  }
15607
15859
  }
15608
15860
  function displayRewrites(rewrites) {
15609
15861
  if (rewrites.length === 0) return;
15610
15862
  const affectedFiles = new Set(rewrites.map((r) => r.file));
15611
- console.log(chalk158.bold(`
15863
+ console.log(chalk160.bold(`
15612
15864
  Import rewrites (${affectedFiles.size} files):`));
15613
15865
  for (const file of affectedFiles) {
15614
- console.log(` ${chalk158.cyan(relPath(file))}:`);
15866
+ console.log(` ${chalk160.cyan(relPath(file))}:`);
15615
15867
  for (const { oldSpecifier, newSpecifier } of rewrites.filter(
15616
15868
  (r) => r.file === file
15617
15869
  )) {
15618
15870
  console.log(
15619
- ` ${chalk158.red(`"${oldSpecifier}"`)} \u2192 ${chalk158.green(`"${newSpecifier}"`)}`
15871
+ ` ${chalk160.red(`"${oldSpecifier}"`)} \u2192 ${chalk160.green(`"${newSpecifier}"`)}`
15620
15872
  );
15621
15873
  }
15622
15874
  }
15623
15875
  }
15624
15876
  function displayPlan2(plan2) {
15625
15877
  if (plan2.warnings.length > 0) {
15626
- console.log(chalk158.yellow("\nWarnings:"));
15627
- for (const w of plan2.warnings) console.log(chalk158.yellow(` ${w}`));
15878
+ console.log(chalk160.yellow("\nWarnings:"));
15879
+ for (const w of plan2.warnings) console.log(chalk160.yellow(` ${w}`));
15628
15880
  }
15629
15881
  if (plan2.newDirectories.length > 0) {
15630
- console.log(chalk158.bold("\nNew directories:"));
15882
+ console.log(chalk160.bold("\nNew directories:"));
15631
15883
  for (const dir of plan2.newDirectories)
15632
- console.log(chalk158.green(` ${dir}/`));
15884
+ console.log(chalk160.green(` ${dir}/`));
15633
15885
  }
15634
15886
  displayMoves(plan2);
15635
15887
  displayRewrites(plan2.rewrites);
15636
15888
  console.log(
15637
- chalk158.dim(
15889
+ chalk160.dim(
15638
15890
  `
15639
15891
  Summary: ${plan2.moves.length} file(s) moved, ${plan2.rewrites.length} imports rewritten`
15640
15892
  )
@@ -15644,18 +15896,18 @@ Summary: ${plan2.moves.length} file(s) moved, ${plan2.rewrites.length} imports r
15644
15896
  // src/commands/refactor/restructure/executePlan.ts
15645
15897
  import fs27 from "fs";
15646
15898
  import path45 from "path";
15647
- import chalk159 from "chalk";
15899
+ import chalk161 from "chalk";
15648
15900
  function executePlan(plan2) {
15649
15901
  const updatedContents = applyRewrites(plan2.rewrites);
15650
15902
  for (const [file, content] of updatedContents) {
15651
15903
  fs27.writeFileSync(file, content, "utf8");
15652
15904
  console.log(
15653
- chalk159.cyan(` Rewrote imports in ${path45.relative(process.cwd(), file)}`)
15905
+ chalk161.cyan(` Rewrote imports in ${path45.relative(process.cwd(), file)}`)
15654
15906
  );
15655
15907
  }
15656
15908
  for (const dir of plan2.newDirectories) {
15657
15909
  fs27.mkdirSync(dir, { recursive: true });
15658
- console.log(chalk159.green(` Created ${path45.relative(process.cwd(), dir)}/`));
15910
+ console.log(chalk161.green(` Created ${path45.relative(process.cwd(), dir)}/`));
15659
15911
  }
15660
15912
  for (const move of plan2.moves) {
15661
15913
  const targetDir = path45.dirname(move.to);
@@ -15664,7 +15916,7 @@ function executePlan(plan2) {
15664
15916
  }
15665
15917
  fs27.renameSync(move.from, move.to);
15666
15918
  console.log(
15667
- chalk159.white(
15919
+ chalk161.white(
15668
15920
  ` Moved ${path45.relative(process.cwd(), move.from)} \u2192 ${path45.relative(process.cwd(), move.to)}`
15669
15921
  )
15670
15922
  );
@@ -15679,7 +15931,7 @@ function removeEmptyDirectories(dirs) {
15679
15931
  if (entries.length === 0) {
15680
15932
  fs27.rmdirSync(dir);
15681
15933
  console.log(
15682
- chalk159.dim(
15934
+ chalk161.dim(
15683
15935
  ` Removed empty directory ${path45.relative(process.cwd(), dir)}`
15684
15936
  )
15685
15937
  );
@@ -15812,22 +16064,22 @@ async function restructure(pattern2, options2 = {}) {
15812
16064
  const targetPattern = pattern2 ?? "src";
15813
16065
  const files = findSourceFiles2(targetPattern);
15814
16066
  if (files.length === 0) {
15815
- console.log(chalk160.yellow("No files found matching pattern"));
16067
+ console.log(chalk162.yellow("No files found matching pattern"));
15816
16068
  return;
15817
16069
  }
15818
16070
  const tsConfigPath = path48.resolve("tsconfig.json");
15819
16071
  const plan2 = buildPlan3(files, tsConfigPath);
15820
16072
  if (plan2.moves.length === 0) {
15821
- console.log(chalk160.green("No restructuring needed"));
16073
+ console.log(chalk162.green("No restructuring needed"));
15822
16074
  return;
15823
16075
  }
15824
16076
  displayPlan2(plan2);
15825
16077
  if (options2.apply) {
15826
- console.log(chalk160.bold("\nApplying changes..."));
16078
+ console.log(chalk162.bold("\nApplying changes..."));
15827
16079
  executePlan(plan2);
15828
- console.log(chalk160.green("\nRestructuring complete"));
16080
+ console.log(chalk162.green("\nRestructuring complete"));
15829
16081
  } else {
15830
- console.log(chalk160.dim("\nDry run. Use --apply to execute."));
16082
+ console.log(chalk162.dim("\nDry run. Use --apply to execute."));
15831
16083
  }
15832
16084
  }
15833
16085
 
@@ -15982,11 +16234,11 @@ ${annotateDiffWithLineNumbers(context.diff.trimEnd())}
15982
16234
  }
15983
16235
 
15984
16236
  // src/commands/review/buildReviewPaths.ts
15985
- import { homedir as homedir14 } from "os";
15986
- import { basename as basename7, join as join45 } from "path";
16237
+ import { homedir as homedir15 } from "os";
16238
+ import { basename as basename7, join as join47 } from "path";
15987
16239
  function buildReviewPaths(repoRoot, key) {
15988
- const reviewDir = join45(
15989
- homedir14(),
16240
+ const reviewDir = join47(
16241
+ homedir15(),
15990
16242
  ".assist",
15991
16243
  "reviews",
15992
16244
  basename7(repoRoot),
@@ -15994,10 +16246,10 @@ function buildReviewPaths(repoRoot, key) {
15994
16246
  );
15995
16247
  return {
15996
16248
  reviewDir,
15997
- requestPath: join45(reviewDir, "request.md"),
15998
- claudePath: join45(reviewDir, "claude.md"),
15999
- codexPath: join45(reviewDir, "codex.md"),
16000
- synthesisPath: join45(reviewDir, "synthesis.md")
16249
+ requestPath: join47(reviewDir, "request.md"),
16250
+ claudePath: join47(reviewDir, "claude.md"),
16251
+ codexPath: join47(reviewDir, "codex.md"),
16252
+ synthesisPath: join47(reviewDir, "synthesis.md")
16001
16253
  };
16002
16254
  }
16003
16255
 
@@ -16140,7 +16392,7 @@ function gatherContext() {
16140
16392
  }
16141
16393
 
16142
16394
  // src/commands/review/postReviewToPr.ts
16143
- import { readFileSync as readFileSync33 } from "fs";
16395
+ import { readFileSync as readFileSync34 } from "fs";
16144
16396
 
16145
16397
  // src/commands/review/parseFindings.ts
16146
16398
  var SEVERITIES = ["blocker", "major", "minor", "nit"];
@@ -16396,18 +16648,18 @@ function partitionFindingsByDiff(findings, index3) {
16396
16648
  }
16397
16649
 
16398
16650
  // src/commands/review/warnOutOfDiff.ts
16399
- import chalk161 from "chalk";
16651
+ import chalk163 from "chalk";
16400
16652
  function warnOutOfDiff(outOfDiff) {
16401
16653
  if (outOfDiff.length === 0) return;
16402
16654
  console.warn(
16403
- chalk161.yellow(
16655
+ chalk163.yellow(
16404
16656
  `Skipped ${outOfDiff.length} finding(s) whose lines fall outside the PR diff (GitHub would silently drop these):`
16405
16657
  )
16406
16658
  );
16407
16659
  for (const finding of outOfDiff) {
16408
16660
  const range = finding.startLine !== void 0 ? `${finding.startLine}-${finding.line}` : `${finding.line}`;
16409
16661
  console.warn(
16410
- ` ${chalk161.yellow("\xB7")} ${finding.title} ${chalk161.dim(
16662
+ ` ${chalk163.yellow("\xB7")} ${finding.title} ${chalk163.dim(
16411
16663
  `(${finding.file}:${range})`
16412
16664
  )}`
16413
16665
  );
@@ -16426,18 +16678,18 @@ function selectInDiffFindings(lineBound, prDiff) {
16426
16678
  }
16427
16679
 
16428
16680
  // src/commands/review/warnUnlocated.ts
16429
- import chalk162 from "chalk";
16681
+ import chalk164 from "chalk";
16430
16682
  function warnUnlocated(unlocated) {
16431
16683
  if (unlocated.length === 0) return;
16432
16684
  console.warn(
16433
- chalk162.yellow(
16685
+ chalk164.yellow(
16434
16686
  `Skipped ${unlocated.length} finding(s) without a parseable file:line:`
16435
16687
  )
16436
16688
  );
16437
16689
  for (const finding of unlocated) {
16438
- const where = finding.location || chalk162.dim("missing");
16690
+ const where = finding.location || chalk164.dim("missing");
16439
16691
  console.warn(
16440
- ` ${chalk162.yellow("\xB7")} ${finding.title} ${chalk162.dim(`(${where})`)}`
16692
+ ` ${chalk164.yellow("\xB7")} ${finding.title} ${chalk164.dim(`(${where})`)}`
16441
16693
  );
16442
16694
  }
16443
16695
  }
@@ -16450,7 +16702,7 @@ async function confirmPost(prNumber, count6, options2) {
16450
16702
  async function postReviewToPr(synthesisPath, options2) {
16451
16703
  const prInfo = fetchPrDiffInfo();
16452
16704
  const prNumber = prInfo.prNumber;
16453
- const markdown = readFileSync33(synthesisPath, "utf8");
16705
+ const markdown = readFileSync34(synthesisPath, "utf8");
16454
16706
  const findings = parseFindings(markdown);
16455
16707
  if (findings.length === 0) {
16456
16708
  console.log("Synthesis contains no findings; nothing to post.");
@@ -16532,16 +16784,16 @@ async function handlePostSynthesis(synthesisPath, options2) {
16532
16784
  }
16533
16785
 
16534
16786
  // src/commands/review/prepareReviewDir.ts
16535
- import { existsSync as existsSync37, mkdirSync as mkdirSync14, unlinkSync as unlinkSync12, writeFileSync as writeFileSync31 } from "fs";
16787
+ import { existsSync as existsSync38, mkdirSync as mkdirSync15, unlinkSync as unlinkSync14, writeFileSync as writeFileSync33 } from "fs";
16536
16788
  function clearReviewFiles(paths) {
16537
16789
  for (const path57 of [paths.claudePath, paths.codexPath, paths.synthesisPath]) {
16538
- if (existsSync37(path57)) unlinkSync12(path57);
16790
+ if (existsSync38(path57)) unlinkSync14(path57);
16539
16791
  }
16540
16792
  }
16541
16793
  function prepareReviewDir(paths, requestBody, force) {
16542
- mkdirSync14(paths.reviewDir, { recursive: true });
16794
+ mkdirSync15(paths.reviewDir, { recursive: true });
16543
16795
  if (force) clearReviewFiles(paths);
16544
- writeFileSync31(paths.requestPath, requestBody);
16796
+ writeFileSync33(paths.requestPath, requestBody);
16545
16797
  }
16546
16798
 
16547
16799
  // src/commands/review/runApplySession.ts
@@ -16603,11 +16855,11 @@ async function runBacklogSession(synthesisPath) {
16603
16855
  }
16604
16856
 
16605
16857
  // src/commands/review/cachedReviewerResult.ts
16606
- import { statSync as statSync4 } from "fs";
16858
+ import { statSync as statSync5 } from "fs";
16607
16859
  function cachedReviewerResult(name, outputPath) {
16608
16860
  let size;
16609
16861
  try {
16610
- size = statSync4(outputPath).size;
16862
+ size = statSync5(outputPath).size;
16611
16863
  } catch {
16612
16864
  return null;
16613
16865
  }
@@ -16820,7 +17072,7 @@ function printReviewerFailures(results) {
16820
17072
  }
16821
17073
 
16822
17074
  // src/commands/review/runAndSynthesise.ts
16823
- import { existsSync as existsSync39, unlinkSync as unlinkSync14 } from "fs";
17075
+ import { existsSync as existsSync40, unlinkSync as unlinkSync16 } from "fs";
16824
17076
 
16825
17077
  // src/commands/review/buildReviewerStdin.ts
16826
17078
  var REVIEW_PROMPT = `You are acting as a reviewer for a proposed code change made by another engineer. The full review request \u2014 branch, base, changed files, and unified diff \u2014 is in the request file whose absolute path is given below.
@@ -16886,7 +17138,7 @@ The review request is at: ${requestPath}
16886
17138
  }
16887
17139
 
16888
17140
  // src/commands/review/runClaudeReviewer.ts
16889
- import { writeFileSync as writeFileSync32 } from "fs";
17141
+ import { writeFileSync as writeFileSync34 } from "fs";
16890
17142
 
16891
17143
  // src/commands/review/finaliseReviewerSpinner.ts
16892
17144
  var SUMMARY_MAX_LEN = 80;
@@ -17222,7 +17474,7 @@ async function runClaudeReviewer(spec) {
17222
17474
  }
17223
17475
  });
17224
17476
  if (result.exitCode === 0 && finalText)
17225
- writeFileSync32(spec.outputPath, finalText);
17477
+ writeFileSync34(spec.outputPath, finalText);
17226
17478
  return finaliseReviewerRun({ ...spec, command }, spinner, result);
17227
17479
  }
17228
17480
 
@@ -17240,7 +17492,7 @@ function resolveClaude(args) {
17240
17492
  }
17241
17493
 
17242
17494
  // src/commands/review/runCodexReviewer.ts
17243
- import { existsSync as existsSync38, unlinkSync as unlinkSync13 } from "fs";
17495
+ import { existsSync as existsSync39, unlinkSync as unlinkSync15 } from "fs";
17244
17496
 
17245
17497
  // src/commands/review/parseCodexEvent.ts
17246
17498
  function isItemStarted(value) {
@@ -17292,8 +17544,8 @@ async function runCodexReviewer(spec) {
17292
17544
  reportReviewerToolUse(spec.name, event, spinner);
17293
17545
  }
17294
17546
  });
17295
- if (result.exitCode !== 0 && existsSync38(spec.outputPath)) {
17296
- unlinkSync13(spec.outputPath);
17547
+ if (result.exitCode !== 0 && existsSync39(spec.outputPath)) {
17548
+ unlinkSync15(spec.outputPath);
17297
17549
  }
17298
17550
  return finaliseReviewerRun({ ...spec, command }, spinner, result);
17299
17551
  }
@@ -17334,7 +17586,7 @@ async function runReviewers(reviewDir, claudePath, codexPath, stdinPrompt, optio
17334
17586
  }
17335
17587
 
17336
17588
  // src/commands/review/synthesise.ts
17337
- import { readFileSync as readFileSync34 } from "fs";
17589
+ import { readFileSync as readFileSync35 } from "fs";
17338
17590
 
17339
17591
  // src/commands/review/buildSynthesisStdin.ts
17340
17592
  var SYNTHESIS_PROMPT = `You are consolidating two independent code reviews of the same change. The original review request is in request.md. The two reviews are in claude.md and codex.md in the current working directory.
@@ -17390,7 +17642,7 @@ Files:
17390
17642
 
17391
17643
  // src/commands/review/synthesise.ts
17392
17644
  function printSummary2(synthesisPath) {
17393
- const markdown = readFileSync34(synthesisPath, "utf8");
17645
+ const markdown = readFileSync35(synthesisPath, "utf8");
17394
17646
  console.log("");
17395
17647
  console.log(buildReviewSummary(markdown));
17396
17648
  console.log("");
@@ -17438,8 +17690,8 @@ async function runAndSynthesise(args) {
17438
17690
  console.error("Both reviewers failed; skipping synthesis.");
17439
17691
  return { ok: false, failures };
17440
17692
  }
17441
- if (anyFresh && existsSync39(paths.synthesisPath)) {
17442
- unlinkSync14(paths.synthesisPath);
17693
+ if (anyFresh && existsSync40(paths.synthesisPath)) {
17694
+ unlinkSync16(paths.synthesisPath);
17443
17695
  }
17444
17696
  const synthesisResult = await synthesise(paths, { multi });
17445
17697
  if (synthesisResult.exitCode !== 0) failures.push(synthesisResult);
@@ -17608,7 +17860,7 @@ function registerReview(program2) {
17608
17860
  }
17609
17861
 
17610
17862
  // src/commands/seq/seqAuth.ts
17611
- import chalk164 from "chalk";
17863
+ import chalk166 from "chalk";
17612
17864
 
17613
17865
  // src/commands/seq/loadConnections.ts
17614
17866
  function loadConnections2() {
@@ -17637,10 +17889,10 @@ function setDefaultConnection(name) {
17637
17889
  }
17638
17890
 
17639
17891
  // src/shared/assertUniqueName.ts
17640
- import chalk163 from "chalk";
17892
+ import chalk165 from "chalk";
17641
17893
  function assertUniqueName(existingNames, name) {
17642
17894
  if (existingNames.includes(name)) {
17643
- console.error(chalk163.red(`Connection "${name}" already exists.`));
17895
+ console.error(chalk165.red(`Connection "${name}" already exists.`));
17644
17896
  process.exit(1);
17645
17897
  }
17646
17898
  }
@@ -17658,16 +17910,16 @@ async function promptConnection2(existingNames) {
17658
17910
  var seqAuth = createConnectionAuth({
17659
17911
  load: loadConnections2,
17660
17912
  save: saveConnections2,
17661
- format: (c) => `${chalk164.bold(c.name)} ${c.url}`,
17913
+ format: (c) => `${chalk166.bold(c.name)} ${c.url}`,
17662
17914
  promptNew: promptConnection2,
17663
17915
  onFirst: (c) => setDefaultConnection(c.name)
17664
17916
  });
17665
17917
 
17666
17918
  // src/commands/seq/seqQuery.ts
17667
- import chalk168 from "chalk";
17919
+ import chalk170 from "chalk";
17668
17920
 
17669
17921
  // src/commands/seq/fetchSeq.ts
17670
- import chalk165 from "chalk";
17922
+ import chalk167 from "chalk";
17671
17923
  async function fetchSeq(conn, path57, params) {
17672
17924
  const url = `${conn.url}${path57}?${params}`;
17673
17925
  const response = await fetch(url, {
@@ -17678,7 +17930,7 @@ async function fetchSeq(conn, path57, params) {
17678
17930
  });
17679
17931
  if (!response.ok) {
17680
17932
  const body = await response.text();
17681
- console.error(chalk165.red(`Seq returned ${response.status}: ${body}`));
17933
+ console.error(chalk167.red(`Seq returned ${response.status}: ${body}`));
17682
17934
  process.exit(1);
17683
17935
  }
17684
17936
  return response;
@@ -17737,23 +17989,23 @@ async function fetchSeqEvents(conn, params) {
17737
17989
  }
17738
17990
 
17739
17991
  // src/commands/seq/formatEvent.ts
17740
- import chalk166 from "chalk";
17992
+ import chalk168 from "chalk";
17741
17993
  function levelColor(level) {
17742
17994
  switch (level) {
17743
17995
  case "Fatal":
17744
- return chalk166.bgRed.white;
17996
+ return chalk168.bgRed.white;
17745
17997
  case "Error":
17746
- return chalk166.red;
17998
+ return chalk168.red;
17747
17999
  case "Warning":
17748
- return chalk166.yellow;
18000
+ return chalk168.yellow;
17749
18001
  case "Information":
17750
- return chalk166.cyan;
18002
+ return chalk168.cyan;
17751
18003
  case "Debug":
17752
- return chalk166.gray;
18004
+ return chalk168.gray;
17753
18005
  case "Verbose":
17754
- return chalk166.dim;
18006
+ return chalk168.dim;
17755
18007
  default:
17756
- return chalk166.white;
18008
+ return chalk168.white;
17757
18009
  }
17758
18010
  }
17759
18011
  function levelAbbrev(level) {
@@ -17794,12 +18046,12 @@ function formatTimestamp(iso) {
17794
18046
  function formatEvent(event) {
17795
18047
  const color = levelColor(event.Level);
17796
18048
  const abbrev = levelAbbrev(event.Level);
17797
- const ts8 = chalk166.dim(formatTimestamp(event.Timestamp));
18049
+ const ts8 = chalk168.dim(formatTimestamp(event.Timestamp));
17798
18050
  const msg = renderMessage(event);
17799
18051
  const lines = [`${ts8} ${color(`[${abbrev}]`)} ${msg}`];
17800
18052
  if (event.Exception) {
17801
18053
  for (const line of event.Exception.split("\n")) {
17802
- lines.push(chalk166.red(` ${line}`));
18054
+ lines.push(chalk168.red(` ${line}`));
17803
18055
  }
17804
18056
  }
17805
18057
  return lines.join("\n");
@@ -17832,11 +18084,11 @@ function rejectTimestampFilter(filter) {
17832
18084
  }
17833
18085
 
17834
18086
  // src/shared/resolveNamedConnection.ts
17835
- import chalk167 from "chalk";
18087
+ import chalk169 from "chalk";
17836
18088
  function resolveNamedConnection(connections, requested, defaultName, kind, authCommand) {
17837
18089
  if (connections.length === 0) {
17838
18090
  console.error(
17839
- chalk167.red(
18091
+ chalk169.red(
17840
18092
  `No ${kind} connections configured. Run '${authCommand}' first.`
17841
18093
  )
17842
18094
  );
@@ -17845,7 +18097,7 @@ function resolveNamedConnection(connections, requested, defaultName, kind, authC
17845
18097
  const target = requested ?? defaultName ?? connections[0].name;
17846
18098
  const connection = connections.find((c) => c.name === target);
17847
18099
  if (!connection) {
17848
- console.error(chalk167.red(`${kind} connection "${target}" not found.`));
18100
+ console.error(chalk169.red(`${kind} connection "${target}" not found.`));
17849
18101
  process.exit(1);
17850
18102
  }
17851
18103
  return connection;
@@ -17874,7 +18126,7 @@ async function seqQuery(filter, options2) {
17874
18126
  new URLSearchParams({ filter, count: String(count6) })
17875
18127
  );
17876
18128
  if (events.length === 0) {
17877
- console.log(chalk168.yellow("No events found."));
18129
+ console.log(chalk170.yellow("No events found."));
17878
18130
  return;
17879
18131
  }
17880
18132
  if (options2.json) {
@@ -17885,11 +18137,11 @@ async function seqQuery(filter, options2) {
17885
18137
  for (const event of chronological) {
17886
18138
  console.log(formatEvent(event));
17887
18139
  }
17888
- console.log(chalk168.dim(`
18140
+ console.log(chalk170.dim(`
17889
18141
  ${events.length} events`));
17890
18142
  if (events.length >= count6) {
17891
18143
  console.log(
17892
- chalk168.yellow(
18144
+ chalk170.yellow(
17893
18145
  `Results limited to ${count6}. Use --count to retrieve more.`
17894
18146
  )
17895
18147
  );
@@ -17897,10 +18149,10 @@ ${events.length} events`));
17897
18149
  }
17898
18150
 
17899
18151
  // src/shared/setNamedDefaultConnection.ts
17900
- import chalk169 from "chalk";
18152
+ import chalk171 from "chalk";
17901
18153
  function setNamedDefaultConnection(connections, name, setDefault, kind) {
17902
18154
  if (!connections.find((c) => c.name === name)) {
17903
- console.error(chalk169.red(`Connection "${name}" not found.`));
18155
+ console.error(chalk171.red(`Connection "${name}" not found.`));
17904
18156
  process.exit(1);
17905
18157
  }
17906
18158
  setDefault(name);
@@ -17948,7 +18200,7 @@ function registerSignal(program2) {
17948
18200
  }
17949
18201
 
17950
18202
  // src/commands/sql/sqlAuth.ts
17951
- import chalk171 from "chalk";
18203
+ import chalk173 from "chalk";
17952
18204
 
17953
18205
  // src/commands/sql/loadConnections.ts
17954
18206
  function loadConnections3() {
@@ -17977,7 +18229,7 @@ function setDefaultConnection2(name) {
17977
18229
  }
17978
18230
 
17979
18231
  // src/commands/sql/promptConnection.ts
17980
- import chalk170 from "chalk";
18232
+ import chalk172 from "chalk";
17981
18233
  async function promptConnection3(existingNames) {
17982
18234
  const name = await promptInput("name", "Connection name:", "default");
17983
18235
  assertUniqueName(existingNames, name);
@@ -17985,7 +18237,7 @@ async function promptConnection3(existingNames) {
17985
18237
  const portStr = await promptInput("port", "Port:", "1433");
17986
18238
  const port = Number.parseInt(portStr, 10);
17987
18239
  if (!Number.isFinite(port)) {
17988
- console.error(chalk170.red(`Invalid port "${portStr}".`));
18240
+ console.error(chalk172.red(`Invalid port "${portStr}".`));
17989
18241
  process.exit(1);
17990
18242
  }
17991
18243
  const user = await promptInput("user", "User:");
@@ -17998,13 +18250,13 @@ async function promptConnection3(existingNames) {
17998
18250
  var sqlAuth = createConnectionAuth({
17999
18251
  load: loadConnections3,
18000
18252
  save: saveConnections3,
18001
- format: (c) => `${chalk171.bold(c.name)} ${c.server}:${c.port}/${c.database} (${c.user})`,
18253
+ format: (c) => `${chalk173.bold(c.name)} ${c.server}:${c.port}/${c.database} (${c.user})`,
18002
18254
  promptNew: promptConnection3,
18003
18255
  onFirst: (c) => setDefaultConnection2(c.name)
18004
18256
  });
18005
18257
 
18006
18258
  // src/commands/sql/printTable.ts
18007
- import chalk172 from "chalk";
18259
+ import chalk174 from "chalk";
18008
18260
  function formatCell(value) {
18009
18261
  if (value === null || value === void 0) return "";
18010
18262
  if (value instanceof Date) return value.toISOString();
@@ -18013,7 +18265,7 @@ function formatCell(value) {
18013
18265
  }
18014
18266
  function printTable(rows) {
18015
18267
  if (rows.length === 0) {
18016
- console.log(chalk172.yellow("(no rows)"));
18268
+ console.log(chalk174.yellow("(no rows)"));
18017
18269
  return;
18018
18270
  }
18019
18271
  const columns = Object.keys(rows[0]);
@@ -18021,13 +18273,13 @@ function printTable(rows) {
18021
18273
  (col) => Math.max(col.length, ...rows.map((r) => formatCell(r[col]).length))
18022
18274
  );
18023
18275
  const header = columns.map((c, i) => c.padEnd(widths[i])).join(" ");
18024
- console.log(chalk172.dim(header));
18025
- console.log(chalk172.dim("-".repeat(header.length)));
18276
+ console.log(chalk174.dim(header));
18277
+ console.log(chalk174.dim("-".repeat(header.length)));
18026
18278
  for (const row of rows) {
18027
18279
  const line = columns.map((c, i) => formatCell(row[c]).padEnd(widths[i])).join(" ");
18028
18280
  console.log(line);
18029
18281
  }
18030
- console.log(chalk172.dim(`
18282
+ console.log(chalk174.dim(`
18031
18283
  ${rows.length} row${rows.length === 1 ? "" : "s"}`));
18032
18284
  }
18033
18285
 
@@ -18087,7 +18339,7 @@ async function sqlColumns(table, connectionName) {
18087
18339
  }
18088
18340
 
18089
18341
  // src/commands/sql/sqlMutate.ts
18090
- import chalk173 from "chalk";
18342
+ import chalk175 from "chalk";
18091
18343
 
18092
18344
  // src/commands/sql/isMutation.ts
18093
18345
  var MUTATION_KEYWORDS = [
@@ -18121,7 +18373,7 @@ function isMutation(sql6) {
18121
18373
  async function sqlMutate(query, connectionName) {
18122
18374
  if (!isMutation(query)) {
18123
18375
  console.error(
18124
- chalk173.red(
18376
+ chalk175.red(
18125
18377
  "assist sql mutate refuses non-mutating statements. Use `assist sql query` instead."
18126
18378
  )
18127
18379
  );
@@ -18131,18 +18383,18 @@ async function sqlMutate(query, connectionName) {
18131
18383
  const pool = await sqlConnect(conn);
18132
18384
  try {
18133
18385
  const result = await pool.request().query(query);
18134
- console.log(chalk173.dim(`${result.rowsAffected.join(", ")} row(s) affected`));
18386
+ console.log(chalk175.dim(`${result.rowsAffected.join(", ")} row(s) affected`));
18135
18387
  } finally {
18136
18388
  await pool.close();
18137
18389
  }
18138
18390
  }
18139
18391
 
18140
18392
  // src/commands/sql/sqlQuery.ts
18141
- import chalk174 from "chalk";
18393
+ import chalk176 from "chalk";
18142
18394
  async function sqlQuery(query, connectionName) {
18143
18395
  if (isMutation(query)) {
18144
18396
  console.error(
18145
- chalk174.red(
18397
+ chalk176.red(
18146
18398
  "assist sql query refuses mutating statements. Use `assist sql mutate` instead."
18147
18399
  )
18148
18400
  );
@@ -18157,7 +18409,7 @@ async function sqlQuery(query, connectionName) {
18157
18409
  printTable(rows);
18158
18410
  } else {
18159
18411
  console.log(
18160
- chalk174.dim(`${result.rowsAffected.join(", ")} row(s) affected`)
18412
+ chalk176.dim(`${result.rowsAffected.join(", ")} row(s) affected`)
18161
18413
  );
18162
18414
  }
18163
18415
  } finally {
@@ -18217,8 +18469,8 @@ function registerSql(program2) {
18217
18469
  }
18218
18470
 
18219
18471
  // src/commands/transcript/shared.ts
18220
- import { existsSync as existsSync40, readdirSync as readdirSync7, statSync as statSync5 } from "fs";
18221
- import { basename as basename8, join as join46, relative as relative2 } from "path";
18472
+ import { existsSync as existsSync41, readdirSync as readdirSync8, statSync as statSync6 } from "fs";
18473
+ import { basename as basename8, join as join48, relative as relative2 } from "path";
18222
18474
  import * as readline2 from "readline";
18223
18475
  var DATE_PREFIX_REGEX = /^\d{4}-\d{2}-\d{2}/;
18224
18476
  function getDatePrefix(daysOffset = 0) {
@@ -18233,11 +18485,11 @@ function isValidDatePrefix(filename) {
18233
18485
  return DATE_PREFIX_REGEX.test(filename);
18234
18486
  }
18235
18487
  function collectFiles(dir, extension) {
18236
- if (!existsSync40(dir)) return [];
18488
+ if (!existsSync41(dir)) return [];
18237
18489
  const results = [];
18238
- for (const entry of readdirSync7(dir)) {
18239
- const fullPath = join46(dir, entry);
18240
- if (statSync5(fullPath).isDirectory()) {
18490
+ for (const entry of readdirSync8(dir)) {
18491
+ const fullPath = join48(dir, entry);
18492
+ if (statSync6(fullPath).isDirectory()) {
18241
18493
  results.push(...collectFiles(fullPath, extension));
18242
18494
  } else if (entry.endsWith(extension)) {
18243
18495
  results.push(fullPath);
@@ -18330,14 +18582,14 @@ async function configure() {
18330
18582
  }
18331
18583
 
18332
18584
  // src/commands/transcript/format/index.ts
18333
- import { existsSync as existsSync42 } from "fs";
18585
+ import { existsSync as existsSync43 } from "fs";
18334
18586
 
18335
18587
  // src/commands/transcript/format/fixInvalidDatePrefixes/index.ts
18336
- import { dirname as dirname22, join as join48 } from "path";
18588
+ import { dirname as dirname22, join as join50 } from "path";
18337
18589
 
18338
18590
  // src/commands/transcript/format/fixInvalidDatePrefixes/promptForDateFix.ts
18339
18591
  import { renameSync as renameSync2 } from "fs";
18340
- import { join as join47 } from "path";
18592
+ import { join as join49 } from "path";
18341
18593
  async function resolveDate(rl, choice) {
18342
18594
  if (choice === "1") return getDatePrefix(0);
18343
18595
  if (choice === "2") return getDatePrefix(-1);
@@ -18352,7 +18604,7 @@ async function resolveDate(rl, choice) {
18352
18604
  }
18353
18605
  function renameWithPrefix(vttDir, vttFile, prefix2) {
18354
18606
  const newFilename = `${prefix2}.${vttFile}`;
18355
- renameSync2(join47(vttDir, vttFile), join47(vttDir, newFilename));
18607
+ renameSync2(join49(vttDir, vttFile), join49(vttDir, newFilename));
18356
18608
  console.log(`Renamed to: ${newFilename}`);
18357
18609
  return newFilename;
18358
18610
  }
@@ -18386,12 +18638,12 @@ async function fixInvalidDatePrefixes(vttFiles) {
18386
18638
  const vttFileDir = dirname22(vttFile.absolutePath);
18387
18639
  const newFilename = await promptForDateFix(vttFile.filename, vttFileDir);
18388
18640
  if (newFilename) {
18389
- const newRelativePath = join48(
18641
+ const newRelativePath = join50(
18390
18642
  dirname22(vttFile.relativePath),
18391
18643
  newFilename
18392
18644
  );
18393
18645
  vttFiles[i] = {
18394
- absolutePath: join48(vttFileDir, newFilename),
18646
+ absolutePath: join50(vttFileDir, newFilename),
18395
18647
  relativePath: newRelativePath,
18396
18648
  filename: newFilename
18397
18649
  };
@@ -18404,8 +18656,8 @@ async function fixInvalidDatePrefixes(vttFiles) {
18404
18656
  }
18405
18657
 
18406
18658
  // src/commands/transcript/format/processVttFile/index.ts
18407
- import { existsSync as existsSync41, mkdirSync as mkdirSync15, readFileSync as readFileSync35, writeFileSync as writeFileSync33 } from "fs";
18408
- import { basename as basename9, dirname as dirname23, join as join49 } from "path";
18659
+ import { existsSync as existsSync42, mkdirSync as mkdirSync16, readFileSync as readFileSync36, writeFileSync as writeFileSync35 } from "fs";
18660
+ import { basename as basename9, dirname as dirname23, join as join51 } from "path";
18409
18661
 
18410
18662
  // src/commands/transcript/cleanText.ts
18411
18663
  function cleanText(text6) {
@@ -18615,22 +18867,22 @@ function toMdFilename(vttFilename) {
18615
18867
  return `${basename9(vttFilename, ".vtt").replace(/\s*Transcription\s*/g, " ").trim()}.md`;
18616
18868
  }
18617
18869
  function resolveOutputDir(relativeDir, transcriptsDir) {
18618
- return relativeDir === "." ? transcriptsDir : join49(transcriptsDir, relativeDir);
18870
+ return relativeDir === "." ? transcriptsDir : join51(transcriptsDir, relativeDir);
18619
18871
  }
18620
18872
  function buildOutputPaths(vttFile, transcriptsDir) {
18621
18873
  const mdFile = toMdFilename(vttFile.filename);
18622
18874
  const relativeDir = dirname23(vttFile.relativePath);
18623
18875
  const outputDir = resolveOutputDir(relativeDir, transcriptsDir);
18624
- const outputPath = join49(outputDir, mdFile);
18876
+ const outputPath = join51(outputDir, mdFile);
18625
18877
  return { outputDir, outputPath, mdFile, relativeDir };
18626
18878
  }
18627
18879
  function logSkipped(relativeDir, mdFile) {
18628
- console.log(`Skipping (already exists): ${join49(relativeDir, mdFile)}`);
18880
+ console.log(`Skipping (already exists): ${join51(relativeDir, mdFile)}`);
18629
18881
  return "skipped";
18630
18882
  }
18631
18883
  function ensureDirectory(dir, label2) {
18632
- if (!existsSync41(dir)) {
18633
- mkdirSync15(dir, { recursive: true });
18884
+ if (!existsSync42(dir)) {
18885
+ mkdirSync16(dir, { recursive: true });
18634
18886
  console.log(`Created ${label2}: ${dir}`);
18635
18887
  }
18636
18888
  }
@@ -18652,10 +18904,10 @@ function logReduction(cueCount, messageCount) {
18652
18904
  }
18653
18905
  function readAndParseCues(inputPath) {
18654
18906
  console.log(`Reading: ${inputPath}`);
18655
- return processCues(readFileSync35(inputPath, "utf8"));
18907
+ return processCues(readFileSync36(inputPath, "utf8"));
18656
18908
  }
18657
18909
  function writeFormatted(outputPath, content) {
18658
- writeFileSync33(outputPath, content, "utf8");
18910
+ writeFileSync35(outputPath, content, "utf8");
18659
18911
  console.log(`Written: ${outputPath}`);
18660
18912
  }
18661
18913
  function convertVttToMarkdown(inputPath, outputPath) {
@@ -18665,7 +18917,7 @@ function convertVttToMarkdown(inputPath, outputPath) {
18665
18917
  logReduction(cues.length, chatMessages.length);
18666
18918
  }
18667
18919
  function tryProcessVtt(vttFile, paths) {
18668
- if (existsSync41(paths.outputPath))
18920
+ if (existsSync42(paths.outputPath))
18669
18921
  return logSkipped(paths.relativeDir, paths.mdFile);
18670
18922
  convertVttToMarkdown(vttFile.absolutePath, paths.outputPath);
18671
18923
  return "processed";
@@ -18691,7 +18943,7 @@ function processAllFiles(vttFiles, transcriptsDir) {
18691
18943
  logSummary(counts);
18692
18944
  }
18693
18945
  function requireVttDir(vttDir) {
18694
- if (!existsSync42(vttDir)) {
18946
+ if (!existsSync43(vttDir)) {
18695
18947
  console.error(`VTT directory not found: ${vttDir}`);
18696
18948
  process.exit(1);
18697
18949
  }
@@ -18723,28 +18975,28 @@ async function format() {
18723
18975
  }
18724
18976
 
18725
18977
  // src/commands/transcript/summarise/index.ts
18726
- import { existsSync as existsSync44 } from "fs";
18727
- import { basename as basename10, dirname as dirname25, join as join51, relative as relative3 } from "path";
18978
+ import { existsSync as existsSync45 } from "fs";
18979
+ import { basename as basename10, dirname as dirname25, join as join53, relative as relative3 } from "path";
18728
18980
 
18729
18981
  // src/commands/transcript/summarise/processStagedFile/index.ts
18730
18982
  import {
18731
- existsSync as existsSync43,
18732
- mkdirSync as mkdirSync16,
18733
- readFileSync as readFileSync36,
18983
+ existsSync as existsSync44,
18984
+ mkdirSync as mkdirSync17,
18985
+ readFileSync as readFileSync37,
18734
18986
  renameSync as renameSync3,
18735
18987
  rmSync as rmSync3
18736
18988
  } from "fs";
18737
- import { dirname as dirname24, join as join50 } from "path";
18989
+ import { dirname as dirname24, join as join52 } from "path";
18738
18990
 
18739
18991
  // src/commands/transcript/summarise/processStagedFile/validateStagedContent.ts
18740
- import chalk175 from "chalk";
18992
+ import chalk177 from "chalk";
18741
18993
  var FULL_TRANSCRIPT_REGEX = /^\[Full Transcript\]\(([^)]+)\)/;
18742
18994
  function validateStagedContent(filename, content) {
18743
18995
  const firstLine = content.split("\n")[0];
18744
18996
  const match = firstLine.match(FULL_TRANSCRIPT_REGEX);
18745
18997
  if (!match) {
18746
18998
  console.error(
18747
- chalk175.red(
18999
+ chalk177.red(
18748
19000
  `Staged file ${filename} missing [Full Transcript](<path>) link on first line.`
18749
19001
  )
18750
19002
  );
@@ -18753,7 +19005,7 @@ function validateStagedContent(filename, content) {
18753
19005
  const contentAfterLink = content.slice(firstLine.length).trim();
18754
19006
  if (!contentAfterLink) {
18755
19007
  console.error(
18756
- chalk175.red(
19008
+ chalk177.red(
18757
19009
  `Staged file ${filename} has no summary content after the transcript link.`
18758
19010
  )
18759
19011
  );
@@ -18763,9 +19015,9 @@ function validateStagedContent(filename, content) {
18763
19015
  }
18764
19016
 
18765
19017
  // src/commands/transcript/summarise/processStagedFile/index.ts
18766
- var STAGING_DIR = join50(process.cwd(), ".assist", "transcript");
19018
+ var STAGING_DIR = join52(process.cwd(), ".assist", "transcript");
18767
19019
  function processStagedFile() {
18768
- if (!existsSync43(STAGING_DIR)) {
19020
+ if (!existsSync44(STAGING_DIR)) {
18769
19021
  return false;
18770
19022
  }
18771
19023
  const stagedFiles = findMdFilesRecursive(STAGING_DIR);
@@ -18774,7 +19026,7 @@ function processStagedFile() {
18774
19026
  }
18775
19027
  const { transcriptsDir, summaryDir } = getTranscriptConfig();
18776
19028
  const stagedFile = stagedFiles[0];
18777
- const content = readFileSync36(stagedFile.absolutePath, "utf8");
19029
+ const content = readFileSync37(stagedFile.absolutePath, "utf8");
18778
19030
  validateStagedContent(stagedFile.filename, content);
18779
19031
  const stagedBaseName = getTranscriptBaseName(stagedFile.filename);
18780
19032
  const transcriptFiles = findMdFilesRecursive(transcriptsDir);
@@ -18787,10 +19039,10 @@ function processStagedFile() {
18787
19039
  );
18788
19040
  process.exit(1);
18789
19041
  }
18790
- const destPath = join50(summaryDir, matchingTranscript.relativePath);
19042
+ const destPath = join52(summaryDir, matchingTranscript.relativePath);
18791
19043
  const destDir = dirname24(destPath);
18792
- if (!existsSync43(destDir)) {
18793
- mkdirSync16(destDir, { recursive: true });
19044
+ if (!existsSync44(destDir)) {
19045
+ mkdirSync17(destDir, { recursive: true });
18794
19046
  }
18795
19047
  renameSync3(stagedFile.absolutePath, destPath);
18796
19048
  const remaining = findMdFilesRecursive(STAGING_DIR);
@@ -18803,7 +19055,7 @@ function processStagedFile() {
18803
19055
  // src/commands/transcript/summarise/index.ts
18804
19056
  function buildRelativeKey(relativePath, baseName) {
18805
19057
  const relDir = dirname25(relativePath);
18806
- return relDir === "." ? baseName : join51(relDir, baseName);
19058
+ return relDir === "." ? baseName : join53(relDir, baseName);
18807
19059
  }
18808
19060
  function buildSummaryIndex(summaryDir) {
18809
19061
  const summaryFiles = findMdFilesRecursive(summaryDir);
@@ -18816,7 +19068,7 @@ function buildSummaryIndex(summaryDir) {
18816
19068
  function summarise2() {
18817
19069
  processStagedFile();
18818
19070
  const { transcriptsDir, summaryDir } = getTranscriptConfig();
18819
- if (!existsSync44(transcriptsDir)) {
19071
+ if (!existsSync45(transcriptsDir)) {
18820
19072
  console.log("No transcripts directory found.");
18821
19073
  return;
18822
19074
  }
@@ -18837,8 +19089,8 @@ function summarise2() {
18837
19089
  }
18838
19090
  const next3 = missing[0];
18839
19091
  const outputFilename = `${getTranscriptBaseName(next3.filename)}.md`;
18840
- const outputPath = join51(STAGING_DIR, outputFilename);
18841
- const summaryFileDir = join51(summaryDir, dirname25(next3.relativePath));
19092
+ const outputPath = join53(STAGING_DIR, outputFilename);
19093
+ const summaryFileDir = join53(summaryDir, dirname25(next3.relativePath));
18842
19094
  const relativeTranscriptPath = encodeURI(
18843
19095
  relative3(summaryFileDir, next3.absolutePath).replace(/\\/g, "/")
18844
19096
  );
@@ -18895,50 +19147,50 @@ function registerVerify(program2) {
18895
19147
 
18896
19148
  // src/commands/voice/devices.ts
18897
19149
  import { spawnSync as spawnSync5 } from "child_process";
18898
- import { join as join53 } from "path";
19150
+ import { join as join55 } from "path";
18899
19151
 
18900
19152
  // src/commands/voice/shared.ts
18901
- import { homedir as homedir15 } from "os";
18902
- import { dirname as dirname26, join as join52 } from "path";
19153
+ import { homedir as homedir16 } from "os";
19154
+ import { dirname as dirname26, join as join54 } from "path";
18903
19155
  import { fileURLToPath as fileURLToPath6 } from "url";
18904
19156
  var __dirname5 = dirname26(fileURLToPath6(import.meta.url));
18905
- var VOICE_DIR = join52(homedir15(), ".assist", "voice");
19157
+ var VOICE_DIR = join54(homedir16(), ".assist", "voice");
18906
19158
  var voicePaths = {
18907
19159
  dir: VOICE_DIR,
18908
- pid: join52(VOICE_DIR, "voice.pid"),
18909
- log: join52(VOICE_DIR, "voice.log"),
18910
- venv: join52(VOICE_DIR, ".venv"),
18911
- lock: join52(VOICE_DIR, "voice.lock")
19160
+ pid: join54(VOICE_DIR, "voice.pid"),
19161
+ log: join54(VOICE_DIR, "voice.log"),
19162
+ venv: join54(VOICE_DIR, ".venv"),
19163
+ lock: join54(VOICE_DIR, "voice.lock")
18912
19164
  };
18913
19165
  function getPythonDir() {
18914
- return join52(__dirname5, "commands", "voice", "python");
19166
+ return join54(__dirname5, "commands", "voice", "python");
18915
19167
  }
18916
19168
  function getVenvPython() {
18917
- return process.platform === "win32" ? join52(voicePaths.venv, "Scripts", "python.exe") : join52(voicePaths.venv, "bin", "python");
19169
+ return process.platform === "win32" ? join54(voicePaths.venv, "Scripts", "python.exe") : join54(voicePaths.venv, "bin", "python");
18918
19170
  }
18919
19171
  function getLockDir() {
18920
19172
  const config = loadConfig();
18921
19173
  return config.voice?.lockDir ?? VOICE_DIR;
18922
19174
  }
18923
19175
  function getLockFile() {
18924
- return join52(getLockDir(), "voice.lock");
19176
+ return join54(getLockDir(), "voice.lock");
18925
19177
  }
18926
19178
 
18927
19179
  // src/commands/voice/devices.ts
18928
19180
  function devices() {
18929
- const script = join53(getPythonDir(), "list_devices.py");
19181
+ const script = join55(getPythonDir(), "list_devices.py");
18930
19182
  spawnSync5(getVenvPython(), [script], { stdio: "inherit" });
18931
19183
  }
18932
19184
 
18933
19185
  // src/commands/voice/logs.ts
18934
- import { existsSync as existsSync45, readFileSync as readFileSync37 } from "fs";
19186
+ import { existsSync as existsSync46, readFileSync as readFileSync38 } from "fs";
18935
19187
  function logs(options2) {
18936
- if (!existsSync45(voicePaths.log)) {
19188
+ if (!existsSync46(voicePaths.log)) {
18937
19189
  console.log("No voice log file found");
18938
19190
  return;
18939
19191
  }
18940
19192
  const count6 = Number.parseInt(options2.lines ?? "150", 10);
18941
- const content = readFileSync37(voicePaths.log, "utf8").trim();
19193
+ const content = readFileSync38(voicePaths.log, "utf8").trim();
18942
19194
  if (!content) {
18943
19195
  console.log("Voice log is empty");
18944
19196
  return;
@@ -18960,13 +19212,13 @@ function logs(options2) {
18960
19212
 
18961
19213
  // src/commands/voice/setup.ts
18962
19214
  import { spawnSync as spawnSync6 } from "child_process";
18963
- import { mkdirSync as mkdirSync18 } from "fs";
18964
- import { join as join55 } from "path";
19215
+ import { mkdirSync as mkdirSync19 } from "fs";
19216
+ import { join as join57 } from "path";
18965
19217
 
18966
19218
  // src/commands/voice/checkLockFile.ts
18967
19219
  import { execSync as execSync48 } from "child_process";
18968
- import { existsSync as existsSync46, mkdirSync as mkdirSync17, readFileSync as readFileSync38, writeFileSync as writeFileSync34 } from "fs";
18969
- import { join as join54 } from "path";
19220
+ import { existsSync as existsSync47, mkdirSync as mkdirSync18, readFileSync as readFileSync39, writeFileSync as writeFileSync36 } from "fs";
19221
+ import { join as join56 } from "path";
18970
19222
  function isProcessAlive2(pid) {
18971
19223
  try {
18972
19224
  process.kill(pid, 0);
@@ -18977,9 +19229,9 @@ function isProcessAlive2(pid) {
18977
19229
  }
18978
19230
  function checkLockFile() {
18979
19231
  const lockFile = getLockFile();
18980
- if (!existsSync46(lockFile)) return;
19232
+ if (!existsSync47(lockFile)) return;
18981
19233
  try {
18982
- const lock2 = JSON.parse(readFileSync38(lockFile, "utf8"));
19234
+ const lock2 = JSON.parse(readFileSync39(lockFile, "utf8"));
18983
19235
  if (lock2.pid && isProcessAlive2(lock2.pid)) {
18984
19236
  console.error(
18985
19237
  `Voice daemon already running (PID ${lock2.pid}, env: ${lock2.env}). Stop it first with: assist voice stop`
@@ -18990,7 +19242,7 @@ function checkLockFile() {
18990
19242
  }
18991
19243
  }
18992
19244
  function bootstrapVenv() {
18993
- if (existsSync46(getVenvPython())) return;
19245
+ if (existsSync47(getVenvPython())) return;
18994
19246
  console.log("Setting up Python environment...");
18995
19247
  const pythonDir = getPythonDir();
18996
19248
  execSync48(
@@ -19003,8 +19255,8 @@ function bootstrapVenv() {
19003
19255
  }
19004
19256
  function writeLockFile(pid) {
19005
19257
  const lockFile = getLockFile();
19006
- mkdirSync17(join54(lockFile, ".."), { recursive: true });
19007
- writeFileSync34(
19258
+ mkdirSync18(join56(lockFile, ".."), { recursive: true });
19259
+ writeFileSync36(
19008
19260
  lockFile,
19009
19261
  JSON.stringify({
19010
19262
  pid,
@@ -19016,10 +19268,10 @@ function writeLockFile(pid) {
19016
19268
 
19017
19269
  // src/commands/voice/setup.ts
19018
19270
  function setup() {
19019
- mkdirSync18(voicePaths.dir, { recursive: true });
19271
+ mkdirSync19(voicePaths.dir, { recursive: true });
19020
19272
  bootstrapVenv();
19021
19273
  console.log("\nDownloading models...\n");
19022
- const script = join55(getPythonDir(), "setup_models.py");
19274
+ const script = join57(getPythonDir(), "setup_models.py");
19023
19275
  const result = spawnSync6(getVenvPython(), [script], {
19024
19276
  stdio: "inherit",
19025
19277
  env: { ...process.env, VOICE_LOG_FILE: voicePaths.log }
@@ -19032,8 +19284,8 @@ function setup() {
19032
19284
 
19033
19285
  // src/commands/voice/start.ts
19034
19286
  import { spawn as spawn7 } from "child_process";
19035
- import { mkdirSync as mkdirSync19, writeFileSync as writeFileSync35 } from "fs";
19036
- import { join as join56 } from "path";
19287
+ import { mkdirSync as mkdirSync20, writeFileSync as writeFileSync37 } from "fs";
19288
+ import { join as join58 } from "path";
19037
19289
 
19038
19290
  // src/commands/voice/buildDaemonEnv.ts
19039
19291
  function buildDaemonEnv(options2) {
@@ -19061,17 +19313,17 @@ function spawnBackground(python, script, env) {
19061
19313
  console.error("Failed to start voice daemon");
19062
19314
  process.exit(1);
19063
19315
  }
19064
- writeFileSync35(voicePaths.pid, String(pid));
19316
+ writeFileSync37(voicePaths.pid, String(pid));
19065
19317
  writeLockFile(pid);
19066
19318
  console.log(`Voice daemon started (PID ${pid})`);
19067
19319
  }
19068
19320
  function start2(options2) {
19069
- mkdirSync19(voicePaths.dir, { recursive: true });
19321
+ mkdirSync20(voicePaths.dir, { recursive: true });
19070
19322
  checkLockFile();
19071
19323
  bootstrapVenv();
19072
19324
  const debug = options2.debug || options2.foreground || process.platform === "win32";
19073
19325
  const env = buildDaemonEnv({ debug });
19074
- const script = join56(getPythonDir(), "voice_daemon.py");
19326
+ const script = join58(getPythonDir(), "voice_daemon.py");
19075
19327
  const python = getVenvPython();
19076
19328
  if (options2.foreground) {
19077
19329
  spawnForeground(python, script, env);
@@ -19081,7 +19333,7 @@ function start2(options2) {
19081
19333
  }
19082
19334
 
19083
19335
  // src/commands/voice/status.ts
19084
- import { existsSync as existsSync47, readFileSync as readFileSync39 } from "fs";
19336
+ import { existsSync as existsSync48, readFileSync as readFileSync40 } from "fs";
19085
19337
  function isProcessAlive3(pid) {
19086
19338
  try {
19087
19339
  process.kill(pid, 0);
@@ -19091,16 +19343,16 @@ function isProcessAlive3(pid) {
19091
19343
  }
19092
19344
  }
19093
19345
  function readRecentLogs(count6) {
19094
- if (!existsSync47(voicePaths.log)) return [];
19095
- const lines = readFileSync39(voicePaths.log, "utf8").trim().split("\n");
19346
+ if (!existsSync48(voicePaths.log)) return [];
19347
+ const lines = readFileSync40(voicePaths.log, "utf8").trim().split("\n");
19096
19348
  return lines.slice(-count6);
19097
19349
  }
19098
19350
  function status() {
19099
- if (!existsSync47(voicePaths.pid)) {
19351
+ if (!existsSync48(voicePaths.pid)) {
19100
19352
  console.log("Voice daemon: not running (no PID file)");
19101
19353
  return;
19102
19354
  }
19103
- const pid = Number.parseInt(readFileSync39(voicePaths.pid, "utf8").trim(), 10);
19355
+ const pid = Number.parseInt(readFileSync40(voicePaths.pid, "utf8").trim(), 10);
19104
19356
  const alive = isProcessAlive3(pid);
19105
19357
  console.log(`Voice daemon: ${alive ? "running" : "dead"} (PID ${pid})`);
19106
19358
  const recent = readRecentLogs(5);
@@ -19119,13 +19371,13 @@ function status() {
19119
19371
  }
19120
19372
 
19121
19373
  // src/commands/voice/stop.ts
19122
- import { existsSync as existsSync48, readFileSync as readFileSync40, unlinkSync as unlinkSync15 } from "fs";
19374
+ import { existsSync as existsSync49, readFileSync as readFileSync41, unlinkSync as unlinkSync17 } from "fs";
19123
19375
  function stop2() {
19124
- if (!existsSync48(voicePaths.pid)) {
19376
+ if (!existsSync49(voicePaths.pid)) {
19125
19377
  console.log("Voice daemon is not running (no PID file)");
19126
19378
  return;
19127
19379
  }
19128
- const pid = Number.parseInt(readFileSync40(voicePaths.pid, "utf8").trim(), 10);
19380
+ const pid = Number.parseInt(readFileSync41(voicePaths.pid, "utf8").trim(), 10);
19129
19381
  try {
19130
19382
  process.kill(pid, "SIGTERM");
19131
19383
  console.log(`Sent SIGTERM to voice daemon (PID ${pid})`);
@@ -19133,12 +19385,12 @@ function stop2() {
19133
19385
  console.log(`Voice daemon (PID ${pid}) is not running`);
19134
19386
  }
19135
19387
  try {
19136
- unlinkSync15(voicePaths.pid);
19388
+ unlinkSync17(voicePaths.pid);
19137
19389
  } catch {
19138
19390
  }
19139
19391
  try {
19140
19392
  const lockFile = getLockFile();
19141
- if (existsSync48(lockFile)) unlinkSync15(lockFile);
19393
+ if (existsSync49(lockFile)) unlinkSync17(lockFile);
19142
19394
  } catch {
19143
19395
  }
19144
19396
  console.log("Voice daemon stopped");
@@ -19156,8 +19408,8 @@ function registerVoice(program2) {
19156
19408
  }
19157
19409
 
19158
19410
  // src/commands/roam/auth.ts
19159
- import { randomBytes } from "crypto";
19160
- import chalk176 from "chalk";
19411
+ import { randomBytes as randomBytes2 } from "crypto";
19412
+ import chalk178 from "chalk";
19161
19413
 
19162
19414
  // src/commands/roam/waitForCallback.ts
19163
19415
  import { createServer as createServer3 } from "http";
@@ -19286,15 +19538,15 @@ async function auth() {
19286
19538
  const existingRoam = config.roam ?? {};
19287
19539
  config.roam = { ...existingRoam, clientId, clientSecret };
19288
19540
  saveGlobalConfig(config);
19289
- const state = randomBytes(16).toString("hex");
19541
+ const state = randomBytes2(16).toString("hex");
19290
19542
  console.log(
19291
- chalk176.yellow("\nEnsure this Redirect URI is set in your Roam OAuth app:")
19543
+ chalk178.yellow("\nEnsure this Redirect URI is set in your Roam OAuth app:")
19292
19544
  );
19293
- console.log(chalk176.white("http://localhost:14523/callback\n"));
19294
- console.log(chalk176.blue("Opening browser for authorization..."));
19295
- console.log(chalk176.dim("Waiting for authorization callback..."));
19545
+ console.log(chalk178.white("http://localhost:14523/callback\n"));
19546
+ console.log(chalk178.blue("Opening browser for authorization..."));
19547
+ console.log(chalk178.dim("Waiting for authorization callback..."));
19296
19548
  const { code, redirectUri } = await authorizeInBrowser(clientId, state);
19297
- console.log(chalk176.dim("Exchanging code for tokens..."));
19549
+ console.log(chalk178.dim("Exchanging code for tokens..."));
19298
19550
  const tokens = await exchangeToken({
19299
19551
  code,
19300
19552
  clientId,
@@ -19310,25 +19562,25 @@ async function auth() {
19310
19562
  };
19311
19563
  saveGlobalConfig(config);
19312
19564
  console.log(
19313
- chalk176.green("Roam credentials and tokens saved to ~/.assist.yml")
19565
+ chalk178.green("Roam credentials and tokens saved to ~/.assist.yml")
19314
19566
  );
19315
19567
  }
19316
19568
 
19317
19569
  // src/commands/roam/postRoamActivity.ts
19318
19570
  import { execFileSync as execFileSync7 } from "child_process";
19319
- import { readdirSync as readdirSync8, readFileSync as readFileSync41, statSync as statSync6 } from "fs";
19320
- import { join as join57 } from "path";
19571
+ import { readdirSync as readdirSync9, readFileSync as readFileSync42, statSync as statSync7 } from "fs";
19572
+ import { join as join59 } from "path";
19321
19573
  function findPortFile(roamDir) {
19322
19574
  let entries;
19323
19575
  try {
19324
- entries = readdirSync8(roamDir);
19576
+ entries = readdirSync9(roamDir);
19325
19577
  } catch {
19326
19578
  return void 0;
19327
19579
  }
19328
19580
  const candidates = entries.filter((name) => /^roam-local-api(-[^.]+)?\.port$/.test(name)).map((name) => {
19329
- const path57 = join57(roamDir, name);
19581
+ const path57 = join59(roamDir, name);
19330
19582
  try {
19331
- return { path: path57, mtimeMs: statSync6(path57).mtimeMs };
19583
+ return { path: path57, mtimeMs: statSync7(path57).mtimeMs };
19332
19584
  } catch {
19333
19585
  return void 0;
19334
19586
  }
@@ -19338,11 +19590,11 @@ function findPortFile(roamDir) {
19338
19590
  function postRoamActivity(app, event) {
19339
19591
  const appData = process.env.APPDATA;
19340
19592
  if (!appData) return;
19341
- const portFile = findPortFile(join57(appData, "Roam"));
19593
+ const portFile = findPortFile(join59(appData, "Roam"));
19342
19594
  if (!portFile) return;
19343
19595
  let port;
19344
19596
  try {
19345
- port = readFileSync41(portFile, "utf8").trim();
19597
+ port = readFileSync42(portFile, "utf8").trim();
19346
19598
  } catch {
19347
19599
  return;
19348
19600
  }
@@ -19484,15 +19736,15 @@ function runPreCommands(pre, cwd) {
19484
19736
 
19485
19737
  // src/commands/run/spawnRunCommand.ts
19486
19738
  import { execFileSync as execFileSync8, spawn as spawn8 } from "child_process";
19487
- import { existsSync as existsSync49 } from "fs";
19488
- import { dirname as dirname27, join as join58, resolve as resolve13 } from "path";
19739
+ import { existsSync as existsSync50 } from "fs";
19740
+ import { dirname as dirname27, join as join60, resolve as resolve13 } from "path";
19489
19741
  function resolveCommand2(command) {
19490
19742
  if (process.platform !== "win32" || command !== "bash") return command;
19491
19743
  try {
19492
19744
  const gitPath = execFileSync8("where", ["git"], { encoding: "utf8" }).trim().split("\r\n")[0];
19493
19745
  const gitRoot = resolve13(dirname27(gitPath), "..");
19494
- const gitBash = join58(gitRoot, "bin", "bash.exe");
19495
- if (existsSync49(gitBash)) return gitBash;
19746
+ const gitBash = join60(gitRoot, "bin", "bash.exe");
19747
+ if (existsSync50(gitBash)) return gitBash;
19496
19748
  } catch {
19497
19749
  }
19498
19750
  return command;
@@ -19577,8 +19829,8 @@ async function run3(name, args) {
19577
19829
  }
19578
19830
 
19579
19831
  // src/commands/run/add.ts
19580
- import { mkdirSync as mkdirSync20, writeFileSync as writeFileSync36 } from "fs";
19581
- import { join as join59 } from "path";
19832
+ import { mkdirSync as mkdirSync21, writeFileSync as writeFileSync38 } from "fs";
19833
+ import { join as join61 } from "path";
19582
19834
 
19583
19835
  // src/commands/run/extractOption.ts
19584
19836
  function extractOption(args, flag) {
@@ -19639,16 +19891,16 @@ function saveNewRunConfig(name, command, args, cwd) {
19639
19891
  saveConfig(config);
19640
19892
  }
19641
19893
  function createCommandFile(name) {
19642
- const dir = join59(".claude", "commands");
19643
- mkdirSync20(dir, { recursive: true });
19894
+ const dir = join61(".claude", "commands");
19895
+ mkdirSync21(dir, { recursive: true });
19644
19896
  const content = `---
19645
19897
  description: Run ${name}
19646
19898
  ---
19647
19899
 
19648
19900
  Run \`assist run ${name} $ARGUMENTS 2>&1\`.
19649
19901
  `;
19650
- const filePath = join59(dir, `${name}.md`);
19651
- writeFileSync36(filePath, content);
19902
+ const filePath = join61(dir, `${name}.md`);
19903
+ writeFileSync38(filePath, content);
19652
19904
  console.log(`Created command file: ${filePath}`);
19653
19905
  }
19654
19906
  function add3() {
@@ -19703,8 +19955,8 @@ function link2() {
19703
19955
  }
19704
19956
 
19705
19957
  // src/commands/run/remove.ts
19706
- import { existsSync as existsSync50, unlinkSync as unlinkSync16 } from "fs";
19707
- import { join as join60 } from "path";
19958
+ import { existsSync as existsSync51, unlinkSync as unlinkSync18 } from "fs";
19959
+ import { join as join62 } from "path";
19708
19960
  function findRemoveIndex() {
19709
19961
  const idx = process.argv.indexOf("remove");
19710
19962
  if (idx === -1 || idx + 1 >= process.argv.length) return -1;
@@ -19719,9 +19971,9 @@ function parseRemoveName() {
19719
19971
  return process.argv[idx + 1];
19720
19972
  }
19721
19973
  function deleteCommandFile(name) {
19722
- const filePath = join60(".claude", "commands", `${name}.md`);
19723
- if (existsSync50(filePath)) {
19724
- unlinkSync16(filePath);
19974
+ const filePath = join62(".claude", "commands", `${name}.md`);
19975
+ if (existsSync51(filePath)) {
19976
+ unlinkSync18(filePath);
19725
19977
  console.log(`Deleted command file: ${filePath}`);
19726
19978
  }
19727
19979
  }
@@ -19759,10 +20011,10 @@ function registerRun(program2) {
19759
20011
 
19760
20012
  // src/commands/screenshot/index.ts
19761
20013
  import { execSync as execSync50 } from "child_process";
19762
- import { existsSync as existsSync51, mkdirSync as mkdirSync21, unlinkSync as unlinkSync17, writeFileSync as writeFileSync37 } from "fs";
20014
+ import { existsSync as existsSync52, mkdirSync as mkdirSync22, unlinkSync as unlinkSync19, writeFileSync as writeFileSync39 } from "fs";
19763
20015
  import { tmpdir as tmpdir7 } from "os";
19764
- import { join as join61, resolve as resolve15 } from "path";
19765
- import chalk177 from "chalk";
20016
+ import { join as join63, resolve as resolve15 } from "path";
20017
+ import chalk179 from "chalk";
19766
20018
 
19767
20019
  // src/commands/screenshot/captureWindowPs1.ts
19768
20020
  var captureWindowPs1 = `
@@ -19891,35 +20143,35 @@ Write-Output $OutputPath
19891
20143
 
19892
20144
  // src/commands/screenshot/index.ts
19893
20145
  function buildOutputPath(outputDir, processName) {
19894
- if (!existsSync51(outputDir)) {
19895
- mkdirSync21(outputDir, { recursive: true });
20146
+ if (!existsSync52(outputDir)) {
20147
+ mkdirSync22(outputDir, { recursive: true });
19896
20148
  }
19897
20149
  const timestamp4 = (/* @__PURE__ */ new Date()).toISOString().replace(/[:.]/g, "-");
19898
20150
  return resolve15(outputDir, `${processName}-${timestamp4}.png`);
19899
20151
  }
19900
20152
  function runPowerShellScript(processName, outputPath) {
19901
- const scriptPath = join61(tmpdir7(), `assist-screenshot-${Date.now()}.ps1`);
19902
- writeFileSync37(scriptPath, captureWindowPs1, "utf8");
20153
+ const scriptPath = join63(tmpdir7(), `assist-screenshot-${Date.now()}.ps1`);
20154
+ writeFileSync39(scriptPath, captureWindowPs1, "utf8");
19903
20155
  try {
19904
20156
  execSync50(
19905
20157
  `powershell -NoProfile -ExecutionPolicy Bypass -File "${scriptPath}" -ProcessName "${processName}" -OutputPath "${outputPath}"`,
19906
20158
  { stdio: ["ignore", "pipe", "pipe"], encoding: "utf8" }
19907
20159
  );
19908
20160
  } finally {
19909
- unlinkSync17(scriptPath);
20161
+ unlinkSync19(scriptPath);
19910
20162
  }
19911
20163
  }
19912
20164
  function screenshot(processName) {
19913
20165
  const config = loadConfig();
19914
20166
  const outputDir = resolve15(config.screenshot.outputDir);
19915
20167
  const outputPath = buildOutputPath(outputDir, processName);
19916
- console.log(chalk177.gray(`Capturing window for process "${processName}" ...`));
20168
+ console.log(chalk179.gray(`Capturing window for process "${processName}" ...`));
19917
20169
  try {
19918
20170
  runPowerShellScript(processName, outputPath);
19919
- console.log(chalk177.green(`Screenshot saved: ${outputPath}`));
20171
+ console.log(chalk179.green(`Screenshot saved: ${outputPath}`));
19920
20172
  } catch (error) {
19921
20173
  const msg = error instanceof Error ? error.message : String(error);
19922
- console.error(chalk177.red(`Failed to capture screenshot: ${msg}`));
20174
+ console.error(chalk179.red(`Failed to capture screenshot: ${msg}`));
19923
20175
  process.exit(1);
19924
20176
  }
19925
20177
  }
@@ -19975,7 +20227,7 @@ function applyLine(result, pending, line) {
19975
20227
  }
19976
20228
 
19977
20229
  // src/commands/sessions/daemon/reportStolenSocket.ts
19978
- import { readFileSync as readFileSync42 } from "fs";
20230
+ import { readFileSync as readFileSync43 } from "fs";
19979
20231
  function reportStolenSocket(socketPid) {
19980
20232
  if (!socketPid) return;
19981
20233
  const filePid = readPidFile();
@@ -19987,7 +20239,7 @@ function reportStolenSocket(socketPid) {
19987
20239
  function readPidFile() {
19988
20240
  try {
19989
20241
  const pid = Number.parseInt(
19990
- readFileSync42(daemonPaths.pid, "utf8").trim(),
20242
+ readFileSync43(daemonPaths.pid, "utf8").trim(),
19991
20243
  10
19992
20244
  );
19993
20245
  return Number.isInteger(pid) ? pid : void 0;
@@ -20152,7 +20404,7 @@ function requestDrain(socket) {
20152
20404
  }
20153
20405
 
20154
20406
  // src/commands/sessions/daemon/runDaemon.ts
20155
- import { mkdirSync as mkdirSync23 } from "fs";
20407
+ import { mkdirSync as mkdirSync24 } from "fs";
20156
20408
 
20157
20409
  // src/commands/sessions/daemon/createAutoExit.ts
20158
20410
  var DEFAULT_GRACE_MS = 6e4;
@@ -20329,7 +20581,7 @@ var ClientHub = class extends Set {
20329
20581
  import * as pty from "node-pty";
20330
20582
 
20331
20583
  // src/commands/sessions/daemon/ensureSpawnHelperExecutable.ts
20332
- import { chmodSync, existsSync as existsSync52, statSync as statSync7 } from "fs";
20584
+ import { chmodSync, existsSync as existsSync53, statSync as statSync8 } from "fs";
20333
20585
  import { createRequire as createRequire3 } from "module";
20334
20586
  import path49 from "path";
20335
20587
  var require4 = createRequire3(import.meta.url);
@@ -20344,8 +20596,8 @@ function ensureSpawnHelperExecutable() {
20344
20596
  `${process.platform}-${process.arch}`,
20345
20597
  "spawn-helper"
20346
20598
  );
20347
- if (!existsSync52(helper)) return;
20348
- const mode = statSync7(helper).mode;
20599
+ if (!existsSync53(helper)) return;
20600
+ const mode = statSync8(helper).mode;
20349
20601
  if ((mode & 73) === 0) chmodSync(helper, mode | 493);
20350
20602
  }
20351
20603
 
@@ -20763,7 +21015,7 @@ function resumeSession(id2, sessionId, cwd, name) {
20763
21015
  }
20764
21016
 
20765
21017
  // src/commands/sessions/daemon/watchActivity.ts
20766
- import { existsSync as existsSync53, mkdirSync as mkdirSync22, watch } from "fs";
21018
+ import { existsSync as existsSync54, mkdirSync as mkdirSync23, watch } from "fs";
20767
21019
  import { dirname as dirname28 } from "path";
20768
21020
 
20769
21021
  // src/commands/sessions/daemon/applyReviewPause.ts
@@ -20784,7 +21036,7 @@ function watchActivity(session, notify2) {
20784
21036
  const path57 = activityPath(session.id);
20785
21037
  const dir = dirname28(path57);
20786
21038
  try {
20787
- mkdirSync22(dir, { recursive: true });
21039
+ mkdirSync23(dir, { recursive: true });
20788
21040
  } catch {
20789
21041
  return;
20790
21042
  }
@@ -20805,7 +21057,7 @@ function watchActivity(session, notify2) {
20805
21057
  if (timer) clearTimeout(timer);
20806
21058
  timer = setTimeout(read, DEBOUNCE_MS);
20807
21059
  });
20808
- if (existsSync53(path57)) read();
21060
+ if (existsSync54(path57)) read();
20809
21061
  }
20810
21062
  function refreshActivity(session) {
20811
21063
  if (session.commandType !== "assist" || !session.cwd) return;
@@ -21614,7 +21866,7 @@ var SessionManager = class {
21614
21866
  };
21615
21867
 
21616
21868
  // src/commands/sessions/daemon/startDaemonServer.ts
21617
- import { unlinkSync as unlinkSync19 } from "fs";
21869
+ import { unlinkSync as unlinkSync21 } from "fs";
21618
21870
  import * as net3 from "net";
21619
21871
 
21620
21872
  // src/commands/sessions/daemon/handleConnection.ts
@@ -22021,10 +22273,10 @@ function handleConnection(socket, manager) {
22021
22273
  }
22022
22274
 
22023
22275
  // src/commands/sessions/daemon/onListening.ts
22024
- import { unlinkSync as unlinkSync18, writeFileSync as writeFileSync38 } from "fs";
22276
+ import { unlinkSync as unlinkSync20, writeFileSync as writeFileSync40 } from "fs";
22025
22277
 
22026
22278
  // src/commands/sessions/daemon/startPidFileWatchdog.ts
22027
- import { readFileSync as readFileSync43 } from "fs";
22279
+ import { readFileSync as readFileSync44 } from "fs";
22028
22280
  var WATCHDOG_INTERVAL_MS = 5e3;
22029
22281
  function startPidFileWatchdog(onLost, intervalMs = WATCHDOG_INTERVAL_MS) {
22030
22282
  const timer = setInterval(() => {
@@ -22035,7 +22287,7 @@ function startPidFileWatchdog(onLost, intervalMs = WATCHDOG_INTERVAL_MS) {
22035
22287
  }
22036
22288
  function ownsPidFile() {
22037
22289
  try {
22038
- return readFileSync43(daemonPaths.pid, "utf8").trim() === String(process.pid);
22290
+ return readFileSync44(daemonPaths.pid, "utf8").trim() === String(process.pid);
22039
22291
  } catch {
22040
22292
  return false;
22041
22293
  }
@@ -22043,7 +22295,7 @@ function ownsPidFile() {
22043
22295
 
22044
22296
  // src/commands/sessions/daemon/onListening.ts
22045
22297
  function onListening(manager, checkAutoExit) {
22046
- writeFileSync38(daemonPaths.pid, String(process.pid));
22298
+ writeFileSync40(daemonPaths.pid, String(process.pid));
22047
22299
  startPidFileWatchdog(() => {
22048
22300
  daemonLog("lost daemon.pid ownership; shutting down sessions and exiting");
22049
22301
  manager.shutdown();
@@ -22062,12 +22314,12 @@ function onListening(manager, checkAutoExit) {
22062
22314
  function cleanupOwnedFiles() {
22063
22315
  if (!ownsPidFile()) return;
22064
22316
  try {
22065
- unlinkSync18(daemonPaths.pid);
22317
+ unlinkSync20(daemonPaths.pid);
22066
22318
  } catch {
22067
22319
  }
22068
22320
  if (process.platform !== "win32") {
22069
22321
  try {
22070
- unlinkSync18(daemonPaths.socket);
22322
+ unlinkSync20(daemonPaths.socket);
22071
22323
  } catch {
22072
22324
  }
22073
22325
  }
@@ -22110,7 +22362,7 @@ async function recoverFromAddrInUse(server, manager, checkAutoExit) {
22110
22362
  daemonLog("removing stale socket left by a crashed daemon");
22111
22363
  if (process.platform !== "win32") {
22112
22364
  try {
22113
- unlinkSync19(daemonPaths.socket);
22365
+ unlinkSync21(daemonPaths.socket);
22114
22366
  } catch {
22115
22367
  }
22116
22368
  }
@@ -22119,7 +22371,7 @@ async function recoverFromAddrInUse(server, manager, checkAutoExit) {
22119
22371
 
22120
22372
  // src/commands/sessions/daemon/runDaemon.ts
22121
22373
  async function runDaemon() {
22122
- mkdirSync23(daemonPaths.dir, { recursive: true });
22374
+ mkdirSync24(daemonPaths.dir, { recursive: true });
22123
22375
  daemonLog(
22124
22376
  `starting (reason: ${process.env.ASSIST_DAEMON_SPAWN_REASON ?? "manual"})`
22125
22377
  );
@@ -22159,7 +22411,7 @@ function registerDaemon(program2) {
22159
22411
 
22160
22412
  // src/commands/sessions/summarise/index.ts
22161
22413
  import * as fs35 from "fs";
22162
- import chalk178 from "chalk";
22414
+ import chalk180 from "chalk";
22163
22415
 
22164
22416
  // src/commands/sessions/summarise/shared.ts
22165
22417
  import * as fs33 from "fs";
@@ -22313,22 +22565,22 @@ ${firstMessage}`);
22313
22565
  async function summarise3(options2) {
22314
22566
  const files = await discoverSessionFiles();
22315
22567
  if (files.length === 0) {
22316
- console.log(chalk178.yellow("No sessions found."));
22568
+ console.log(chalk180.yellow("No sessions found."));
22317
22569
  return;
22318
22570
  }
22319
22571
  const toProcess = selectCandidates(files, options2);
22320
22572
  if (toProcess.length === 0) {
22321
- console.log(chalk178.green("All sessions already summarised."));
22573
+ console.log(chalk180.green("All sessions already summarised."));
22322
22574
  return;
22323
22575
  }
22324
22576
  console.log(
22325
- chalk178.cyan(
22577
+ chalk180.cyan(
22326
22578
  `Summarising ${toProcess.length} session(s) (${files.length} total)\u2026`
22327
22579
  )
22328
22580
  );
22329
22581
  const { succeeded, failed: failed2 } = processSessions(toProcess);
22330
22582
  console.log(
22331
- chalk178.green(`Done: ${succeeded} summarised`) + (failed2 > 0 ? chalk178.yellow(`, ${failed2} skipped`) : "")
22583
+ chalk180.green(`Done: ${succeeded} summarised`) + (failed2 > 0 ? chalk180.yellow(`, ${failed2} skipped`) : "")
22332
22584
  );
22333
22585
  }
22334
22586
  function selectCandidates(files, options2) {
@@ -22348,16 +22600,16 @@ function processSessions(files) {
22348
22600
  let failed2 = 0;
22349
22601
  for (let i = 0; i < files.length; i++) {
22350
22602
  const file = files[i];
22351
- process.stdout.write(chalk178.dim(` [${i + 1}/${files.length}] `));
22603
+ process.stdout.write(chalk180.dim(` [${i + 1}/${files.length}] `));
22352
22604
  const summary = summariseSession(file);
22353
22605
  if (summary) {
22354
22606
  writeSummary(file, summary);
22355
22607
  succeeded++;
22356
- process.stdout.write(`${chalk178.green("\u2713")} ${summary}
22608
+ process.stdout.write(`${chalk180.green("\u2713")} ${summary}
22357
22609
  `);
22358
22610
  } else {
22359
22611
  failed2++;
22360
- process.stdout.write(` ${chalk178.yellow("skip")}
22612
+ process.stdout.write(` ${chalk180.yellow("skip")}
22361
22613
  `);
22362
22614
  }
22363
22615
  }
@@ -22375,10 +22627,10 @@ function registerSessions(program2) {
22375
22627
  }
22376
22628
 
22377
22629
  // src/commands/statusLine.ts
22378
- import chalk180 from "chalk";
22630
+ import chalk182 from "chalk";
22379
22631
 
22380
22632
  // src/commands/buildLimitsSegment.ts
22381
- import chalk179 from "chalk";
22633
+ import chalk181 from "chalk";
22382
22634
 
22383
22635
  // src/shared/rateLimitLevel.ts
22384
22636
  var FIVE_HOUR_SECONDS = 5 * 3600;
@@ -22409,9 +22661,9 @@ function rateLimitLevel(pct, resetsAt, windowSeconds, now) {
22409
22661
 
22410
22662
  // src/commands/buildLimitsSegment.ts
22411
22663
  var LEVEL_COLOR = {
22412
- ok: chalk179.green,
22413
- warn: chalk179.yellow,
22414
- over: chalk179.red
22664
+ ok: chalk181.green,
22665
+ warn: chalk181.yellow,
22666
+ over: chalk181.red
22415
22667
  };
22416
22668
  function formatLimit(pct, resetsAt, windowSeconds, fallbackLabel, now) {
22417
22669
  const level = rateLimitLevel(pct, resetsAt, windowSeconds, now);
@@ -22451,14 +22703,14 @@ async function relayRateLimits(rateLimits) {
22451
22703
  }
22452
22704
 
22453
22705
  // src/commands/statusLine.ts
22454
- chalk180.level = 3;
22706
+ chalk182.level = 3;
22455
22707
  function formatNumber(num) {
22456
22708
  return num.toLocaleString("en-US");
22457
22709
  }
22458
22710
  function colorizePercent(pct) {
22459
22711
  const label2 = `${Math.round(pct)}%`;
22460
- if (pct > 80) return chalk180.red(label2);
22461
- if (pct > 40) return chalk180.yellow(label2);
22712
+ if (pct > 80) return chalk182.red(label2);
22713
+ if (pct > 40) return chalk182.yellow(label2);
22462
22714
  return label2;
22463
22715
  }
22464
22716
  async function statusLine() {
@@ -22482,7 +22734,7 @@ import { fileURLToPath as fileURLToPath7 } from "url";
22482
22734
  // src/commands/sync/syncClaudeMd.ts
22483
22735
  import * as fs36 from "fs";
22484
22736
  import * as path53 from "path";
22485
- import chalk181 from "chalk";
22737
+ import chalk183 from "chalk";
22486
22738
  async function syncClaudeMd(claudeDir, targetBase, options2) {
22487
22739
  const source = path53.join(claudeDir, "CLAUDE.md");
22488
22740
  const target = path53.join(targetBase, "CLAUDE.md");
@@ -22491,12 +22743,12 @@ async function syncClaudeMd(claudeDir, targetBase, options2) {
22491
22743
  const targetContent = fs36.readFileSync(target, "utf8");
22492
22744
  if (sourceContent !== targetContent) {
22493
22745
  console.log(
22494
- chalk181.yellow("\n\u26A0\uFE0F Warning: CLAUDE.md differs from existing file")
22746
+ chalk183.yellow("\n\u26A0\uFE0F Warning: CLAUDE.md differs from existing file")
22495
22747
  );
22496
22748
  console.log();
22497
22749
  printDiff(targetContent, sourceContent);
22498
22750
  const confirm = options2?.yes || await promptConfirm(
22499
- chalk181.red("Overwrite existing CLAUDE.md?"),
22751
+ chalk183.red("Overwrite existing CLAUDE.md?"),
22500
22752
  false
22501
22753
  );
22502
22754
  if (!confirm) {
@@ -22512,7 +22764,7 @@ async function syncClaudeMd(claudeDir, targetBase, options2) {
22512
22764
  // src/commands/sync/syncSettings.ts
22513
22765
  import * as fs37 from "fs";
22514
22766
  import * as path54 from "path";
22515
- import chalk182 from "chalk";
22767
+ import chalk184 from "chalk";
22516
22768
  async function syncSettings(claudeDir, targetBase, options2) {
22517
22769
  const source = path54.join(claudeDir, "settings.json");
22518
22770
  const target = path54.join(targetBase, "settings.json");
@@ -22528,14 +22780,14 @@ async function syncSettings(claudeDir, targetBase, options2) {
22528
22780
  if (mergedContent !== normalizedTarget) {
22529
22781
  if (!options2?.yes) {
22530
22782
  console.log(
22531
- chalk182.yellow(
22783
+ chalk184.yellow(
22532
22784
  "\n\u26A0\uFE0F Warning: settings.json differs from existing file"
22533
22785
  )
22534
22786
  );
22535
22787
  console.log();
22536
22788
  printDiff(targetContent, mergedContent);
22537
22789
  const confirm = await promptConfirm(
22538
- chalk182.red("Overwrite existing settings.json?"),
22790
+ chalk184.red("Overwrite existing settings.json?"),
22539
22791
  false
22540
22792
  );
22541
22793
  if (!confirm) {
@@ -22653,6 +22905,7 @@ program.command("screenshot").description("Capture a screenshot of a running app
22653
22905
  registerActivity(program);
22654
22906
  registerBackup(program);
22655
22907
  registerCliHook(program);
22908
+ registerCodeComment(program);
22656
22909
  registerEditHook(program);
22657
22910
  registerGithub(program);
22658
22911
  registerHandover(program);