@byh3071/vhk 1.6.5 → 1.6.6

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
@@ -12,6 +12,7 @@ import {
12
12
  countLocalCommits,
13
13
  deploy,
14
14
  detectExistingRuleFiles,
15
+ ensureInteractive,
15
16
  env,
16
17
  envCheck,
17
18
  filterSevereFindings,
@@ -22,12 +23,15 @@ import {
22
23
  gitOut,
23
24
  gitRun,
24
25
  hasGitRemote,
26
+ isInteractive,
27
+ isPromptAbortError,
25
28
  ko,
26
29
  listBackups,
27
30
  localDate,
28
31
  printContextResumeHint,
29
32
  printNextStep,
30
33
  printSecurityWarnings,
34
+ promptOrDefault,
31
35
  publish,
32
36
  readJsonFile,
33
37
  require_ignore,
@@ -38,12 +42,12 @@ import {
38
42
  stripBom,
39
43
  sync,
40
44
  t
41
- } from "./chunk-EJTVXWUZ.js";
45
+ } from "./chunk-HLUFOT2T.js";
42
46
 
43
47
  // src/index.ts
44
48
  import { Command, Help } from "commander";
45
49
  import { pathToFileURL } from "url";
46
- import chalk34 from "chalk";
50
+ import chalk33 from "chalk";
47
51
  import inquirer13 from "inquirer";
48
52
 
49
53
  // src/lib/nlp-router.ts
@@ -500,37 +504,12 @@ function detectNaturalLanguageInput(argv) {
500
504
  }
501
505
 
502
506
  // src/lib/nlp-run.ts
503
- import chalk32 from "chalk";
507
+ import chalk31 from "chalk";
504
508
  import inquirer12 from "inquirer";
505
509
 
506
510
  // src/commands/gate.ts
507
511
  import inquirer from "inquirer";
508
- import chalk2 from "chalk";
509
-
510
- // src/lib/interactive.ts
511
512
  import chalk from "chalk";
512
- function isInteractive(opts) {
513
- if (opts?.yes) return false;
514
- if (process.env.VHK_FORCE_INTERACTIVE === "1") return true;
515
- return !!process.stdin.isTTY;
516
- }
517
- async function promptOrDefault(ask, fallback, opts) {
518
- if (!isInteractive(opts)) return fallback;
519
- return await ask();
520
- }
521
- function ensureInteractive(hint = "") {
522
- if (isInteractive()) return true;
523
- console.error(chalk.yellow(" \u26A0\uFE0F \uC774 \uBA85\uB839\uC740 \uB300\uD654\uD615 \uC785\uB825\uC774 \uD544\uC694\uD569\uB2C8\uB2E4 \u2014 \uBE44-TTY/\uD30C\uC774\uD504 \uD658\uACBD\uC5D0\uC11C\uB294 \uC2E4\uD589\uD560 \uC218 \uC5C6\uC5B4\uC694."));
524
- if (hint) console.error(chalk.dim(` ${hint}`));
525
- process.exitCode = 1;
526
- return false;
527
- }
528
- function isPromptAbortError(err) {
529
- const msg = err instanceof Error ? err.message : String(err);
530
- return /ERR_USE_AFTER_CLOSE|force closed|ExitPromptError|readline was closed|User force closed/i.test(msg);
531
- }
532
-
533
- // src/commands/gate.ts
534
513
  var GATE_QUESTIONS = [
535
514
  { id: 1, stage: "\uBB38\uC81C \uC815\uC758", question: "\uC774 \uC544\uC774\uB514\uC5B4\uAC00 \uD574\uACB0\uD558\uB294 \uBB38\uC81C\uB97C \uD55C \uBB38\uC7A5\uC73C\uB85C \uB9D0\uD574\uBCF4\uC138\uC694.", failIf: "\uD55C \uBB38\uC7A5 \uBD88\uAC00 \u2192 \uBBF8\uC131\uC219", quick: true },
536
515
  { id: 2, stage: "\uD575\uC2EC \uAE30\uB2A5", question: "\uB531 1\uAC1C \uAE30\uB2A5\uB9CC \uACE0\uB974\uBA74?", failIf: "2\uAC1C \uC774\uC0C1 \u2192 \uBC94\uC704 \uCD08\uACFC", quick: true },
@@ -553,7 +532,7 @@ function judgeGate(failCount, holdCount) {
553
532
  }
554
533
  async function gate() {
555
534
  if (!ensureInteractive("\uC544\uC774\uB514\uC5B4 \uAC80\uC99D\uC740 \uB300\uD654\uD615 \uC9C8\uBB38\uC774 \uD544\uC694\uD569\uB2C8\uB2E4. \uD130\uBBF8\uB110(PowerShell \uB4F1)\uC5D0\uC11C \uC9C1\uC811 \uC2E4\uD589\uD558\uC138\uC694. Git Bash \uBA74 VHK_FORCE_INTERACTIVE=1.")) return;
556
- console.log(chalk2.bold(`
535
+ console.log(chalk.bold(`
557
536
  ${ko.gate.title}
558
537
  `));
559
538
  const { mode: mode2 } = await inquirer.prompt([{
@@ -572,33 +551,33 @@ ${ko.gate.title}
572
551
  name: "source",
573
552
  message: ko.gate.skipSourcePrompt
574
553
  }]);
575
- console.log(chalk2.green.bold(`
554
+ console.log(chalk.green.bold(`
576
555
  ${ko.gate.skipGo}`));
577
- console.log(chalk2.dim(ko.gate.skipSourceLabel(source)));
556
+ console.log(chalk.dim(ko.gate.skipSourceLabel(source)));
578
557
  return;
579
558
  }
580
559
  const questions = mode2 === "quick" ? GATE_QUESTIONS.filter((q) => q.quick) : GATE_QUESTIONS;
581
560
  const total = questions.length;
582
561
  const header = mode2 === "quick" ? ko.gate.quickHeader : ko.gate.fullHeader;
583
- console.log(chalk2.dim(`
562
+ console.log(chalk.dim(`
584
563
  ${header} ${ko.gate.modeCountSuffix(total)}
585
564
  `));
586
- console.log(chalk2.dim(`
565
+ console.log(chalk.dim(`
587
566
  ${ko.gate.welcome}
588
567
  `));
589
- console.log(chalk2.dim(` ${ko.gate.ideaHint}`));
568
+ console.log(chalk.dim(` ${ko.gate.ideaHint}`));
590
569
  const { idea } = await inquirer.prompt([
591
570
  { type: "input", name: "idea", message: ko.gate.idea }
592
571
  ]);
593
- console.log(chalk2.dim(` ${ko.gate.painPointHint}`));
572
+ console.log(chalk.dim(` ${ko.gate.painPointHint}`));
594
573
  const { painPoint } = await inquirer.prompt([
595
574
  { type: "input", name: "painPoint", message: ko.gate.painPoint }
596
575
  ]);
597
- console.log(chalk2.dim(` ${ko.gate.edgeHint}`));
576
+ console.log(chalk.dim(` ${ko.gate.edgeHint}`));
598
577
  const { edge } = await inquirer.prompt([
599
578
  { type: "input", name: "edge", message: ko.gate.edge }
600
579
  ]);
601
- console.log(chalk2.dim(`
580
+ console.log(chalk.dim(`
602
581
  ${ko.gate.checklistStart}
603
582
  `));
604
583
  let failCount = 0;
@@ -606,7 +585,7 @@ ${ko.gate.checklistStart}
606
585
  const results = [];
607
586
  for (let i = 0; i < questions.length; i++) {
608
587
  const q = questions[i];
609
- if (q.hint) console.log(chalk2.dim(`${ko.gate.hintPrefix} ${q.hint}`));
588
+ if (q.hint) console.log(chalk.dim(`${ko.gate.hintPrefix} ${q.hint}`));
610
589
  const { answer } = await inquirer.prompt([{
611
590
  type: "input",
612
591
  name: "answer",
@@ -625,22 +604,22 @@ ${ko.gate.checklistStart}
625
604
  if (status2 === "fail") failCount++;
626
605
  if (status2 === "hold") holdCount++;
627
606
  results.push({ id: q.id, stage: q.stage, status: status2, answer });
628
- const icon = status2 === "pass" ? chalk2.green(ko.gate.statusPassLine) : status2 === "hold" ? chalk2.yellow(ko.gate.statusHoldLine) : chalk2.red(ko.gate.statusFailLine);
607
+ const icon = status2 === "pass" ? chalk.green(ko.gate.statusPassLine) : status2 === "hold" ? chalk.yellow(ko.gate.statusHoldLine) : chalk.red(ko.gate.statusFailLine);
629
608
  console.log(icon);
630
609
  }
631
- console.log(chalk2.bold(`
610
+ console.log(chalk.bold(`
632
611
  ${ko.gate.verdictTitle}
633
612
  `));
634
- console.log(`${ko.gate.ideaLabel} ${chalk2.cyan(idea)}`);
613
+ console.log(`${ko.gate.ideaLabel} ${chalk.cyan(idea)}`);
635
614
  console.log(`${ko.gate.painPointLabel} ${painPoint}`);
636
615
  console.log(`${ko.gate.edgeLabel} ${edge}`);
637
616
  console.log(`${ko.gate.countLine(failCount, holdCount, total)}
638
617
  `);
639
618
  const verdict = judgeGate(failCount, holdCount);
640
619
  if (verdict === "GO") {
641
- console.log(chalk2.green.bold(ko.gate.go));
620
+ console.log(chalk.green.bold(ko.gate.go));
642
621
  if (holdCount > 0) {
643
- console.log(chalk2.yellow(ko.gate.holdRemainHint));
622
+ console.log(chalk.yellow(ko.gate.holdRemainHint));
644
623
  }
645
624
  printNextStep({
646
625
  message: "\uC544\uC774\uB514\uC5B4 \uD1B5\uACFC! \uC774\uC81C \uD504\uB85C\uC81D\uD2B8\uB97C \uB9CC\uB4E4\uC5B4\uBCF4\uC138\uC694.",
@@ -648,20 +627,20 @@ ${ko.gate.verdictTitle}
648
627
  cursorHint: "\uD504\uB85C\uC81D\uD2B8 \uB9CC\uB4E4\uC5B4\uC918"
649
628
  });
650
629
  } else if (verdict === "REFINE") {
651
- console.log(chalk2.yellow.bold(ko.gate.refine));
630
+ console.log(chalk.yellow.bold(ko.gate.refine));
652
631
  printNextStep({
653
632
  message: "\uC870\uAE08 \uB354 \uB2E4\uB4EC\uC740 \uD6C4 \uB2E4\uC2DC \uAC80\uC99D\uD574\uBCF4\uC138\uC694.",
654
633
  command: "vhk \uAC80\uC99D",
655
634
  cursorHint: "\uC544\uC774\uB514\uC5B4 \uB2E4\uC2DC \uAC80\uC99D\uD574\uC918"
656
635
  });
657
636
  } else {
658
- console.log(chalk2.red.bold(ko.gate.drop));
637
+ console.log(chalk.red.bold(ko.gate.drop));
659
638
  }
660
639
  }
661
640
 
662
641
  // src/commands/init.ts
663
642
  import inquirer2 from "inquirer";
664
- import chalk4 from "chalk";
643
+ import chalk3 from "chalk";
665
644
  import fs2 from "fs";
666
645
  import path2 from "path";
667
646
 
@@ -983,13 +962,13 @@ function VHK_CONTEXT_SEED(name, type, stack) {
983
962
  }
984
963
 
985
964
  // src/utils/logger.ts
986
- import chalk3 from "chalk";
965
+ import chalk2 from "chalk";
987
966
  var log = {
988
- success: (msg) => console.log(chalk3.green(`\u2705 ${msg}`)),
989
- error: (msg) => console.log(chalk3.red(`\u274C ${msg}`)),
990
- warn: (msg) => console.log(chalk3.yellow(`\u26A0\uFE0F ${msg}`)),
991
- info: (msg) => console.log(chalk3.blue(`\u2139\uFE0F ${msg}`)),
992
- step: (msg) => console.log(chalk3.bold(`
967
+ success: (msg) => console.log(chalk2.green(`\u2705 ${msg}`)),
968
+ error: (msg) => console.log(chalk2.red(`\u274C ${msg}`)),
969
+ warn: (msg) => console.log(chalk2.yellow(`\u26A0\uFE0F ${msg}`)),
970
+ info: (msg) => console.log(chalk2.blue(`\u2139\uFE0F ${msg}`)),
971
+ step: (msg) => console.log(chalk2.bold(`
993
972
  \u25B8 ${msg}`))
994
973
  };
995
974
 
@@ -1232,11 +1211,11 @@ async function collectAnswers(options, defaults = {}) {
1232
1211
  async function init(options = {}) {
1233
1212
  const skipGate = Boolean(options.skipGate || options.fromNotion);
1234
1213
  if (skipGate) {
1235
- console.log(chalk4.dim(`
1214
+ console.log(chalk3.dim(`
1236
1215
  ${ko.init.skipGate}
1237
1216
  `));
1238
1217
  }
1239
- console.log(chalk4.bold(`
1218
+ console.log(chalk3.bold(`
1240
1219
  ${ko.init.title}
1241
1220
  `));
1242
1221
  printSecurityWarnings();
@@ -1262,8 +1241,8 @@ ${ko.init.title}
1262
1241
  }
1263
1242
  const detected = detectProjectStack(process.cwd());
1264
1243
  const stack = detected ?? STACK_PRESETS[answers.type];
1265
- if (detected) console.log(chalk4.dim(" \u{1F50E} package.json \uC758\uC874\uC131\uC5D0\uC11C \uC2E4\uC81C \uC2A4\uD0DD \uAC10\uC9C0"));
1266
- console.log(chalk4.dim(`
1244
+ if (detected) console.log(chalk3.dim(" \u{1F50E} package.json \uC758\uC874\uC131\uC5D0\uC11C \uC2E4\uC81C \uC2A4\uD0DD \uAC10\uC9C0"));
1245
+ console.log(chalk3.dim(`
1267
1246
  ${ko.init.recommendedStack} ${stack.join(" + ")}
1268
1247
  `));
1269
1248
  if (isInteractive(options)) {
@@ -1294,7 +1273,7 @@ ${ko.init.recommendedStack} ${stack.join(" + ")}
1294
1273
  }]);
1295
1274
  if (adopt) {
1296
1275
  adoptedRules = buildAdoptedRules(existingRules, answers.name);
1297
- console.log(chalk4.dim(` ${ko.init.adoptPreview(existingRules.length)}`));
1276
+ console.log(chalk3.dim(` ${ko.init.adoptPreview(existingRules.length)}`));
1298
1277
  }
1299
1278
  }
1300
1279
  }
@@ -1319,21 +1298,21 @@ ${ko.init.recommendedStack} ${stack.join(" + ")}
1319
1298
  log.success(filePath);
1320
1299
  }
1321
1300
  await writeInitExtras(cwd, !isInteractive(options));
1322
- console.log(chalk4.bold.green(`
1301
+ console.log(chalk3.bold.green(`
1323
1302
  ${ko.init.done}`));
1324
- console.log(chalk4.dim(`
1303
+ console.log(chalk3.dim(`
1325
1304
  ${ko.init.nextSteps}`));
1326
1305
  if (options.fromNotion) {
1327
1306
  console.log(` 1. ${ko.init.notionReviewHint}`);
1328
1307
  console.log(` 2. ${ko.init.gitHintLabel}`);
1329
- console.log(` ${chalk4.cyan(ko.init.gitHintCommand)}`);
1308
+ console.log(` ${chalk3.cyan(ko.init.gitHintCommand)}`);
1330
1309
  console.log(` 3. ${ko.init.startDev}
1331
1310
  `);
1332
1311
  } else {
1333
1312
  console.log(` 1. ${ko.init.fillHint}`);
1334
1313
  console.log(` 2. ${ko.init.prdHint}`);
1335
1314
  console.log(` 3. ${ko.init.gitHintLabel}`);
1336
- console.log(` ${chalk4.cyan(ko.init.gitHintCommand)}`);
1315
+ console.log(` ${chalk3.cyan(ko.init.gitHintCommand)}`);
1337
1316
  console.log(` 4. ${ko.init.startDev}
1338
1317
  `);
1339
1318
  }
@@ -1465,7 +1444,7 @@ async function writeInitExtras(projectDir, noninteractive = false) {
1465
1444
 
1466
1445
  // src/commands/recap.ts
1467
1446
  import inquirer3 from "inquirer";
1468
- import chalk6 from "chalk";
1447
+ import chalk5 from "chalk";
1469
1448
  import fs4 from "fs";
1470
1449
  import path5 from "path";
1471
1450
 
@@ -1651,7 +1630,7 @@ function createAdrFile(cwd, title, context2, decision, consequences) {
1651
1630
  }
1652
1631
 
1653
1632
  // src/lib/hard-stop-guard.ts
1654
- import chalk5 from "chalk";
1633
+ import chalk4 from "chalk";
1655
1634
 
1656
1635
  // src/lib/state-files.ts
1657
1636
  import { existsSync, mkdirSync, readFileSync, writeFileSync, appendFileSync, rmSync } from "fs";
@@ -1766,11 +1745,11 @@ function clearHardStop() {
1766
1745
  // src/lib/hard-stop-guard.ts
1767
1746
  function ensureNotHardStopped(action) {
1768
1747
  if (!isHardStopActive()) return true;
1769
- console.error(chalk5.red.bold(`
1748
+ console.error(chalk4.red.bold(`
1770
1749
  \u{1F6D1} HARD STOP \uD65C\uC131 \u2014 '${action}' \uC744(\uB97C) \uC2E4\uD589\uD558\uC9C0 \uC54A\uC558\uC2B5\uB2C8\uB2E4.`));
1771
1750
  const reason = readHardStopReason();
1772
- if (reason) console.error(chalk5.dim(` \uC0AC\uC720: ${reason.replace(/\s*\n\s*/g, " ")}`));
1773
- console.error(chalk5.dim(" \uD574\uC81C: vhk resume --confirm (\uC0AC\uB78C\uC774 \uC9C1\uC811 \uC2E4\uD589)"));
1751
+ if (reason) console.error(chalk4.dim(` \uC0AC\uC720: ${reason.replace(/\s*\n\s*/g, " ")}`));
1752
+ console.error(chalk4.dim(" \uD574\uC81C: vhk resume --confirm (\uC0AC\uB78C\uC774 \uC9C1\uC811 \uC2E4\uD589)"));
1774
1753
  process.exitCode = 1;
1775
1754
  return false;
1776
1755
  }
@@ -1778,45 +1757,45 @@ function ensureNotHardStopped(action) {
1778
1757
  // src/commands/recap.ts
1779
1758
  async function recap(options = {}) {
1780
1759
  if (!ensureNotHardStopped("recap")) return;
1781
- console.log(chalk6.bold(`
1760
+ console.log(chalk5.bold(`
1782
1761
  ${ko.recap.title}
1783
1762
  `));
1784
1763
  if (!await isGitRepo()) {
1785
- console.log(chalk6.red(ko.recap.noRepo));
1764
+ console.log(chalk5.red(ko.recap.noRepo));
1786
1765
  return;
1787
1766
  }
1788
1767
  if (!await hasAnyCommits()) {
1789
- console.log(chalk6.yellow("\u26A0\uFE0F \uC544\uC9C1 \uCEE4\uBC0B\uC774 \uC5C6\uC5B4\uC694."));
1790
- console.log(chalk6.gray(" \uD30C\uC77C\uC744 \uCD94\uAC00\uD558\uACE0 `vhk save` \uB610\uB294 `git commit`\uC73C\uB85C \uCCAB \uCEE4\uBC0B\uC744 \uB9CC\uB4E4\uC5B4 \uBCF4\uC138\uC694."));
1768
+ console.log(chalk5.yellow("\u26A0\uFE0F \uC544\uC9C1 \uCEE4\uBC0B\uC774 \uC5C6\uC5B4\uC694."));
1769
+ console.log(chalk5.gray(" \uD30C\uC77C\uC744 \uCD94\uAC00\uD558\uACE0 `vhk save` \uB610\uB294 `git commit`\uC73C\uB85C \uCCAB \uCEE4\uBC0B\uC744 \uB9CC\uB4E4\uC5B4 \uBCF4\uC138\uC694."));
1791
1770
  return;
1792
1771
  }
1793
1772
  printSecurityWarnings();
1794
- console.log(chalk6.dim(`${ko.recap.analyzing}
1773
+ console.log(chalk5.dim(`${ko.recap.analyzing}
1795
1774
  `));
1796
1775
  const since = options.since || localDate();
1797
1776
  const diff2 = await getSessionDiff(since);
1798
1777
  const commits = await getRecentCommits(10, since);
1799
1778
  if (diff2.filesChanged === 0 && commits.length === 0) {
1800
- console.log(chalk6.yellow(ko.recap.noChanges));
1779
+ console.log(chalk5.yellow(ko.recap.noChanges));
1801
1780
  return;
1802
1781
  }
1803
- console.log(chalk6.bold("\u{1F4CA} \uBCC0\uACBD \uC694\uC57D:"));
1804
- console.log(` \uD30C\uC77C: ${chalk6.cyan(String(diff2.filesChanged))}\uAC1C \uBCC0\uACBD`);
1805
- console.log(` \uCD94\uAC00: ${chalk6.green("+" + diff2.insertions)} / \uC0AD\uC81C: ${chalk6.red("-" + diff2.deletions)}`);
1782
+ console.log(chalk5.bold("\u{1F4CA} \uBCC0\uACBD \uC694\uC57D:"));
1783
+ console.log(` \uD30C\uC77C: ${chalk5.cyan(String(diff2.filesChanged))}\uAC1C \uBCC0\uACBD`);
1784
+ console.log(` \uCD94\uAC00: ${chalk5.green("+" + diff2.insertions)} / \uC0AD\uC81C: ${chalk5.red("-" + diff2.deletions)}`);
1806
1785
  if (diff2.files.length > 0) {
1807
- console.log(chalk6.dim("\n \uBCC0\uACBD \uD30C\uC77C:"));
1786
+ console.log(chalk5.dim("\n \uBCC0\uACBD \uD30C\uC77C:"));
1808
1787
  diff2.files.slice(0, 15).forEach((f) => {
1809
- const icon = f.status === "new" ? chalk6.green("\u{1F195}") : f.status === "deleted" ? chalk6.red("\u{1F5D1}\uFE0F") : chalk6.yellow("\u270F\uFE0F");
1788
+ const icon = f.status === "new" ? chalk5.green("\u{1F195}") : f.status === "deleted" ? chalk5.red("\u{1F5D1}\uFE0F") : chalk5.yellow("\u270F\uFE0F");
1810
1789
  console.log(` ${icon} ${f.file}`);
1811
1790
  });
1812
1791
  if (diff2.files.length > 15) {
1813
- console.log(chalk6.dim(` ... \uC678 ${diff2.files.length - 15}\uAC1C`));
1792
+ console.log(chalk5.dim(` ... \uC678 ${diff2.files.length - 15}\uAC1C`));
1814
1793
  }
1815
1794
  }
1816
1795
  if (commits.length > 0) {
1817
- console.log(chalk6.dim("\n \uCD5C\uADFC \uCEE4\uBC0B:"));
1796
+ console.log(chalk5.dim("\n \uCD5C\uADFC \uCEE4\uBC0B:"));
1818
1797
  commits.slice(0, 5).forEach((c) => {
1819
- console.log(chalk6.dim(` \u2022 ${c.message}`));
1798
+ console.log(chalk5.dim(` \u2022 ${c.message}`));
1820
1799
  });
1821
1800
  }
1822
1801
  console.log("");
@@ -1885,11 +1864,11 @@ ${ko.recap.title}
1885
1864
  fs4.writeFileSync(filePath, content, "utf-8");
1886
1865
  const adrCandidates = detectAdrCandidates(diff2);
1887
1866
  if (adrCandidates.length > 0) {
1888
- console.log(chalk6.cyan.bold(`
1867
+ console.log(chalk5.cyan.bold(`
1889
1868
  ${ko.recap.adrDetected} (${adrCandidates.length}\uAC74)`));
1890
1869
  for (const candidate of adrCandidates) {
1891
- console.log(chalk6.cyan(` \u2022 ${candidate.title}: ${candidate.context}`));
1892
- candidate.files.forEach((f) => console.log(chalk6.dim(` ${f}`)));
1870
+ console.log(chalk5.cyan(` \u2022 ${candidate.title}: ${candidate.context}`));
1871
+ candidate.files.forEach((f) => console.log(chalk5.dim(` ${f}`)));
1893
1872
  }
1894
1873
  const { createAdr } = await inquirer3.prompt([{
1895
1874
  type: "confirm",
@@ -1919,17 +1898,17 @@ ${ko.recap.adrDetected} (${adrCandidates.length}\uAC74)`));
1919
1898
  adrAnswers.decision,
1920
1899
  adrAnswers.consequences
1921
1900
  );
1922
- console.log(chalk6.green(` \u2705 ADR \uC0DD\uC131: ${path5.relative(process.cwd(), adrPath)}`));
1901
+ console.log(chalk5.green(` \u2705 ADR \uC0DD\uC131: ${path5.relative(process.cwd(), adrPath)}`));
1923
1902
  }
1924
1903
  }
1925
1904
  }
1926
1905
  const troubleshootingKeywords = /fix|bug|error|crash|hotfix|patch|revert|트러블|에러|버그|수정|핫픽스/i;
1927
1906
  const troubleCommits = commits.filter((c) => troubleshootingKeywords.test(c.message));
1928
1907
  if (troubleCommits.length > 0) {
1929
- console.log(chalk6.yellow.bold(`
1908
+ console.log(chalk5.yellow.bold(`
1930
1909
  ${ko.recap.troubleDetected} (${troubleCommits.length}\uAC74)`));
1931
1910
  troubleCommits.forEach((c) => {
1932
- console.log(chalk6.dim(` \u2022 ${c.message}`));
1911
+ console.log(chalk5.dim(` \u2022 ${c.message}`));
1933
1912
  });
1934
1913
  const { createTroubleshoot } = await inquirer3.prompt([{
1935
1914
  type: "confirm",
@@ -1980,12 +1959,12 @@ ${ko.recap.troubleDetected} (${troubleCommits.length}\uAC74)`));
1980
1959
  `*Generated by \`vhk recap\` at ${(/* @__PURE__ */ new Date()).toISOString()}*`
1981
1960
  ].join("\n");
1982
1961
  fs4.writeFileSync(tsFilePath, tsContent, "utf-8");
1983
- console.log(chalk6.green(` \u2705 \uD2B8\uB7EC\uBE14\uC288\uD305 \uBB38\uC11C \uC0DD\uC131: ${path5.relative(process.cwd(), tsFilePath)}`));
1962
+ console.log(chalk5.green(` \u2705 \uD2B8\uB7EC\uBE14\uC288\uD305 \uBB38\uC11C \uC0DD\uC131: ${path5.relative(process.cwd(), tsFilePath)}`));
1984
1963
  }
1985
1964
  }
1986
- console.log(chalk6.green.bold(`
1965
+ console.log(chalk5.green.bold(`
1987
1966
  ${ko.recap.done}`));
1988
- console.log(chalk6.dim(` \u{1F4C4} ${path5.relative(process.cwd(), filePath)}`));
1967
+ console.log(chalk5.dim(` \u{1F4C4} ${path5.relative(process.cwd(), filePath)}`));
1989
1968
  const claudeMdPath = path5.join(process.cwd(), "CLAUDE.md");
1990
1969
  if (fs4.existsSync(claudeMdPath)) {
1991
1970
  const { updateClaude } = await inquirer3.prompt([{
@@ -2005,7 +1984,7 @@ ${ko.recap.done}`));
2005
1984
  `- **\uB2E4\uC74C \uC561\uC158:** ${answers.nextTodo}`
2006
1985
  );
2007
1986
  fs4.writeFileSync(claudeMdPath, claudeContent, "utf-8");
2008
- console.log(chalk6.green(" \u2705 CLAUDE.md \uC5C5\uB370\uC774\uD2B8 \uC644\uB8CC"));
1987
+ console.log(chalk5.green(" \u2705 CLAUDE.md \uC5C5\uB370\uC774\uD2B8 \uC644\uB8CC"));
2009
1988
  }
2010
1989
  }
2011
1990
  const gitSaveCmd = process.platform === "win32" ? 'git add .; git commit -m "recap: \uC138\uC158 \uAE30\uB85D"' : 'git add . && git commit -m "recap: \uC138\uC158 \uAE30\uB85D"';
@@ -2017,7 +1996,7 @@ ${ko.recap.done}`));
2017
1996
  }
2018
1997
 
2019
1998
  // src/commands/check.ts
2020
- import chalk8 from "chalk";
1999
+ import chalk7 from "chalk";
2021
2000
  import path7 from "path";
2022
2001
  import fs6 from "fs";
2023
2002
 
@@ -2181,7 +2160,7 @@ function escapeRegex(str) {
2181
2160
  // src/commands/goal.ts
2182
2161
  import { existsSync as existsSync3, mkdirSync as mkdirSync2, writeFileSync as writeFileSync2, readFileSync as readFileSync3 } from "fs";
2183
2162
  import { join as join4 } from "path";
2184
- import chalk7 from "chalk";
2163
+ import chalk6 from "chalk";
2185
2164
 
2186
2165
  // src/lib/goal-frontmatter.ts
2187
2166
  import { existsSync as existsSync2, readFileSync as readFileSync2, readdirSync, statSync } from "fs";
@@ -2361,14 +2340,14 @@ function resolveGoalId(optId, goals) {
2361
2340
  return selectActiveId(goals);
2362
2341
  }
2363
2342
  async function goalList() {
2364
- console.log(chalk7.bold(`
2343
+ console.log(chalk6.bold(`
2365
2344
  ${ko.goal.listTitle}
2366
2345
  `));
2367
2346
  const goals = listGoals(GOALS_DIR);
2368
2347
  const skipped = findSkippedGoalFiles(GOALS_DIR);
2369
2348
  if (goals.length === 0) {
2370
- console.log(chalk7.yellow(" \u{1F4ED} goals/ \uB514\uB809\uD1A0\uB9AC\uC5D0 goal \uD30C\uC77C\uC774 \uC5C6\uC2B5\uB2C8\uB2E4."));
2371
- console.log(chalk7.dim(" vhk goal init \uC73C\uB85C \uC2DC\uC791\uD558\uC138\uC694."));
2349
+ console.log(chalk6.yellow(" \u{1F4ED} goals/ \uB514\uB809\uD1A0\uB9AC\uC5D0 goal \uD30C\uC77C\uC774 \uC5C6\uC2B5\uB2C8\uB2E4."));
2350
+ console.log(chalk6.dim(" vhk goal init \uC73C\uB85C \uC2DC\uC791\uD558\uC138\uC694."));
2372
2351
  printSkippedGoalWarnings(skipped);
2373
2352
  return;
2374
2353
  }
@@ -2386,33 +2365,33 @@ ${ko.goal.listTitle}
2386
2365
  const dups = findDuplicateIds(goals);
2387
2366
  if (dups.length > 0) {
2388
2367
  console.log("");
2389
- console.log(chalk7.yellow(` ${ko.goal.duplicateId(dups.join(", "))}`));
2368
+ console.log(chalk6.yellow(` ${ko.goal.duplicateId(dups.join(", "))}`));
2390
2369
  }
2391
2370
  printSkippedGoalWarnings(skipped);
2392
2371
  }
2393
2372
  function printSkippedGoalWarnings(skipped) {
2394
2373
  if (skipped.length > 0) {
2395
2374
  console.log("");
2396
- console.log(chalk7.yellow(` ${ko.goal.skippedFiles(skipped.length)}`));
2375
+ console.log(chalk6.yellow(` ${ko.goal.skippedFiles(skipped.length)}`));
2397
2376
  for (const s of skipped) {
2398
- console.log(chalk7.yellow(` - goals/${s.file}: ${s.reason}`));
2377
+ console.log(chalk6.yellow(` - goals/${s.file}: ${s.reason}`));
2399
2378
  }
2400
- console.log(chalk7.dim(" \uD544\uC218: type: goal + \uC22B\uC790 id. \uC2A4\uD0A4\uB9C8 \uC804\uCCB4: goals/_meta.md"));
2379
+ console.log(chalk6.dim(" \uD544\uC218: type: goal + \uC22B\uC790 id. \uC2A4\uD0A4\uB9C8 \uC804\uCCB4: goals/_meta.md"));
2401
2380
  }
2402
2381
  }
2403
2382
  async function goalNext() {
2404
- console.log(chalk7.bold(`
2383
+ console.log(chalk6.bold(`
2405
2384
  ${ko.goal.nextTitle}
2406
2385
  `));
2407
2386
  const goals = listGoals(GOALS_DIR);
2408
2387
  if (goals.length === 0) {
2409
- console.log(chalk7.yellow(" \u{1F4ED} \uC815\uC758\uB41C goal \uC774 \uC5C6\uC2B5\uB2C8\uB2E4."));
2410
- console.log(chalk7.dim(" vhk goal init \uC73C\uB85C \uC2DC\uC791\uD558\uC138\uC694."));
2388
+ console.log(chalk6.yellow(" \u{1F4ED} \uC815\uC758\uB41C goal \uC774 \uC5C6\uC2B5\uB2C8\uB2E4."));
2389
+ console.log(chalk6.dim(" vhk goal init \uC73C\uB85C \uC2DC\uC791\uD558\uC138\uC694."));
2411
2390
  return;
2412
2391
  }
2413
2392
  const activeId = selectActiveId(goals);
2414
2393
  if (activeId === null) {
2415
- console.log(chalk7.green(" \u{1F389} \uBAA8\uB4E0 goal \uC774 \uC644\uB8CC\uB418\uC5C8\uC2B5\uB2C8\uB2E4!"));
2394
+ console.log(chalk6.green(" \u{1F389} \uBAA8\uB4E0 goal \uC774 \uC644\uB8CC\uB418\uC5C8\uC2B5\uB2C8\uB2E4!"));
2416
2395
  return;
2417
2396
  }
2418
2397
  const active = goals.find((g) => g.frontmatter.id === activeId);
@@ -2434,7 +2413,7 @@ ${ko.goal.nextTitle}
2434
2413
  mkdirSync2(STATE_DIR2, { recursive: true });
2435
2414
  writeFileSync2(join4(STATE_DIR2, "next-task.md"), text, "utf-8");
2436
2415
  console.log(
2437
- chalk7.green(
2416
+ chalk6.green(
2438
2417
  ` \u2705 next-task.md \uAC31\uC2E0 \u2014 Goal ${activeId}: ${active.frontmatter.title ?? ""}`
2439
2418
  )
2440
2419
  );
@@ -2493,7 +2472,7 @@ var STATE_NEXT_TASK_TEMPLATE = "# Next Task\n\n```\nTASK: (vhk goal next \uB85C
2493
2472
  var STATE_BLOCKERS_TEMPLATE = "# Blockers\n\n_Append-only. \uD574\uACB0 \uD56D\uBAA9\uC740 ~~\uCDE8\uC18C\uC120~~\uC73C\uB85C \uD45C\uAE30._\n";
2494
2473
  var STATE_LEARNINGS_TEMPLATE = "# Learnings\n\n_Append-only. \uD55C \uC904 = \uD55C \uAD50\uD6C8._\n";
2495
2474
  async function goalInit() {
2496
- console.log(chalk7.bold(`
2475
+ console.log(chalk6.bold(`
2497
2476
  ${ko.goal.initTitle}
2498
2477
  `));
2499
2478
  const targets = [
@@ -2508,15 +2487,15 @@ ${ko.goal.initTitle}
2508
2487
  let skipped = 0;
2509
2488
  for (const t2 of targets) {
2510
2489
  if (existsSync3(t2.path)) {
2511
- console.log(chalk7.gray(` \u2298 skip (\uC774\uBBF8 \uC874\uC7AC): ${t2.path}`));
2490
+ console.log(chalk6.gray(` \u2298 skip (\uC774\uBBF8 \uC874\uC7AC): ${t2.path}`));
2512
2491
  skipped++;
2513
2492
  } else {
2514
2493
  writeFileSync2(t2.path, t2.content, "utf-8");
2515
- console.log(chalk7.green(` \u2713 created: ${t2.path}`));
2494
+ console.log(chalk6.green(` \u2713 created: ${t2.path}`));
2516
2495
  created++;
2517
2496
  }
2518
2497
  }
2519
- console.log(chalk7.bold(`
2498
+ console.log(chalk6.bold(`
2520
2499
  \u{1F4CA} created=${created} skipped=${skipped}`));
2521
2500
  if (created > 0) {
2522
2501
  printNextStep({
@@ -2542,76 +2521,76 @@ function runGate(scriptPath) {
2542
2521
  function warnIfBashOnWindows(scriptPath) {
2543
2522
  if (process.platform === "win32" && scriptPath.endsWith(".sh")) {
2544
2523
  console.log(
2545
- chalk7.yellow(
2524
+ chalk6.yellow(
2546
2525
  " \u26A0 Windows: .sh \uAC8C\uC774\uD2B8\uB294 bash \uAC00 \uD544\uC694\uD569\uB2C8\uB2E4. cross-platform .mjs \uB85C \uBC31\uD544\uD558\uC138\uC694 \u2192 vhk goal sync"
2547
2526
  )
2548
2527
  );
2549
2528
  }
2550
2529
  }
2551
2530
  async function goalCheck(opts) {
2552
- console.log(chalk7.bold(`
2531
+ console.log(chalk6.bold(`
2553
2532
  ${ko.goal.checkTitle}
2554
2533
  `));
2555
2534
  const goals = listGoals(GOALS_DIR);
2556
2535
  const id = resolveGoalId(opts.id, goals);
2557
2536
  if (id === null) {
2558
2537
  console.log(
2559
- chalk7.yellow(" \u26A0 \uB300\uC0C1 goal \uC744 \uACB0\uC815\uD560 \uC218 \uC5C6\uC2B5\uB2C8\uB2E4 (--id \uBA85\uC2DC \uB610\uB294 active goal \uD544\uC694).")
2538
+ chalk6.yellow(" \u26A0 \uB300\uC0C1 goal \uC744 \uACB0\uC815\uD560 \uC218 \uC5C6\uC2B5\uB2C8\uB2E4 (--id \uBA85\uC2DC \uB610\uB294 active goal \uD544\uC694).")
2560
2539
  );
2561
2540
  process.exitCode = 1;
2562
2541
  return;
2563
2542
  }
2564
2543
  if (!goals.some((g) => g.frontmatter.id === id)) {
2565
- console.log(chalk7.red(` \u274C ${ko.goal.notFound(id)}`));
2544
+ console.log(chalk6.red(` \u274C ${ko.goal.notFound(id)}`));
2566
2545
  process.exitCode = 1;
2567
2546
  return;
2568
2547
  }
2569
2548
  const scriptPath = findGateScript(id);
2570
2549
  if (!scriptPath) {
2571
2550
  console.log(
2572
- chalk7.red(` \u274C \uAC8C\uC774\uD2B8 \uC2A4\uD06C\uB9BD\uD2B8 \uC5C6\uC74C: scripts/check-goal-${id}.{mjs,sh}`)
2551
+ chalk6.red(` \u274C \uAC8C\uC774\uD2B8 \uC2A4\uD06C\uB9BD\uD2B8 \uC5C6\uC74C: scripts/check-goal-${id}.{mjs,sh}`)
2573
2552
  );
2574
2553
  process.exitCode = 1;
2575
2554
  return;
2576
2555
  }
2577
2556
  warnIfBashOnWindows(scriptPath);
2578
2557
  const gate2 = runGate(scriptPath);
2579
- console.log(chalk7.dim(` \u25B6 ${gate2.runner} ${scriptPath}
2558
+ console.log(chalk6.dim(` \u25B6 ${gate2.runner} ${scriptPath}
2580
2559
  `));
2581
2560
  if (gate2.out) console.log(gate2.out);
2582
2561
  if (gate2.ok) {
2583
- console.log(chalk7.green(`
2562
+ console.log(chalk6.green(`
2584
2563
  \u2705 Goal ${id} \uAC8C\uC774\uD2B8 \uD1B5\uACFC`));
2585
2564
  } else {
2586
- console.log(chalk7.red(`
2565
+ console.log(chalk6.red(`
2587
2566
  \u274C Goal ${id} \uAC8C\uC774\uD2B8 \uC2E4\uD328`));
2588
- if (gate2.err && !gate2.out) console.log(chalk7.dim(gate2.err.slice(0, 500)));
2567
+ if (gate2.err && !gate2.out) console.log(chalk6.dim(gate2.err.slice(0, 500)));
2589
2568
  process.exitCode = 1;
2590
2569
  }
2591
2570
  }
2592
2571
  async function goalDone(opts) {
2593
- console.log(chalk7.bold(`
2572
+ console.log(chalk6.bold(`
2594
2573
  ${ko.goal.doneTitle}
2595
2574
  `));
2596
2575
  const goals = listGoals(GOALS_DIR);
2597
2576
  const id = resolveGoalId(opts.id, goals);
2598
2577
  if (id === null) {
2599
2578
  console.log(
2600
- chalk7.yellow(" \u26A0 \uB300\uC0C1 goal \uC744 \uACB0\uC815\uD560 \uC218 \uC5C6\uC2B5\uB2C8\uB2E4 (--id \uBA85\uC2DC \uB610\uB294 active goal \uD544\uC694).")
2579
+ chalk6.yellow(" \u26A0 \uB300\uC0C1 goal \uC744 \uACB0\uC815\uD560 \uC218 \uC5C6\uC2B5\uB2C8\uB2E4 (--id \uBA85\uC2DC \uB610\uB294 active goal \uD544\uC694).")
2601
2580
  );
2602
2581
  process.exitCode = 1;
2603
2582
  return;
2604
2583
  }
2605
2584
  const target = goals.find((g) => g.frontmatter.id === id);
2606
2585
  if (!target) {
2607
- console.log(chalk7.red(` \u274C ${ko.goal.notFound(id)}`));
2586
+ console.log(chalk6.red(` \u274C ${ko.goal.notFound(id)}`));
2608
2587
  process.exitCode = 1;
2609
2588
  return;
2610
2589
  }
2611
2590
  const scriptPath = findGateScript(id);
2612
2591
  if (!scriptPath) {
2613
2592
  console.log(
2614
- chalk7.red(
2593
+ chalk6.red(
2615
2594
  ` \u274C \uAC8C\uC774\uD2B8 \uC2A4\uD06C\uB9BD\uD2B8 \uC5C6\uC74C \u2014 done \uCC98\uB9AC \uAC70\uBD80: scripts/check-goal-${id}.{mjs,sh}`
2616
2595
  )
2617
2596
  );
@@ -2620,12 +2599,12 @@ ${ko.goal.doneTitle}
2620
2599
  }
2621
2600
  warnIfBashOnWindows(scriptPath);
2622
2601
  const gate2 = runGate(scriptPath);
2623
- console.log(chalk7.dim(` \u25B6 \uAC8C\uC774\uD2B8 \uAC80\uC99D: ${gate2.runner} ${scriptPath}
2602
+ console.log(chalk6.dim(` \u25B6 \uAC8C\uC774\uD2B8 \uAC80\uC99D: ${gate2.runner} ${scriptPath}
2624
2603
  `));
2625
2604
  if (gate2.out) console.log(gate2.out);
2626
2605
  if (!gate2.ok) {
2627
2606
  console.log(
2628
- chalk7.red(
2607
+ chalk6.red(
2629
2608
  `
2630
2609
  \u274C \uAC8C\uC774\uD2B8 \uC2E4\uD328 \u2014 frontmatter \uBCC0\uACBD \uC5C6\uC774 \uC885\uB8CC. (Forbidden: \uC2E4\uD328 = \uBCF4\uC874)`
2631
2610
  )
@@ -2637,7 +2616,7 @@ ${ko.goal.doneTitle}
2637
2616
  const today = localDate();
2638
2617
  const updated = updateFrontmatterStatus(content, "DONE", { completed: today });
2639
2618
  writeFileSync2(target.filePath, updated, "utf-8");
2640
- console.log(chalk7.green(`
2619
+ console.log(chalk6.green(`
2641
2620
  \u2705 Goal ${id} \u2192 DONE (completed: ${today})`));
2642
2621
  printNextStep({
2643
2622
  message: `Goal ${id} \uC644\uB8CC! \uB2E4\uC74C goal \uB85C:`,
@@ -2710,14 +2689,14 @@ function generateGateScript(id) {
2710
2689
  ].join("\n");
2711
2690
  }
2712
2691
  async function goalSync() {
2713
- console.log(chalk7.bold(`
2692
+ console.log(chalk6.bold(`
2714
2693
  ${ko.goal.syncTitle}
2715
2694
  `));
2716
2695
  const goals = listGoals(GOALS_DIR);
2717
2696
  const result = { created: [], skipped: [] };
2718
2697
  if (goals.length === 0) {
2719
2698
  console.log(
2720
- chalk7.yellow(" \u{1F4ED} goals/ \uC5D0 goal \uD30C\uC77C\uC774 \uC5C6\uC2B5\uB2C8\uB2E4. vhk goal init \uC73C\uB85C \uC2DC\uC791\uD558\uC138\uC694.")
2699
+ chalk6.yellow(" \u{1F4ED} goals/ \uC5D0 goal \uD30C\uC77C\uC774 \uC5C6\uC2B5\uB2C8\uB2E4. vhk goal init \uC73C\uB85C \uC2DC\uC791\uD558\uC138\uC694.")
2721
2700
  );
2722
2701
  return result;
2723
2702
  }
@@ -2727,19 +2706,19 @@ ${ko.goal.syncTitle}
2727
2706
  if (typeof id !== "number") continue;
2728
2707
  const target = join4(SCRIPTS_DIR, `check-goal-${id}.mjs`);
2729
2708
  if (existsSync3(target)) {
2730
- console.log(chalk7.gray(` \u2298 skip (\uC774\uBBF8 \uC874\uC7AC): ${target}`));
2709
+ console.log(chalk6.gray(` \u2298 skip (\uC774\uBBF8 \uC874\uC7AC): ${target}`));
2731
2710
  result.skipped.push(id);
2732
2711
  continue;
2733
2712
  }
2734
2713
  const shOnly = existsSync3(join4(SCRIPTS_DIR, `check-goal-${id}.sh`));
2735
2714
  writeFileSync2(target, generateGateScript(id), "utf-8");
2736
2715
  console.log(
2737
- chalk7.green(` \u2713 created: ${target}${shOnly ? " (.sh \u2192 .mjs \uBC31\uD544, Windows 1\uAE09)" : ""}`)
2716
+ chalk6.green(` \u2713 created: ${target}${shOnly ? " (.sh \u2192 .mjs \uBC31\uD544, Windows 1\uAE09)" : ""}`)
2738
2717
  );
2739
2718
  result.created.push(id);
2740
2719
  }
2741
2720
  console.log(
2742
- chalk7.bold(`
2721
+ chalk6.bold(`
2743
2722
  \u{1F4CA} created=${result.created.length} skipped=${result.skipped.length}`)
2744
2723
  );
2745
2724
  if (result.created.length > 0) {
@@ -2760,22 +2739,22 @@ async function check(opts = {}) {
2760
2739
  return checkRules();
2761
2740
  }
2762
2741
  async function checkRules() {
2763
- console.log(chalk8.bold(`
2742
+ console.log(chalk7.bold(`
2764
2743
  ${ko.check.title}
2765
2744
  `));
2766
2745
  const cwd = process.cwd();
2767
2746
  const rulesPath = path7.join(cwd, "RULES.md");
2768
2747
  if (!fs6.existsSync(rulesPath)) {
2769
- console.log(chalk8.yellow(ko.check.noRules));
2770
- console.log(chalk8.dim(" vhk init\uC73C\uB85C \uC2DC\uC791\uD558\uAC70\uB098 RULES.md\uB97C \uB9CC\uB4E4\uC5B4 \uBCF4\uC138\uC694."));
2748
+ console.log(chalk7.yellow(ko.check.noRules));
2749
+ console.log(chalk7.dim(" vhk init\uC73C\uB85C \uC2DC\uC791\uD558\uAC70\uB098 RULES.md\uB97C \uB9CC\uB4E4\uC5B4 \uBCF4\uC138\uC694."));
2771
2750
  return;
2772
2751
  }
2773
2752
  const rules = parseRules(rulesPath);
2774
- console.log(chalk8.dim(` \u{1F4CF} \uC790\uB3D9 \uAC80\uC99D \uAC00\uB2A5\uD55C \uADDC\uCE59 ${rules.length}\uAC1C \uAC10\uC9C0 (\uB098\uBA38\uC9C0 \uADDC\uCE59\uC740 \uC218\uB3D9/\uB3C4\uAD6C \uD655\uC778)
2753
+ console.log(chalk7.dim(` \u{1F4CF} \uC790\uB3D9 \uAC80\uC99D \uAC00\uB2A5\uD55C \uADDC\uCE59 ${rules.length}\uAC1C \uAC10\uC9C0 (\uB098\uBA38\uC9C0 \uADDC\uCE59\uC740 \uC218\uB3D9/\uB3C4\uAD6C \uD655\uC778)
2775
2754
  `));
2776
2755
  if (rules.length === 0) {
2777
- console.log(chalk8.yellow(ko.check.noAutoRules));
2778
- console.log(chalk8.dim(" RULES.md\uC5D0 \uD30C\uC77C \uC774\uB984\xB7\uD3F4\uB354 \uADDC\uCE59\uC744 \uC801\uC73C\uBA74 \uC790\uB3D9\uC73C\uB85C \uC810\uAC80\uD574\uC694."));
2756
+ console.log(chalk7.yellow(ko.check.noAutoRules));
2757
+ console.log(chalk7.dim(" RULES.md\uC5D0 \uD30C\uC77C \uC774\uB984\xB7\uD3F4\uB354 \uADDC\uCE59\uC744 \uC801\uC73C\uBA74 \uC790\uB3D9\uC73C\uB85C \uC810\uAC80\uD574\uC694."));
2779
2758
  return;
2780
2759
  }
2781
2760
  const allViolations = [];
@@ -2783,14 +2762,14 @@ ${ko.check.title}
2783
2762
  for (const rule of rules) {
2784
2763
  const violations = rule.check(cwd);
2785
2764
  if (violations.length === 0) {
2786
- const patternHint = rule.type === "content" && rule.pattern ? chalk8.dim(` [\uAC80\uC0AC: ${rule.pattern.source}]`) : "";
2787
- console.log(chalk8.green(` \u2705 ${rule.id}`) + chalk8.dim(` \u2014 ${rule.description.slice(0, 60)}`) + patternHint);
2765
+ const patternHint = rule.type === "content" && rule.pattern ? chalk7.dim(` [\uAC80\uC0AC: ${rule.pattern.source}]`) : "";
2766
+ console.log(chalk7.green(` \u2705 ${rule.id}`) + chalk7.dim(` \u2014 ${rule.description.slice(0, 60)}`) + patternHint);
2788
2767
  passCount++;
2789
2768
  } else {
2790
- console.log(chalk8.red(` \u274C ${rule.id}`) + chalk8.dim(` \u2014 ${violations.length}\uAC74 \uC704\uBC18`));
2769
+ console.log(chalk7.red(` \u274C ${rule.id}`) + chalk7.dim(` \u2014 ${violations.length}\uAC74 \uC704\uBC18`));
2791
2770
  violations.forEach((v) => {
2792
- const loc = v.file ? chalk8.dim(` (${v.file}${v.line ? ":" + v.line : ""})`) : "";
2793
- const icon = v.severity === "error" ? chalk8.red("\u2716") : v.severity === "warning" ? chalk8.yellow("\u26A0") : chalk8.blue("\u2139");
2771
+ const loc = v.file ? chalk7.dim(` (${v.file}${v.line ? ":" + v.line : ""})`) : "";
2772
+ const icon = v.severity === "error" ? chalk7.red("\u2716") : v.severity === "warning" ? chalk7.yellow("\u26A0") : chalk7.blue("\u2139");
2794
2773
  console.log(` ${icon} ${v.message}${loc}`);
2795
2774
  });
2796
2775
  allViolations.push(...violations);
@@ -2800,18 +2779,18 @@ ${ko.check.title}
2800
2779
  const errors = allViolations.filter((v) => v.severity === "error").length;
2801
2780
  const warnings = allViolations.filter((v) => v.severity === "warning").length;
2802
2781
  if (allViolations.length === 0) {
2803
- console.log(chalk8.green.bold(`\u2705 \uC790\uB3D9 \uAC80\uC99D \uAC00\uB2A5\uD55C \uADDC\uCE59 ${passCount}\uAC1C \uD1B5\uACFC`));
2804
- console.log(chalk8.dim(" (RULES.md \uC758 \uB098\uBA38\uC9C0 \uADDC\uCE59\uC740 \uCF54\uB4DC \uC790\uB3D9 \uAC80\uC0AC \uBD88\uAC00 \u2014 \uC9C1\uC811/\uB3C4\uAD6C\uB85C \uD655\uC778\uD558\uC138\uC694.)"));
2782
+ console.log(chalk7.green.bold(`\u2705 \uC790\uB3D9 \uAC80\uC99D \uAC00\uB2A5\uD55C \uADDC\uCE59 ${passCount}\uAC1C \uD1B5\uACFC`));
2783
+ console.log(chalk7.dim(" (RULES.md \uC758 \uB098\uBA38\uC9C0 \uADDC\uCE59\uC740 \uCF54\uB4DC \uC790\uB3D9 \uAC80\uC0AC \uBD88\uAC00 \u2014 \uC9C1\uC811/\uB3C4\uAD6C\uB85C \uD655\uC778\uD558\uC138\uC694.)"));
2805
2784
  printNextStep({
2806
2785
  message: "\uBAA8\uB4E0 \uADDC\uCE59 \uD1B5\uACFC! \uBCF4\uC548 \uC2A4\uCE94\uB3C4 \uD574\uBCFC\uAE4C\uC694?",
2807
2786
  command: "vhk \uBCF4\uC548 scan",
2808
2787
  cursorHint: "\uBCF4\uC548 \uC2A4\uCE94 \uB3CC\uB824\uC918"
2809
2788
  });
2810
2789
  } else {
2811
- console.log(chalk8.bold(ko.check.summary));
2812
- console.log(` \uADDC\uCE59: ${chalk8.cyan(String(rules.length))}\uAC1C | \uD1B5\uACFC: ${chalk8.green(String(passCount))}\uAC1C | \uC704\uBC18: ${chalk8.red(String(allViolations.length))}\uAC74`);
2813
- if (errors > 0) console.log(` ${chalk8.red(`\u2716 ${errors}\uAC1C \uC5D0\uB7EC`)}`);
2814
- if (warnings > 0) console.log(` ${chalk8.yellow(`\u26A0 ${warnings}\uAC1C \uACBD\uACE0`)}`);
2790
+ console.log(chalk7.bold(ko.check.summary));
2791
+ console.log(` \uADDC\uCE59: ${chalk7.cyan(String(rules.length))}\uAC1C | \uD1B5\uACFC: ${chalk7.green(String(passCount))}\uAC1C | \uC704\uBC18: ${chalk7.red(String(allViolations.length))}\uAC74`);
2792
+ if (errors > 0) console.log(` ${chalk7.red(`\u2716 ${errors}\uAC1C \uC5D0\uB7EC`)}`);
2793
+ if (warnings > 0) console.log(` ${chalk7.yellow(`\u26A0 ${warnings}\uAC1C \uACBD\uACE0`)}`);
2815
2794
  printNextStep({
2816
2795
  message: "\uC704\uBC18 \uD56D\uBAA9\uC744 \uC218\uC815\uD55C \uD6C4 \uB2E4\uC2DC \uC810\uAC80\uD558\uC138\uC694.",
2817
2796
  command: "vhk \uC810\uAC80",
@@ -2824,36 +2803,36 @@ ${ko.check.title}
2824
2803
  }
2825
2804
 
2826
2805
  // src/commands/secure.ts
2827
- import chalk9 from "chalk";
2806
+ import chalk8 from "chalk";
2828
2807
  import fs7 from "fs";
2829
2808
  import path8 from "path";
2830
2809
  async function secure() {
2831
- console.log(chalk9.bold(`
2810
+ console.log(chalk8.bold(`
2832
2811
  ${ko.secure.title}
2833
2812
  `));
2834
2813
  const cwd = process.cwd();
2835
2814
  const gitignorePath = path8.join(cwd, ".gitignore");
2836
2815
  const hasGitignore = fs7.existsSync(gitignorePath);
2837
2816
  if (!hasGitignore) {
2838
- console.log(chalk9.yellow(` ${ko.secure.noGitignore}`));
2839
- console.log(chalk9.dim(" .env \uD30C\uC77C\uC774 \uCEE4\uBC0B\uB420 \uC218 \uC788\uC2B5\uB2C8\uB2E4.\n"));
2817
+ console.log(chalk8.yellow(` ${ko.secure.noGitignore}`));
2818
+ console.log(chalk8.dim(" .env \uD30C\uC77C\uC774 \uCEE4\uBC0B\uB420 \uC218 \uC788\uC2B5\uB2C8\uB2E4.\n"));
2840
2819
  } else {
2841
2820
  const gitignoreContent = fs7.readFileSync(gitignorePath, "utf-8");
2842
2821
  if (!gitignoreContent.includes(".env")) {
2843
- console.log(chalk9.yellow(` ${ko.secure.noEnvInGitignore}`));
2844
- console.log(chalk9.dim(" \uCD94\uAC00\uB97C \uAD8C\uC7A5\uD569\uB2C8\uB2E4.\n"));
2822
+ console.log(chalk8.yellow(` ${ko.secure.noEnvInGitignore}`));
2823
+ console.log(chalk8.dim(" \uCD94\uAC00\uB97C \uAD8C\uC7A5\uD569\uB2C8\uB2E4.\n"));
2845
2824
  }
2846
2825
  }
2847
- console.log(chalk9.dim(` ${ko.secure.scanning}
2826
+ console.log(chalk8.dim(` ${ko.secure.scanning}
2848
2827
  `));
2849
2828
  const { findings, scannedFiles, truncated } = scanProjectForSecrets(cwd);
2850
- console.log(chalk9.dim(` \u{1F4C2} ${scannedFiles}\uAC1C \uD30C\uC77C \uC2A4\uCE94 \uC644\uB8CC (lock\xB7node_modules\xB7>${MAX_SCAN_FILE_BYTES / 1024}KB \uC81C\uC678)`));
2829
+ console.log(chalk8.dim(` \u{1F4C2} ${scannedFiles}\uAC1C \uD30C\uC77C \uC2A4\uCE94 \uC644\uB8CC (lock\xB7node_modules\xB7>${MAX_SCAN_FILE_BYTES / 1024}KB \uC81C\uC678)`));
2851
2830
  if (truncated) {
2852
- console.log(chalk9.yellow(` \u26A0\uFE0F \uACB0\uACFC ${MAX_SECRET_FINDINGS}\uAC74\uC5D0\uC11C \uCD9C\uB825\uC744 \uC81C\uD55C\uD588\uC2B5\uB2C8\uB2E4. lock \uD30C\uC77C \uB4F1\uC740 \uC790\uB3D9 \uC81C\uC678\uB429\uB2C8\uB2E4.`));
2831
+ console.log(chalk8.yellow(` \u26A0\uFE0F \uACB0\uACFC ${MAX_SECRET_FINDINGS}\uAC74\uC5D0\uC11C \uCD9C\uB825\uC744 \uC81C\uD55C\uD588\uC2B5\uB2C8\uB2E4. lock \uD30C\uC77C \uB4F1\uC740 \uC790\uB3D9 \uC81C\uC678\uB429\uB2C8\uB2E4.`));
2853
2832
  }
2854
2833
  console.log("");
2855
2834
  if (findings.length === 0) {
2856
- console.log(chalk9.green.bold(` ${ko.secure.clean}`));
2835
+ console.log(chalk8.green.bold(` ${ko.secure.clean}`));
2857
2836
  printNextStep({
2858
2837
  message: "\uBCF4\uC548 \uC774\uC0C1 \uC5C6\uC74C! \uAE68\uB057\uD569\uB2C8\uB2E4.",
2859
2838
  command: "vhk \uC815\uB9AC",
@@ -2865,43 +2844,43 @@ ${ko.secure.title}
2865
2844
  const high = findings.filter((f) => f.severity === "high");
2866
2845
  const medium = findings.filter((f) => f.severity === "medium");
2867
2846
  if (critical.length > 0) {
2868
- console.log(chalk9.red.bold(` \u{1F6A8} CRITICAL \u2014 ${critical.length}\uAC74`));
2847
+ console.log(chalk8.red.bold(` \u{1F6A8} CRITICAL \u2014 ${critical.length}\uAC74`));
2869
2848
  critical.forEach((f) => {
2870
- console.log(chalk9.red(` \u2716 ${f.patternName}`));
2871
- console.log(chalk9.dim(` ${f.file}:${f.line} \u2192 ${f.match}`));
2849
+ console.log(chalk8.red(` \u2716 ${f.patternName}`));
2850
+ console.log(chalk8.dim(` ${f.file}:${f.line} \u2192 ${f.match}`));
2872
2851
  });
2873
2852
  console.log("");
2874
2853
  }
2875
2854
  if (high.length > 0) {
2876
- console.log(chalk9.yellow.bold(` \u26A0\uFE0F HIGH \u2014 ${high.length}\uAC74`));
2855
+ console.log(chalk8.yellow.bold(` \u26A0\uFE0F HIGH \u2014 ${high.length}\uAC74`));
2877
2856
  high.forEach((f) => {
2878
- console.log(chalk9.yellow(` \u26A0 ${f.patternName}`));
2879
- console.log(chalk9.dim(` ${f.file}:${f.line} \u2192 ${f.match}`));
2857
+ console.log(chalk8.yellow(` \u26A0 ${f.patternName}`));
2858
+ console.log(chalk8.dim(` ${f.file}:${f.line} \u2192 ${f.match}`));
2880
2859
  });
2881
2860
  console.log("");
2882
2861
  }
2883
2862
  if (medium.length > 0) {
2884
- console.log(chalk9.blue.bold(` \u2139 MEDIUM \u2014 ${medium.length}\uAC74`));
2863
+ console.log(chalk8.blue.bold(` \u2139 MEDIUM \u2014 ${medium.length}\uAC74`));
2885
2864
  medium.forEach((f) => {
2886
- console.log(chalk9.blue(` \u2139 ${f.patternName}`));
2887
- console.log(chalk9.dim(` ${f.file}:${f.line} \u2192 ${f.match}`));
2865
+ console.log(chalk8.blue(` \u2139 ${f.patternName}`));
2866
+ console.log(chalk8.dim(` ${f.file}:${f.line} \u2192 ${f.match}`));
2888
2867
  });
2889
2868
  console.log("");
2890
2869
  }
2891
- console.log(chalk9.bold(` ${ko.secure.summary}`));
2892
- console.log(` \uCD1D ${chalk9.red(String(findings.length))}\uAC74 \uAC10\uC9C0 | CRITICAL: ${critical.length} | HIGH: ${high.length} | MEDIUM: ${medium.length}`);
2870
+ console.log(chalk8.bold(` ${ko.secure.summary}`));
2871
+ console.log(` \uCD1D ${chalk8.red(String(findings.length))}\uAC74 \uAC10\uC9C0 | CRITICAL: ${critical.length} | HIGH: ${high.length} | MEDIUM: ${medium.length}`);
2893
2872
  console.log("");
2894
- console.log(chalk9.dim(" \u{1F4A1} \uC870\uCE58 \uBC29\uBC95:"));
2895
- console.log(chalk9.dim(" 1. \uD574\uB2F9 \uD30C\uC77C\uC5D0\uC11C \uC2DC\uD06C\uB9BF\uC744 \uC81C\uAC70\uD558\uACE0 \uD658\uACBD\uBCC0\uC218\uB85C \uC774\uB3D9"));
2896
- console.log(chalk9.dim(" 2. git history\uC5D0\uC11C\uB3C4 \uC81C\uAC70: git filter-branch \uB610\uB294 BFG Repo-Cleaner"));
2897
- console.log(chalk9.dim(" 3. \uC720\uCD9C\uB41C \uD0A4\uB294 \uC989\uC2DC \uD3D0\uAE30\uD558\uACE0 \uC7AC\uBC1C\uAE09\n"));
2873
+ console.log(chalk8.dim(" \u{1F4A1} \uC870\uCE58 \uBC29\uBC95:"));
2874
+ console.log(chalk8.dim(" 1. \uD574\uB2F9 \uD30C\uC77C\uC5D0\uC11C \uC2DC\uD06C\uB9BF\uC744 \uC81C\uAC70\uD558\uACE0 \uD658\uACBD\uBCC0\uC218\uB85C \uC774\uB3D9"));
2875
+ console.log(chalk8.dim(" 2. git history\uC5D0\uC11C\uB3C4 \uC81C\uAC70: git filter-branch \uB610\uB294 BFG Repo-Cleaner"));
2876
+ console.log(chalk8.dim(" 3. \uC720\uCD9C\uB41C \uD0A4\uB294 \uC989\uC2DC \uD3D0\uAE30\uD558\uACE0 \uC7AC\uBC1C\uAE09\n"));
2898
2877
  if (critical.length > 0 || high.length > 0) {
2899
2878
  process.exitCode = 1;
2900
2879
  }
2901
2880
  }
2902
2881
 
2903
2882
  // src/commands/doctor.ts
2904
- import chalk10 from "chalk";
2883
+ import chalk9 from "chalk";
2905
2884
  import fs8 from "fs";
2906
2885
  import path9 from "path";
2907
2886
  import { fileURLToPath } from "url";
@@ -2947,7 +2926,7 @@ function compareSemver(a, b) {
2947
2926
  return a3 - b3;
2948
2927
  }
2949
2928
  async function doctor() {
2950
- console.log(chalk10.bold(`
2929
+ console.log(chalk9.bold(`
2951
2930
  ${ko.doctor.title}
2952
2931
  `));
2953
2932
  const checks = [
@@ -2959,30 +2938,30 @@ ${ko.doctor.title}
2959
2938
  let allOk = true;
2960
2939
  for (const check2 of checks) {
2961
2940
  if (check2.ok) {
2962
- console.log(chalk10.green(` \u2705 ${check2.name}`) + chalk10.dim(` \u2014 ${check2.version}`));
2941
+ console.log(chalk9.green(` \u2705 ${check2.name}`) + chalk9.dim(` \u2014 ${check2.version}`));
2963
2942
  } else {
2964
- console.log(chalk10.red(` \u274C ${check2.name} \uC5C6\uC74C`));
2965
- console.log(chalk10.dim(` \u2192 ${check2.hint}`));
2943
+ console.log(chalk9.red(` \u274C ${check2.name} \uC5C6\uC74C`));
2944
+ console.log(chalk9.dim(` \u2192 ${check2.hint}`));
2966
2945
  allOk = false;
2967
2946
  }
2968
2947
  }
2969
2948
  console.log("");
2970
2949
  const vhkVersion = getVhkVersion2();
2971
2950
  if (vhkVersion) {
2972
- console.log(chalk10.green(" \u2705 VHK") + chalk10.dim(` \u2014 v${vhkVersion}`));
2951
+ console.log(chalk9.green(" \u2705 VHK") + chalk9.dim(` \u2014 v${vhkVersion}`));
2973
2952
  } else {
2974
- console.log(chalk10.green(" \u2705 VHK") + chalk10.dim(" \u2014 \uC124\uCE58\uB428"));
2953
+ console.log(chalk9.green(" \u2705 VHK") + chalk9.dim(" \u2014 \uC124\uCE58\uB428"));
2975
2954
  }
2976
2955
  if (vhkVersion) {
2977
2956
  const latest = fetchLatestNpmVersion("@byh3071/vhk");
2978
2957
  if (latest && compareSemver(latest, vhkVersion) > 0) {
2979
- console.log(chalk10.yellow(` ${ko.doctor.updateAvailable(latest)}`));
2958
+ console.log(chalk9.yellow(` ${ko.doctor.updateAvailable(latest)}`));
2980
2959
  } else if (latest) {
2981
- console.log(chalk10.dim(` ${ko.doctor.updateCurrent}`));
2960
+ console.log(chalk9.dim(` ${ko.doctor.updateCurrent}`));
2982
2961
  }
2983
2962
  }
2984
2963
  console.log("");
2985
- console.log(chalk10.bold(` ${ko.doctor.projectFiles}`));
2964
+ console.log(chalk9.bold(` ${ko.doctor.projectFiles}`));
2986
2965
  const cwd = process.cwd();
2987
2966
  const projectFiles = [
2988
2967
  { name: "RULES.md", hint: "vhk init\uC73C\uB85C \uC0DD\uC131 \uAC00\uB2A5" },
@@ -2994,49 +2973,49 @@ ${ko.doctor.title}
2994
2973
  for (const file of projectFiles) {
2995
2974
  const exists = fs8.existsSync(path9.join(cwd, file.name));
2996
2975
  if (exists) {
2997
- console.log(chalk10.green(` \u2705 ${file.name}`));
2976
+ console.log(chalk9.green(` \u2705 ${file.name}`));
2998
2977
  if (file.name === ".env") {
2999
2978
  const gitignorePath = path9.join(cwd, ".gitignore");
3000
2979
  if (fs8.existsSync(gitignorePath)) {
3001
2980
  const gitignore = fs8.readFileSync(gitignorePath, "utf-8");
3002
2981
  if (!gitignore.includes(".env")) {
3003
- console.log(chalk10.yellow(` ${ko.doctor.envNotIgnored}`));
2982
+ console.log(chalk9.yellow(` ${ko.doctor.envNotIgnored}`));
3004
2983
  }
3005
2984
  }
3006
2985
  }
3007
2986
  } else if (file.name === ".env" && fs8.existsSync(path9.join(cwd, ".env.local"))) {
3008
- console.log(chalk10.green(" \u2705 .env.local") + chalk10.dim(" \u2014 \uB85C\uCEEC env \uC0AC\uC6A9 \uC911 (.env \uC5C6\uC5B4\uB3C4 \uC815\uC0C1)"));
2987
+ console.log(chalk9.green(" \u2705 .env.local") + chalk9.dim(" \u2014 \uB85C\uCEEC env \uC0AC\uC6A9 \uC911 (.env \uC5C6\uC5B4\uB3C4 \uC815\uC0C1)"));
3009
2988
  } else {
3010
- console.log(chalk10.dim(` \u2B1A ${file.name}`) + chalk10.dim(` \u2014 ${file.hint}`));
2989
+ console.log(chalk9.dim(` \u2B1A ${file.name}`) + chalk9.dim(` \u2014 ${file.hint}`));
3011
2990
  }
3012
2991
  }
3013
2992
  console.log("");
3014
- console.log(chalk10.bold(` ${ko.doctor.driftTitle}`));
2993
+ console.log(chalk9.bold(` ${ko.doctor.driftTitle}`));
3015
2994
  const ruleDrift = checkRuleDrift(cwd);
3016
2995
  if (!ruleDrift.checked) {
3017
- console.log(chalk10.dim(` ${ko.doctor.driftNoRules}`));
2996
+ console.log(chalk9.dim(` ${ko.doctor.driftNoRules}`));
3018
2997
  } else {
3019
2998
  const drifted = ruleDrift.results.filter((r) => r.status === "drifted");
3020
2999
  if (drifted.length === 0) {
3021
- console.log(chalk10.green(` ${ko.doctor.driftRuleClean}`));
3000
+ console.log(chalk9.green(` ${ko.doctor.driftRuleClean}`));
3022
3001
  } else {
3023
- console.log(chalk10.yellow(` ${ko.doctor.driftRuleWarn(drifted.map((d) => d.path).join(", "))}`));
3002
+ console.log(chalk9.yellow(` ${ko.doctor.driftRuleWarn(drifted.map((d) => d.path).join(", "))}`));
3024
3003
  }
3025
3004
  }
3026
3005
  const ctxDrift = checkContextDrift(cwd);
3027
3006
  if (ctxDrift.checked && ctxDrift.stale) {
3028
- console.log(chalk10.yellow(` ${ko.doctor.driftContextWarn}`));
3007
+ console.log(chalk9.yellow(` ${ko.doctor.driftContextWarn}`));
3029
3008
  }
3030
3009
  console.log("");
3031
3010
  if (allOk) {
3032
- console.log(chalk10.green.bold(` ${ko.doctor.allOk}`));
3011
+ console.log(chalk9.green.bold(` ${ko.doctor.allOk}`));
3033
3012
  printNextStep({
3034
3013
  message: ko.doctor.nextOkMessage,
3035
3014
  command: "vhk \uC2DC\uC791",
3036
3015
  cursorHint: "\uD504\uB85C\uC81D\uD2B8 \uB9CC\uB4E4\uC5B4\uC918"
3037
3016
  });
3038
3017
  } else {
3039
- console.log(chalk10.yellow.bold(` ${ko.doctor.missing} ${ko.doctor.missingHint}`));
3018
+ console.log(chalk9.yellow.bold(` ${ko.doctor.missing} ${ko.doctor.missingHint}`));
3040
3019
  printNextStep({
3041
3020
  message: ko.doctor.nextRetryMessage,
3042
3021
  command: "vhk doctor",
@@ -3047,7 +3026,7 @@ ${ko.doctor.title}
3047
3026
  }
3048
3027
 
3049
3028
  // src/commands/ship.ts
3050
- import chalk11 from "chalk";
3029
+ import chalk10 from "chalk";
3051
3030
  import inquirer4 from "inquirer";
3052
3031
  import fs9 from "fs";
3053
3032
  import path10 from "path";
@@ -3087,29 +3066,30 @@ function updateChangelogUnreleased(cwd, version, date) {
3087
3066
  }
3088
3067
  async function ship() {
3089
3068
  if (!ensureNotHardStopped("ship")) return;
3090
- console.log(chalk11.bold(`
3069
+ if (!ensureInteractive("\uBC30\uD3EC \uCCB4\uD06C\uB9AC\uC2A4\uD2B8\xB7\uD68C\uACE0\uB294 \uB300\uD654\uD615 \uC785\uB825\uC774 \uD544\uC694\uD569\uB2C8\uB2E4. PowerShell \uB4F1 TTY \uC5D0\uC11C \uC2E4\uD589\uD558\uC138\uC694.")) return;
3070
+ console.log(chalk10.bold(`
3091
3071
  ${ko.ship.title}
3092
3072
  `));
3093
3073
  const cwd = process.cwd();
3094
- console.log(chalk11.cyan.bold(` ${ko.ship.checklist}
3074
+ console.log(chalk10.cyan.bold(` ${ko.ship.checklist}
3095
3075
  `));
3096
3076
  const { passed } = await inquirer4.prompt([{
3097
3077
  type: "checkbox",
3098
3078
  name: "passed",
3099
3079
  message: ko.ship.checkboxPrompt,
3100
3080
  choices: CHECKLIST.map((c) => ({
3101
- name: `${ko.ship[c.questionKey]} ${chalk11.dim(`(${ko.ship[c.hintKey]})`)}`,
3081
+ name: `${ko.ship[c.questionKey]} ${chalk10.dim(`(${ko.ship[c.hintKey]})`)}`,
3102
3082
  value: c.id
3103
3083
  }))
3104
3084
  }]);
3105
3085
  const allPassed = passed.length === CHECKLIST.length;
3106
3086
  const skipped = CHECKLIST.filter((c) => !passed.includes(c.id));
3107
3087
  if (!allPassed) {
3108
- console.log(chalk11.yellow(`
3088
+ console.log(chalk10.yellow(`
3109
3089
  ${ko.ship.incompleteHeader}`));
3110
3090
  skipped.forEach((s) => {
3111
- console.log(chalk11.yellow(` \u2022 ${ko.ship[s.questionKey]}`));
3112
- console.log(chalk11.dim(` \u2192 ${ko.ship[s.hintKey]}`));
3091
+ console.log(chalk10.yellow(` \u2022 ${ko.ship[s.questionKey]}`));
3092
+ console.log(chalk10.dim(` \u2192 ${ko.ship[s.hintKey]}`));
3113
3093
  });
3114
3094
  const { proceed } = await inquirer4.prompt([{
3115
3095
  type: "confirm",
@@ -3126,13 +3106,13 @@ ${ko.ship.title}
3126
3106
  return;
3127
3107
  }
3128
3108
  } else {
3129
- console.log(chalk11.green(`
3109
+ console.log(chalk10.green(`
3130
3110
  ${ko.ship.allPassed}
3131
3111
  `));
3132
3112
  }
3133
- console.log(chalk11.cyan.bold(` ${ko.ship.retro}
3113
+ console.log(chalk10.cyan.bold(` ${ko.ship.retro}
3134
3114
  `));
3135
- console.log(chalk11.dim(` ${ko.ship.versionHint}`));
3115
+ console.log(chalk10.dim(` ${ko.ship.versionHint}`));
3136
3116
  const retro = await inquirer4.prompt([
3137
3117
  { type: "input", name: "version", message: ko.ship.versionPrompt },
3138
3118
  { type: "input", name: "whatWentWell", message: ko.ship.questionWell },
@@ -3175,7 +3155,7 @@ ${ko.ship.title}
3175
3155
  `*Generated by \`vhk ship\` at ${(/* @__PURE__ */ new Date()).toISOString()}*`
3176
3156
  ].join("\n");
3177
3157
  fs9.writeFileSync(filePath, content, "utf-8");
3178
- console.log(chalk11.green(`
3158
+ console.log(chalk10.green(`
3179
3159
  ${ko.ship.buildLogDone(path10.relative(cwd, filePath))}`));
3180
3160
  const changelogResult = updateChangelogUnreleased(cwd, versionSlug, today);
3181
3161
  if (changelogResult.status === "updated") {
@@ -3195,7 +3175,7 @@ ${ko.ship.title}
3195
3175
 
3196
3176
  // src/commands/save.ts
3197
3177
  import { execFileSync } from "child_process";
3198
- import chalk12 from "chalk";
3178
+ import chalk11 from "chalk";
3199
3179
  import ora from "ora";
3200
3180
  import inquirer5 from "inquirer";
3201
3181
 
@@ -3223,29 +3203,29 @@ function statusIcon(code) {
3223
3203
  return "\u{1F4C4}";
3224
3204
  }
3225
3205
  async function save() {
3226
- console.log(chalk12.bold(`
3206
+ console.log(chalk11.bold(`
3227
3207
  \u{1F4BE} ${t("save.title")}`));
3228
- console.log(chalk12.gray("\u2500".repeat(40)));
3208
+ console.log(chalk11.gray("\u2500".repeat(40)));
3229
3209
  let gitRoot;
3230
3210
  try {
3231
3211
  execFileSync("git", ["rev-parse", "--is-inside-work-tree"], { stdio: "pipe" });
3232
3212
  gitRoot = getGitRoot();
3233
3213
  } catch {
3234
- console.log(chalk12.red(`\u274C ${t("save.notGitRepo")}`));
3214
+ console.log(chalk11.red(`\u274C ${t("save.notGitRepo")}`));
3235
3215
  return;
3236
3216
  }
3237
- console.log(chalk12.cyan(`
3217
+ console.log(chalk11.cyan(`
3238
3218
  \u{1F512} ${t("save.securityWarnHeader")}`));
3239
3219
  printSecurityWarnings(gitRoot);
3240
3220
  const severe = filterSevereFindings(scanProjectForSecrets(gitRoot).findings);
3241
3221
  if (severe.length > 0) {
3242
- console.log(chalk12.red(`
3222
+ console.log(chalk11.red(`
3243
3223
  \u26A0\uFE0F ${t("save.secretsFound", severe.length)}`));
3244
3224
  severe.slice(0, 5).forEach((f) => {
3245
- console.log(chalk12.dim(` ${f.file}:${f.line} \u2014 ${f.patternName}`));
3225
+ console.log(chalk11.dim(` ${f.file}:${f.line} \u2014 ${f.patternName}`));
3246
3226
  });
3247
3227
  if (severe.length > 5) {
3248
- console.log(chalk12.dim(` ... \uC678 ${severe.length - 5}\uAC74 (vhk \uBCF4\uC548 scan)`));
3228
+ console.log(chalk11.dim(` ... \uC678 ${severe.length - 5}\uAC74 (vhk \uBCF4\uC548 scan)`));
3249
3229
  }
3250
3230
  const proceed = await promptOrDefault(
3251
3231
  async () => (await inquirer5.prompt([{
@@ -3258,16 +3238,16 @@ async function save() {
3258
3238
  // 비대화형 = 시크릿 커밋 안 함 (안전)
3259
3239
  );
3260
3240
  if (!proceed) {
3261
- console.log(chalk12.gray(t("save.cancelled")));
3241
+ console.log(chalk11.gray(t("save.cancelled")));
3262
3242
  return;
3263
3243
  }
3264
3244
  }
3265
3245
  const lines = parsePorcelainLines(gitOut(["status", "--porcelain"], gitRoot));
3266
3246
  if (lines.length === 0) {
3267
- console.log(chalk12.yellow(`\u{1F4ED} ${t("save.noChanges")}`));
3247
+ console.log(chalk11.yellow(`\u{1F4ED} ${t("save.noChanges")}`));
3268
3248
  return;
3269
3249
  }
3270
- console.log(chalk12.cyan(`
3250
+ console.log(chalk11.cyan(`
3271
3251
  \u{1F4CB} ${t("save.filesHeader", lines.length)}`));
3272
3252
  lines.forEach((line) => {
3273
3253
  const code = line.substring(0, 2);
@@ -3292,21 +3272,21 @@ async function save() {
3292
3272
  spinner.text = t("save.pushing");
3293
3273
  if (!hasGitRemote(gitRoot)) {
3294
3274
  spinner.succeed(t("save.successLocal"));
3295
- console.log(chalk12.yellow(` \u{1F4A1} ${t("save.noRemote")}`));
3275
+ console.log(chalk11.yellow(` \u{1F4A1} ${t("save.noRemote")}`));
3296
3276
  } else {
3297
3277
  try {
3298
3278
  gitRun(["push"], gitRoot);
3299
3279
  spinner.succeed(t("save.successWithPush"));
3300
3280
  } catch (pushErr) {
3301
3281
  spinner.fail(t("save.pushFailed"));
3302
- console.log(chalk12.red(getExecErrorMessage(pushErr)));
3303
- console.log(chalk12.yellow(`
3282
+ console.log(chalk11.red(getExecErrorMessage(pushErr)));
3283
+ console.log(chalk11.yellow(`
3304
3284
  \u{1F4A1} ${t("save.commitOkPushFailed")}`));
3305
3285
  process.exitCode = 1;
3306
3286
  }
3307
3287
  }
3308
3288
  if (process.exitCode !== 1) {
3309
- console.log(chalk12.green(`
3289
+ console.log(chalk11.green(`
3310
3290
  \u2705 ${t("save.done", lines.length)}`));
3311
3291
  printNextStep({
3312
3292
  message: t("save.nextOkMessage"),
@@ -3314,7 +3294,7 @@ async function save() {
3314
3294
  cursorHint: t("save.nextOkCursor")
3315
3295
  });
3316
3296
  } else {
3317
- console.log(chalk12.green(`
3297
+ console.log(chalk11.green(`
3318
3298
  \u2705 ${t("save.doneLocalOnly", lines.length)}`));
3319
3299
  printNextStep({
3320
3300
  message: t("save.nextPushFailMessage"),
@@ -3324,12 +3304,12 @@ async function save() {
3324
3304
  }
3325
3305
  } catch (err) {
3326
3306
  spinner.fail(t("save.failed"));
3327
- console.log(chalk12.red(getExecErrorMessage(err)));
3307
+ console.log(chalk11.red(getExecErrorMessage(err)));
3328
3308
  if (didAdd) {
3329
3309
  try {
3330
3310
  const staged = gitOut(["diff", "--cached", "--stat"], gitRoot).trim();
3331
3311
  if (staged) {
3332
- console.log(chalk12.yellow(`
3312
+ console.log(chalk11.yellow(`
3333
3313
  \u{1F4A1} ${t("save.stagedAfterFail")}`));
3334
3314
  }
3335
3315
  } catch {
@@ -3341,7 +3321,7 @@ async function save() {
3341
3321
 
3342
3322
  // src/commands/undo.ts
3343
3323
  import { execFileSync as execFileSync2 } from "child_process";
3344
- import chalk13 from "chalk";
3324
+ import chalk12 from "chalk";
3345
3325
  import inquirer6 from "inquirer";
3346
3326
  function parseRecentCommits(logOutput) {
3347
3327
  return logOutput.split("\n").map((l) => l.trim()).filter(Boolean);
@@ -3365,30 +3345,30 @@ function isUndoRisky(undoCount, unpushedCount, hasRemote) {
3365
3345
  return false;
3366
3346
  }
3367
3347
  async function undo() {
3368
- console.log(chalk13.bold(`
3348
+ console.log(chalk12.bold(`
3369
3349
  \u23EA ${t("undo.title")}`));
3370
- console.log(chalk13.gray("\u2500".repeat(40)));
3350
+ console.log(chalk12.gray("\u2500".repeat(40)));
3371
3351
  let gitRoot;
3372
3352
  try {
3373
3353
  execFileSync2("git", ["rev-parse", "--is-inside-work-tree"], { stdio: "pipe" });
3374
3354
  gitRoot = getGitRoot();
3375
3355
  } catch {
3376
- console.log(chalk13.red(`\u274C ${t("undo.notGitRepo")}`));
3356
+ console.log(chalk12.red(`\u274C ${t("undo.notGitRepo")}`));
3377
3357
  return;
3378
3358
  }
3379
3359
  let logOutput;
3380
3360
  try {
3381
3361
  logOutput = gitOut(["log", "--oneline", "-5"], gitRoot).trim();
3382
3362
  } catch {
3383
- console.log(chalk13.yellow(`\u{1F4ED} ${t("undo.noCommits")}`));
3363
+ console.log(chalk12.yellow(`\u{1F4ED} ${t("undo.noCommits")}`));
3384
3364
  return;
3385
3365
  }
3386
3366
  const commits = parseRecentCommits(logOutput);
3387
3367
  if (commits.length === 0) {
3388
- console.log(chalk13.yellow(`\u{1F4ED} ${t("undo.noCommits")}`));
3368
+ console.log(chalk12.yellow(`\u{1F4ED} ${t("undo.noCommits")}`));
3389
3369
  return;
3390
3370
  }
3391
- console.log(chalk13.cyan(`
3371
+ console.log(chalk12.cyan(`
3392
3372
  ${t("undo.recentHeader")}`));
3393
3373
  commits.forEach((c, i) => {
3394
3374
  console.log(` ${i === 0 ? "\u{1F449}" : " "} ${c}`);
@@ -3405,7 +3385,7 @@ ${t("undo.recentHeader")}`));
3405
3385
  const undoCount = Math.min(Math.max(1, count || 1), maxUndo);
3406
3386
  const headCount = countLocalCommits(gitRoot);
3407
3387
  if (undoCount >= headCount) {
3408
- console.log(chalk13.yellow(`
3388
+ console.log(chalk12.yellow(`
3409
3389
  \u{1F4ED} ${t("undo.rootCommit")}`));
3410
3390
  return;
3411
3391
  }
@@ -3414,10 +3394,10 @@ ${t("undo.recentHeader")}`));
3414
3394
  const risky = isUndoRisky(undoCount, unpushed, remote);
3415
3395
  if (risky) {
3416
3396
  if (unpushed < 0) {
3417
- console.log(chalk13.red(`
3397
+ console.log(chalk12.red(`
3418
3398
  \u26A0\uFE0F ${t("undo.noUpstreamWarning")}`));
3419
3399
  } else {
3420
- console.log(chalk13.red(`
3400
+ console.log(chalk12.red(`
3421
3401
  \u26A0\uFE0F ${t("undo.alreadyPushed")}`));
3422
3402
  }
3423
3403
  }
@@ -3428,16 +3408,16 @@ ${t("undo.recentHeader")}`));
3428
3408
  default: false
3429
3409
  }]);
3430
3410
  if (!confirm) {
3431
- console.log(chalk13.gray(t("undo.cancelled")));
3411
+ console.log(chalk12.gray(t("undo.cancelled")));
3432
3412
  return;
3433
3413
  }
3434
3414
  try {
3435
3415
  gitRun(["reset", "--soft", `HEAD~${undoCount}`], gitRoot);
3436
- console.log(chalk13.green(`
3416
+ console.log(chalk12.green(`
3437
3417
  \u2705 ${t("undo.success")}`));
3438
- console.log(chalk13.gray(` \u{1F4A1} ${t("undo.stagedHint")}`));
3418
+ console.log(chalk12.gray(` \u{1F4A1} ${t("undo.stagedHint")}`));
3439
3419
  if (risky) {
3440
- console.log(chalk13.yellow(`
3420
+ console.log(chalk12.yellow(`
3441
3421
  \u{1F4A1} ${t("undo.forcePushHint")}`));
3442
3422
  }
3443
3423
  printNextStep({
@@ -3446,35 +3426,35 @@ ${t("undo.recentHeader")}`));
3446
3426
  cursorHint: t("undo.nextCursor")
3447
3427
  });
3448
3428
  } catch (err) {
3449
- console.log(chalk13.red(`\u274C ${t("undo.failed")}`));
3429
+ console.log(chalk12.red(`\u274C ${t("undo.failed")}`));
3450
3430
  const msg = err instanceof Error ? err.message : String(err);
3451
- console.log(chalk13.red(msg));
3431
+ console.log(chalk12.red(msg));
3452
3432
  process.exitCode = 1;
3453
3433
  }
3454
3434
  }
3455
3435
 
3456
3436
  // src/commands/restore.ts
3457
- import chalk14 from "chalk";
3437
+ import chalk13 from "chalk";
3458
3438
  import inquirer7 from "inquirer";
3459
3439
  async function restore(id) {
3460
- console.log(chalk14.bold(`
3440
+ console.log(chalk13.bold(`
3461
3441
  ${ko.restore.title}`));
3462
- console.log(chalk14.gray("\u2500".repeat(40)));
3463
- console.log(chalk14.dim(` ${ko.restore.notGitNote}`));
3442
+ console.log(chalk13.gray("\u2500".repeat(40)));
3443
+ console.log(chalk13.dim(` ${ko.restore.notGitNote}`));
3464
3444
  const cwd = process.cwd();
3465
3445
  const backups = listBackups(cwd);
3466
3446
  if (backups.length === 0) {
3467
- console.log(chalk14.yellow(`
3447
+ console.log(chalk13.yellow(`
3468
3448
  ${ko.restore.noBackups}`));
3469
3449
  return;
3470
3450
  }
3471
3451
  let targetId = id;
3472
3452
  if (!targetId) {
3473
3453
  if (!process.stdout.isTTY) {
3474
- console.log(chalk14.cyan(`
3454
+ console.log(chalk13.cyan(`
3475
3455
  ${ko.restore.listHeader}`));
3476
3456
  for (const b of backups) console.log(` ${b.id} (${b.files.length}\uAC1C \uD30C\uC77C)`);
3477
- console.log(chalk14.yellow(`
3457
+ console.log(chalk13.yellow(`
3478
3458
  ${ko.restore.nonTtyHint}`));
3479
3459
  return;
3480
3460
  }
@@ -3493,16 +3473,16 @@ ${ko.restore.nonTtyHint}`));
3493
3473
  }
3494
3474
  try {
3495
3475
  const restored = restoreBackup(targetId, cwd);
3496
- console.log(chalk14.green(`
3476
+ console.log(chalk13.green(`
3497
3477
  ${ko.restore.restored(restored.length, targetId)}`));
3498
- for (const r of restored) console.log(chalk14.gray(` ${r}`));
3478
+ for (const r of restored) console.log(chalk13.gray(` ${r}`));
3499
3479
  printNextStep({
3500
3480
  message: "\uBC31\uC5C5 \uBCF5\uC6D0 \uC644\uB8CC! \uBCC0\uACBD \uB0B4\uC6A9\uC744 \uD655\uC778\uD558\uC138\uC694.",
3501
3481
  command: "vhk diff",
3502
3482
  cursorHint: "\uBCC0\uACBD\uC0AC\uD56D \uBCF4\uC5EC\uC918"
3503
3483
  });
3504
3484
  } catch {
3505
- console.log(chalk14.red(`
3485
+ console.log(chalk13.red(`
3506
3486
  ${ko.restore.notFound(targetId)}`));
3507
3487
  process.exitCode = 1;
3508
3488
  }
@@ -3512,7 +3492,7 @@ ${ko.restore.notFound(targetId)}`));
3512
3492
  import { execFileSync as execFileSync3 } from "child_process";
3513
3493
  import fs10 from "fs";
3514
3494
  import path11 from "path";
3515
- import chalk15 from "chalk";
3495
+ import chalk14 from "chalk";
3516
3496
  function countFileChanges(porcelain) {
3517
3497
  const lines = porcelain.split("\n").filter(Boolean);
3518
3498
  let staged = 0;
@@ -3587,15 +3567,15 @@ function getSyncCounts(gitRoot) {
3587
3567
  }
3588
3568
  }
3589
3569
  async function status() {
3590
- console.log(chalk15.bold(`
3570
+ console.log(chalk14.bold(`
3591
3571
  \u{1F4CA} ${t("status.title")}`));
3592
- console.log(chalk15.gray("\u2500".repeat(40)));
3572
+ console.log(chalk14.gray("\u2500".repeat(40)));
3593
3573
  let gitRoot;
3594
3574
  try {
3595
3575
  execFileSync3("git", ["rev-parse", "--is-inside-work-tree"], { stdio: "pipe" });
3596
3576
  gitRoot = getGitRoot();
3597
3577
  } catch {
3598
- console.log(chalk15.red(`\u274C ${t("status.notGitRepo")}`));
3578
+ console.log(chalk14.red(`\u274C ${t("status.notGitRepo")}`));
3599
3579
  return;
3600
3580
  }
3601
3581
  let branch;
@@ -3614,29 +3594,29 @@ async function status() {
3614
3594
  commits = [];
3615
3595
  }
3616
3596
  const pkg = readProjectPackage();
3617
- console.log(chalk15.cyan(`
3618
- \u{1F33F} ${t("status.branch")}`) + chalk15.white(` ${branch}`));
3597
+ console.log(chalk14.cyan(`
3598
+ \u{1F33F} ${t("status.branch")}`) + chalk14.white(` ${branch}`));
3619
3599
  console.log(
3620
- chalk15.cyan(`\u{1F4C1} ${t("status.changes")}`) + chalk15.white(
3600
+ chalk14.cyan(`\u{1F4C1} ${t("status.changes")}`) + chalk14.white(
3621
3601
  ` staged ${counts.staged} \xB7 unstaged ${counts.unstaged} \xB7 untracked ${counts.untracked}`
3622
3602
  )
3623
3603
  );
3624
- console.log(chalk15.cyan(`
3604
+ console.log(chalk14.cyan(`
3625
3605
  \u{1F4CB} ${t("status.recentCommits", commits.length)}`));
3626
3606
  if (commits.length === 0) {
3627
- console.log(chalk15.dim(` ${t("status.noCommits")}`));
3607
+ console.log(chalk14.dim(` ${t("status.noCommits")}`));
3628
3608
  } else {
3629
- commits.forEach((c) => console.log(` ${chalk15.dim("\u2022")} ${c}`));
3609
+ commits.forEach((c) => console.log(` ${chalk14.dim("\u2022")} ${c}`));
3630
3610
  }
3631
3611
  console.log(
3632
- chalk15.cyan(`
3633
- \u{1F504} ${t("status.remote")}`) + chalk15.white(` ${formatSyncLabel(sync2)}`)
3612
+ chalk14.cyan(`
3613
+ \u{1F504} ${t("status.remote")}`) + chalk14.white(` ${formatSyncLabel(sync2)}`)
3634
3614
  );
3635
- console.log(chalk15.gray("\n" + "\u2500".repeat(40)));
3615
+ console.log(chalk14.gray("\n" + "\u2500".repeat(40)));
3636
3616
  if (pkg) {
3637
- console.log(chalk15.cyan(`\u{1F4E6} ${t("status.package")}`) + chalk15.white(` ${pkg.name} v${pkg.version}`));
3617
+ console.log(chalk14.cyan(`\u{1F4E6} ${t("status.package")}`) + chalk14.white(` ${pkg.name} v${pkg.version}`));
3638
3618
  } else {
3639
- console.log(chalk15.dim(`\u{1F4E6} ${t("status.noPackage")}`));
3619
+ console.log(chalk14.dim(`\u{1F4E6} ${t("status.noPackage")}`));
3640
3620
  }
3641
3621
  const hasChanges = counts.staged + counts.unstaged + counts.untracked > 0;
3642
3622
  printNextStep(selectStatusNextStep(hasChanges));
@@ -3644,7 +3624,7 @@ async function status() {
3644
3624
  }
3645
3625
 
3646
3626
  // src/commands/diff.ts
3647
- import chalk16 from "chalk";
3627
+ import chalk15 from "chalk";
3648
3628
  function gitOut2(args) {
3649
3629
  const r = safeExecFile("git", args);
3650
3630
  return r.ok ? r.out : "";
@@ -3681,51 +3661,51 @@ function summarizeNumstat(numstat) {
3681
3661
  return { fileCount, totalAdd, totalDel };
3682
3662
  }
3683
3663
  function printFile(f) {
3684
- const adds = f.additions > 0 ? chalk16.green(`+${f.additions}`) : "";
3685
- const dels = f.deletions > 0 ? chalk16.red(`-${f.deletions}`) : "";
3664
+ const adds = f.additions > 0 ? chalk15.green(`+${f.additions}`) : "";
3665
+ const dels = f.deletions > 0 ? chalk15.red(`-${f.deletions}`) : "";
3686
3666
  const change = [adds, dels].filter(Boolean).join(" ");
3687
3667
  console.log(` ${f.name} ${change}`);
3688
3668
  }
3689
3669
  async function diff() {
3690
- console.log(chalk16.bold(`
3670
+ console.log(chalk15.bold(`
3691
3671
  \u{1F50D} ${t("diff.title")}`));
3692
- console.log(chalk16.gray("\u2500".repeat(40)));
3672
+ console.log(chalk15.gray("\u2500".repeat(40)));
3693
3673
  if (!safeExecFile("git", ["rev-parse", "--is-inside-work-tree"]).ok) {
3694
- console.log(chalk16.red(`\u274C ${t("diff.notGitRepo")}`));
3674
+ console.log(chalk15.red(`\u274C ${t("diff.notGitRepo")}`));
3695
3675
  return;
3696
3676
  }
3697
3677
  const unstaged = gitOut2(["diff", "--stat"]);
3698
3678
  const staged = gitOut2(["diff", "--cached", "--stat"]);
3699
3679
  const untracked = gitOut2(["ls-files", "--others", "--exclude-standard"]);
3700
3680
  if (!unstaged && !staged && !untracked) {
3701
- console.log(chalk16.green(`
3681
+ console.log(chalk15.green(`
3702
3682
  \u2705 ${t("diff.noChanges")}`));
3703
3683
  return;
3704
3684
  }
3705
3685
  if (staged) {
3706
- console.log(chalk16.cyan(`
3686
+ console.log(chalk15.cyan(`
3707
3687
  ${t("diff.stagedHeader")}`));
3708
3688
  parseDiffStat(staged).forEach((f) => printFile(f));
3709
3689
  }
3710
3690
  if (unstaged) {
3711
- console.log(chalk16.cyan(`
3691
+ console.log(chalk15.cyan(`
3712
3692
  ${t("diff.unstagedHeader")}`));
3713
3693
  parseDiffStat(unstaged).forEach((f) => printFile(f));
3714
3694
  }
3715
3695
  if (untracked) {
3716
3696
  const files = untracked.split("\n").filter(Boolean);
3717
- console.log(chalk16.cyan(`
3697
+ console.log(chalk15.cyan(`
3718
3698
  ${t("diff.untrackedHeader", files.length)}`));
3719
- files.forEach((f) => console.log(` ${chalk16.green("+")} ${f}`));
3699
+ files.forEach((f) => console.log(` ${chalk15.green("+")} ${f}`));
3720
3700
  }
3721
3701
  const numstat = gitOut2(["diff", "--numstat", "HEAD"]);
3722
3702
  if (numstat) {
3723
3703
  const { fileCount, totalAdd, totalDel } = summarizeNumstat(numstat);
3724
- console.log(chalk16.cyan(`
3704
+ console.log(chalk15.cyan(`
3725
3705
  ${t("diff.summaryHeader")}`));
3726
3706
  console.log(` ${t("diff.filesLine", fileCount)}`);
3727
- console.log(` \uCD94\uAC00: ${chalk16.green(`+${totalAdd}`)}\uC904`);
3728
- console.log(` \uC0AD\uC81C: ${chalk16.red(`-${totalDel}`)}\uC904`);
3707
+ console.log(` \uCD94\uAC00: ${chalk15.green(`+${totalAdd}`)}\uC904`);
3708
+ console.log(` \uC0AD\uC81C: ${chalk15.red(`-${totalDel}`)}\uC904`);
3729
3709
  }
3730
3710
  console.log("");
3731
3711
  }
@@ -3734,7 +3714,7 @@ ${t("diff.summaryHeader")}`));
3734
3714
  import { existsSync as existsSync4, mkdirSync as mkdirSync3, writeFileSync as writeFileSync3 } from "fs";
3735
3715
  import { join as join5, dirname } from "path";
3736
3716
  import { fileURLToPath as fileURLToPath2 } from "url";
3737
- import chalk17 from "chalk";
3717
+ import chalk16 from "chalk";
3738
3718
  function resolveMcpEntryPoint() {
3739
3719
  try {
3740
3720
  const here = fileURLToPath2(import.meta.url);
@@ -3774,8 +3754,8 @@ function resolveVhkMcpEntry() {
3774
3754
  return { command: "vhk-mcp", args: [] };
3775
3755
  }
3776
3756
  async function mcpInit() {
3777
- console.log(chalk17.bold("\n\u{1F50C} " + t("mcp.initTitle")));
3778
- console.log(chalk17.gray("\u2500".repeat(40)));
3757
+ console.log(chalk16.bold("\n\u{1F50C} " + t("mcp.initTitle")));
3758
+ console.log(chalk16.gray("\u2500".repeat(40)));
3779
3759
  const cursorDir = join5(process.cwd(), ".cursor");
3780
3760
  if (!existsSync4(cursorDir)) {
3781
3761
  mkdirSync3(cursorDir, { recursive: true });
@@ -3790,15 +3770,15 @@ async function mcpInit() {
3790
3770
  mcpServers: { ...parsed.mcpServers ?? {}, vhk: vhkEntry }
3791
3771
  };
3792
3772
  } catch {
3793
- console.log(chalk17.yellow("\u26A0\uFE0F \uAE30\uC874 .cursor/mcp.json \uD30C\uC2F1 \uC2E4\uD328 \u2014 \uC0C8 \uD30C\uC77C\uB85C \uB36E\uC5B4\uC501\uB2C8\uB2E4."));
3773
+ console.log(chalk16.yellow("\u26A0\uFE0F \uAE30\uC874 .cursor/mcp.json \uD30C\uC2F1 \uC2E4\uD328 \u2014 \uC0C8 \uD30C\uC77C\uB85C \uB36E\uC5B4\uC501\uB2C8\uB2E4."));
3794
3774
  config = { mcpServers: { vhk: vhkEntry } };
3795
3775
  }
3796
3776
  } else {
3797
3777
  config = { mcpServers: { vhk: vhkEntry } };
3798
3778
  }
3799
3779
  writeFileSync3(configPath, JSON.stringify(config, null, 2) + "\n", "utf-8");
3800
- console.log(chalk17.green("\n\u2705 Cursor MCP \uC124\uC815 \uC644\uB8CC!"));
3801
- console.log(chalk17.cyan("\u{1F4C1} \uC0DD\uC131\uB41C \uD30C\uC77C:"));
3780
+ console.log(chalk16.green("\n\u2705 Cursor MCP \uC124\uC815 \uC644\uB8CC!"));
3781
+ console.log(chalk16.cyan("\u{1F4C1} \uC0DD\uC131\uB41C \uD30C\uC77C:"));
3802
3782
  console.log(` ${configPath}`);
3803
3783
  printNextStep({
3804
3784
  message: t("mcp.nextMessage"),
@@ -3809,7 +3789,7 @@ async function mcpInit() {
3809
3789
 
3810
3790
  // src/commands/design.ts
3811
3791
  import { existsSync as existsSync5, mkdirSync as mkdirSync4, writeFileSync as writeFileSync4 } from "fs";
3812
- import chalk18 from "chalk";
3792
+ import chalk17 from "chalk";
3813
3793
  import inquirer8 from "inquirer";
3814
3794
  var PALETTES = [
3815
3795
  {
@@ -3912,8 +3892,8 @@ export default vhkColors
3912
3892
  `;
3913
3893
  }
3914
3894
  async function design() {
3915
- console.log(chalk18.bold("\n\u{1F3A8} " + t("design.title")));
3916
- console.log(chalk18.gray("\u2500".repeat(40)));
3895
+ console.log(chalk17.bold("\n\u{1F3A8} " + t("design.title")));
3896
+ console.log(chalk17.gray("\u2500".repeat(40)));
3917
3897
  if (!ensureInteractive("\uCEEC\uB7EC \uD314\uB808\uD2B8 \uC120\uD0DD\uC740 \uB300\uD654\uD615\uC73C\uB85C\uB9CC \uAC00\uB2A5\uD569\uB2C8\uB2E4.")) return;
3918
3898
  const { paletteIndex } = await inquirer8.prompt([
3919
3899
  {
@@ -3927,7 +3907,7 @@ async function design() {
3927
3907
  }
3928
3908
  ]);
3929
3909
  const palette = PALETTES[paletteIndex];
3930
- console.log(chalk18.cyan(`
3910
+ console.log(chalk17.cyan(`
3931
3911
  \u{1F3A8} \uC120\uD0DD\uB41C \uD314\uB808\uD2B8: ${palette.name}`));
3932
3912
  const v4 = hasTailwindV4();
3933
3913
  const targetPath = v4 ? "src/styles/theme.css" : hasTailwind() ? "src/styles/vhk-colors.ts" : "src/styles/tokens.css";
@@ -3940,24 +3920,24 @@ async function design() {
3940
3920
  default: false
3941
3921
  }]);
3942
3922
  if (!overwrite) {
3943
- console.log(chalk18.yellow("\n\u23ED\uFE0F \uC0DD\uC131 \uCDE8\uC18C \u2014 \uAE30\uC874 \uD30C\uC77C \uC720\uC9C0."));
3923
+ console.log(chalk17.yellow("\n\u23ED\uFE0F \uC0DD\uC131 \uCDE8\uC18C \u2014 \uAE30\uC874 \uD30C\uC77C \uC720\uC9C0."));
3944
3924
  return;
3945
3925
  }
3946
3926
  }
3947
3927
  mkdirSync4("src/styles", { recursive: true });
3948
3928
  writeFileSync4(targetPath, content, "utf-8");
3949
3929
  if (v4) {
3950
- console.log(chalk18.green("\n\u2705 src/styles/theme.css \uC0DD\uC131 (Tailwind v4 @theme)"));
3951
- console.log(chalk18.gray(' \uC9C4\uC785 CSS(\uC608: src/index.css)\uC5D0 `@import "./styles/theme.css";` \uCD94\uAC00 \u2192 bg-primary \uB4F1 \uC720\uD2F8 \uC0AC\uC6A9.'));
3952
- console.log(chalk18.gray(" \uB2E4\uD06C \uD1A0\uAE00: \uB8E8\uD2B8 <html>/<body> \uC5D0 `.dark` \uD074\uB798\uC2A4 on/off."));
3930
+ console.log(chalk17.green("\n\u2705 src/styles/theme.css \uC0DD\uC131 (Tailwind v4 @theme)"));
3931
+ console.log(chalk17.gray(' \uC9C4\uC785 CSS(\uC608: src/index.css)\uC5D0 `@import "./styles/theme.css";` \uCD94\uAC00 \u2192 bg-primary \uB4F1 \uC720\uD2F8 \uC0AC\uC6A9.'));
3932
+ console.log(chalk17.gray(" \uB2E4\uD06C \uD1A0\uAE00: \uB8E8\uD2B8 <html>/<body> \uC5D0 `.dark` \uD074\uB798\uC2A4 on/off."));
3953
3933
  } else if (hasTailwind()) {
3954
- console.log(chalk18.green("\n\u2705 src/styles/vhk-colors.ts \uC0DD\uC131"));
3955
- console.log(chalk18.gray(" tailwind.config\uC758 extend.colors\uC5D0 import \uD574\uC11C \uC0AC\uC6A9\uD558\uC138\uC694."));
3934
+ console.log(chalk17.green("\n\u2705 src/styles/vhk-colors.ts \uC0DD\uC131"));
3935
+ console.log(chalk17.gray(" tailwind.config\uC758 extend.colors\uC5D0 import \uD574\uC11C \uC0AC\uC6A9\uD558\uC138\uC694."));
3956
3936
  } else {
3957
- console.log(chalk18.green("\n\u2705 src/styles/tokens.css \uC0DD\uC131"));
3958
- console.log(chalk18.gray(" HTML\uC5D0 <link>\uB85C \uCD94\uAC00\uD558\uAC70\uB098 CSS\uC5D0\uC11C @import \uD558\uC138\uC694."));
3937
+ console.log(chalk17.green("\n\u2705 src/styles/tokens.css \uC0DD\uC131"));
3938
+ console.log(chalk17.gray(" HTML\uC5D0 <link>\uB85C \uCD94\uAC00\uD558\uAC70\uB098 CSS\uC5D0\uC11C @import \uD558\uC138\uC694."));
3959
3939
  }
3960
- console.log(chalk18.bold("\n\u{1F308} \uCEEC\uB7EC \uBBF8\uB9AC\uBCF4\uAE30:"));
3940
+ console.log(chalk17.bold("\n\u{1F308} \uCEEC\uB7EC \uBBF8\uB9AC\uBCF4\uAE30:"));
3961
3941
  for (const [key, value] of Object.entries(palette.colors)) {
3962
3942
  console.log(` ${key.padEnd(12)} ${value}`);
3963
3943
  }
@@ -3973,7 +3953,7 @@ async function designPalette() {
3973
3953
 
3974
3954
  // src/commands/theme.ts
3975
3955
  import { existsSync as existsSync6, mkdirSync as mkdirSync5, writeFileSync as writeFileSync5 } from "fs";
3976
- import chalk19 from "chalk";
3956
+ import chalk18 from "chalk";
3977
3957
  import inquirer9 from "inquirer";
3978
3958
  function generateDarkCSS() {
3979
3959
  return `/* vhk theme \u2014 \uB2E4\uD06C/\uB77C\uC774\uD2B8 \uBAA8\uB4DC CSS \uBCC0\uC218 */
@@ -4029,36 +4009,39 @@ export function initTheme(): void {
4029
4009
  }
4030
4010
  `;
4031
4011
  }
4032
- async function theme() {
4033
- console.log(chalk19.bold("\n\u{1F319} " + t("theme.title")));
4034
- console.log(chalk19.gray("\u2500".repeat(40)));
4012
+ async function theme(options) {
4013
+ console.log(chalk18.bold("\n\u{1F319} " + t("theme.title")));
4014
+ console.log(chalk18.gray("\u2500".repeat(40)));
4035
4015
  const cssPath = "src/styles/theme.css";
4036
4016
  const togglePath = "src/lib/theme-toggle.ts";
4037
4017
  const conflicts = [cssPath, togglePath].filter((p) => existsSync6(p));
4038
4018
  if (conflicts.length > 0) {
4039
- const { overwrite } = await inquirer9.prompt([{
4040
- type: "confirm",
4041
- name: "overwrite",
4042
- message: `\uB2E4\uC74C \uD30C\uC77C\uC774 \uC774\uBBF8 \uC788\uC5B4\uC694. \uB36E\uC5B4\uC4F8\uAE4C\uC694?
4019
+ const overwrite = options?.yes === true ? true : await promptOrDefault(
4020
+ async () => (await inquirer9.prompt([{
4021
+ type: "confirm",
4022
+ name: "overwrite",
4023
+ message: `\uB2E4\uC74C \uD30C\uC77C\uC774 \uC774\uBBF8 \uC788\uC5B4\uC694. \uB36E\uC5B4\uC4F8\uAE4C\uC694?
4043
4024
  ${conflicts.join("\n ")}`,
4044
- default: false
4045
- }]);
4025
+ default: false
4026
+ }])).overwrite,
4027
+ false
4028
+ );
4046
4029
  if (!overwrite) {
4047
- console.log(chalk19.yellow("\n\u23ED\uFE0F \uC0DD\uC131 \uCDE8\uC18C \u2014 \uAE30\uC874 \uD30C\uC77C \uC720\uC9C0."));
4030
+ console.log(chalk18.yellow("\n\u23ED\uFE0F \uC0DD\uC131 \uCDE8\uC18C \u2014 \uAE30\uC874 \uD30C\uC77C \uC720\uC9C0. (\uBE44\uB300\uD654\uD615\uC774\uBA74 --yes \uB85C \uB36E\uC5B4\uC4F0\uAE30)"));
4048
4031
  return;
4049
4032
  }
4050
4033
  }
4051
4034
  mkdirSync5("src/styles", { recursive: true });
4052
4035
  mkdirSync5("src/lib", { recursive: true });
4053
4036
  writeFileSync5(cssPath, generateDarkCSS(), "utf-8");
4054
- console.log(chalk19.green("\n\u2705 src/styles/theme.css \uC0DD\uC131 (\uB2E4\uD06C/\uB77C\uC774\uD2B8 \uBAA8\uB4DC)"));
4037
+ console.log(chalk18.green("\n\u2705 src/styles/theme.css \uC0DD\uC131 (\uB2E4\uD06C/\uB77C\uC774\uD2B8 \uBAA8\uB4DC)"));
4055
4038
  writeFileSync5(togglePath, generateToggleUtil(), "utf-8");
4056
- console.log(chalk19.green("\u2705 src/lib/theme-toggle.ts \uC0DD\uC131 (\uD1A0\uAE00 \uC720\uD2F8\uB9AC\uD2F0)"));
4057
- console.log(chalk19.bold("\n\u{1F4D6} \uC0AC\uC6A9\uBC95:"));
4058
- console.log(chalk19.gray(" 1. theme.css\uB97C \uAE00\uB85C\uBC8C \uC2A4\uD0C0\uC77C\uC5D0 \uCD94\uAC00"));
4059
- console.log(chalk19.gray(' 2. import { initTheme, toggleTheme } from "./lib/theme-toggle"'));
4060
- console.log(chalk19.gray(" 3. \uC571 \uC9C4\uC785\uC810\uC5D0\uC11C initTheme() \uD638\uCD9C"));
4061
- console.log(chalk19.gray(" 4. \uD1A0\uAE00 \uBC84\uD2BC\uC5D0\uC11C toggleTheme() \uD638\uCD9C"));
4039
+ console.log(chalk18.green("\u2705 src/lib/theme-toggle.ts \uC0DD\uC131 (\uD1A0\uAE00 \uC720\uD2F8\uB9AC\uD2F0)"));
4040
+ console.log(chalk18.bold("\n\u{1F4D6} \uC0AC\uC6A9\uBC95:"));
4041
+ console.log(chalk18.gray(" 1. theme.css\uB97C \uAE00\uB85C\uBC8C \uC2A4\uD0C0\uC77C\uC5D0 \uCD94\uAC00"));
4042
+ console.log(chalk18.gray(' 2. import { initTheme, toggleTheme } from "./lib/theme-toggle"'));
4043
+ console.log(chalk18.gray(" 3. \uC571 \uC9C4\uC785\uC810\uC5D0\uC11C initTheme() \uD638\uCD9C"));
4044
+ console.log(chalk18.gray(" 4. \uD1A0\uAE00 \uBC84\uD2BC\uC5D0\uC11C toggleTheme() \uD638\uCD9C"));
4062
4045
  printNextStep({
4063
4046
  message: "\uD14C\uB9C8 \uC124\uC815 \uC644\uB8CC!",
4064
4047
  command: "vhk ref list",
@@ -4068,7 +4051,7 @@ async function theme() {
4068
4051
 
4069
4052
  // src/commands/ref.ts
4070
4053
  import { existsSync as existsSync7, mkdirSync as mkdirSync6, writeFileSync as writeFileSync6 } from "fs";
4071
- import chalk20 from "chalk";
4054
+ import chalk19 from "chalk";
4072
4055
  var REFS_PATH = ".vhk/refs.json";
4073
4056
  function loadRefs() {
4074
4057
  if (!existsSync7(REFS_PATH)) return [];
@@ -4084,24 +4067,24 @@ function saveRefs(refs) {
4084
4067
  writeFileSync6(REFS_PATH, JSON.stringify(refs, null, 2) + "\n", "utf-8");
4085
4068
  }
4086
4069
  async function refAdd(url, memo = "") {
4087
- console.log(chalk20.bold("\n\u{1F517} " + t("ref.addTitle")));
4088
- console.log(chalk20.gray("\u2500".repeat(40)));
4070
+ console.log(chalk19.bold("\n\u{1F517} " + t("ref.addTitle")));
4071
+ console.log(chalk19.gray("\u2500".repeat(40)));
4089
4072
  if (!url) {
4090
- console.log(chalk20.red("\u274C URL\uC744 \uC785\uB825\uD574\uC8FC\uC138\uC694."));
4091
- console.log(chalk20.gray(' \uC608: vhk ref add https://example.com --memo "\uCC38\uACE0 \uC0AC\uC774\uD2B8"'));
4073
+ console.log(chalk19.red("\u274C URL\uC744 \uC785\uB825\uD574\uC8FC\uC138\uC694."));
4074
+ console.log(chalk19.gray(' \uC608: vhk ref add https://example.com --memo "\uCC38\uACE0 \uC0AC\uC774\uD2B8"'));
4092
4075
  return;
4093
4076
  }
4094
4077
  const refs = loadRefs();
4095
4078
  if (refs.some((r) => r.url === url)) {
4096
- console.log(chalk20.yellow("\u26A0\uFE0F \uC774\uBBF8 \uC800\uC7A5\uB41C URL\uC785\uB2C8\uB2E4."));
4079
+ console.log(chalk19.yellow("\u26A0\uFE0F \uC774\uBBF8 \uC800\uC7A5\uB41C URL\uC785\uB2C8\uB2E4."));
4097
4080
  return;
4098
4081
  }
4099
4082
  refs.push({ url, memo, addedAt: (/* @__PURE__ */ new Date()).toISOString() });
4100
4083
  saveRefs(refs);
4101
- console.log(chalk20.green(`
4084
+ console.log(chalk19.green(`
4102
4085
  \u2705 \uB808\uD37C\uB7F0\uC2A4 \uCD94\uAC00\uB428 (#${refs.length})`));
4103
- console.log(chalk20.cyan(` ${url}`));
4104
- if (memo) console.log(chalk20.gray(` \u{1F4DD} ${memo}`));
4086
+ console.log(chalk19.cyan(` ${url}`));
4087
+ if (memo) console.log(chalk19.gray(` \u{1F4DD} ${memo}`));
4105
4088
  printNextStep({
4106
4089
  message: "\uB808\uD37C\uB7F0\uC2A4 \uC800\uC7A5 \uC644\uB8CC!",
4107
4090
  command: "vhk ref list",
@@ -4109,22 +4092,22 @@ async function refAdd(url, memo = "") {
4109
4092
  });
4110
4093
  }
4111
4094
  async function refList() {
4112
- console.log(chalk20.bold("\n\u{1F4DA} " + t("ref.listTitle")));
4113
- console.log(chalk20.gray("\u2500".repeat(40)));
4095
+ console.log(chalk19.bold("\n\u{1F4DA} " + t("ref.listTitle")));
4096
+ console.log(chalk19.gray("\u2500".repeat(40)));
4114
4097
  const refs = loadRefs();
4115
4098
  if (refs.length === 0) {
4116
- console.log(chalk20.yellow("\n\u{1F4ED} \uC800\uC7A5\uB41C \uB808\uD37C\uB7F0\uC2A4\uAC00 \uC5C6\uC2B5\uB2C8\uB2E4."));
4117
- console.log(chalk20.gray(' vhk ref add <url> --memo "\uBA54\uBAA8"\uB85C \uCD94\uAC00\uD558\uC138\uC694.'));
4099
+ console.log(chalk19.yellow("\n\u{1F4ED} \uC800\uC7A5\uB41C \uB808\uD37C\uB7F0\uC2A4\uAC00 \uC5C6\uC2B5\uB2C8\uB2E4."));
4100
+ console.log(chalk19.gray(' vhk ref add <url> --memo "\uBA54\uBAA8"\uB85C \uCD94\uAC00\uD558\uC138\uC694.'));
4118
4101
  return;
4119
4102
  }
4120
- console.log(chalk20.cyan(`
4103
+ console.log(chalk19.cyan(`
4121
4104
  \uCD1D ${refs.length}\uAC1C\uC758 \uB808\uD37C\uB7F0\uC2A4:
4122
4105
  `));
4123
4106
  refs.forEach((ref, index) => {
4124
4107
  const date = new Date(ref.addedAt).toLocaleDateString("ko-KR");
4125
- console.log(chalk20.white(` [${index + 1}] ${ref.url}`));
4126
- if (ref.memo) console.log(chalk20.gray(` \u{1F4DD} ${ref.memo}`));
4127
- console.log(chalk20.gray(` \u{1F4C5} ${date}`));
4108
+ console.log(chalk19.white(` [${index + 1}] ${ref.url}`));
4109
+ if (ref.memo) console.log(chalk19.gray(` \u{1F4DD} ${ref.memo}`));
4110
+ console.log(chalk19.gray(` \u{1F4C5} ${date}`));
4128
4111
  console.log("");
4129
4112
  });
4130
4113
  }
@@ -4132,7 +4115,7 @@ async function refOpen(indexStr) {
4132
4115
  const refs = loadRefs();
4133
4116
  const idx = parseInt(indexStr, 10) - 1;
4134
4117
  if (Number.isNaN(idx) || idx < 0 || idx >= refs.length) {
4135
- console.log(chalk20.red(`\u274C \uC720\uD6A8\uD558\uC9C0 \uC54A\uC740 \uBC88\uD638\uC785\uB2C8\uB2E4. (1~${refs.length || 0})`));
4118
+ console.log(chalk19.red(`\u274C \uC720\uD6A8\uD558\uC9C0 \uC54A\uC740 \uBC88\uD638\uC785\uB2C8\uB2E4. (1~${refs.length || 0})`));
4136
4119
  return;
4137
4120
  }
4138
4121
  const ref = refs[idx];
@@ -4140,14 +4123,14 @@ async function refOpen(indexStr) {
4140
4123
  try {
4141
4124
  parsed = new URL(ref.url);
4142
4125
  } catch {
4143
- console.log(chalk20.red(`\u274C \uC720\uD6A8\uD558\uC9C0 \uC54A\uC740 URL: ${ref.url}`));
4126
+ console.log(chalk19.red(`\u274C \uC720\uD6A8\uD558\uC9C0 \uC54A\uC740 URL: ${ref.url}`));
4144
4127
  return;
4145
4128
  }
4146
4129
  if (parsed.protocol !== "http:" && parsed.protocol !== "https:") {
4147
- console.log(chalk20.red(`\u274C http(s) URL\uB9CC \uC5F4 \uC218 \uC788\uC2B5\uB2C8\uB2E4 (${parsed.protocol})`));
4130
+ console.log(chalk19.red(`\u274C http(s) URL\uB9CC \uC5F4 \uC218 \uC788\uC2B5\uB2C8\uB2E4 (${parsed.protocol})`));
4148
4131
  return;
4149
4132
  }
4150
- console.log(chalk20.cyan(`
4133
+ console.log(chalk19.cyan(`
4151
4134
  \u{1F310} \uC5F4\uAE30: ${ref.url}`));
4152
4135
  let result;
4153
4136
  if (process.platform === "darwin") {
@@ -4158,15 +4141,15 @@ async function refOpen(indexStr) {
4158
4141
  result = safeExecFile("xdg-open", [ref.url]);
4159
4142
  }
4160
4143
  if (result.ok) {
4161
- console.log(chalk20.green("\u2705 \uBE0C\uB77C\uC6B0\uC800\uC5D0\uC11C \uC5F4\uC5C8\uC2B5\uB2C8\uB2E4."));
4144
+ console.log(chalk19.green("\u2705 \uBE0C\uB77C\uC6B0\uC800\uC5D0\uC11C \uC5F4\uC5C8\uC2B5\uB2C8\uB2E4."));
4162
4145
  } else {
4163
- console.log(chalk20.yellow("\u26A0\uFE0F \uBE0C\uB77C\uC6B0\uC800\uB97C \uC5F4 \uC218 \uC5C6\uC2B5\uB2C8\uB2E4. URL\uC744 \uC9C1\uC811 \uBC29\uBB38\uD574\uC8FC\uC138\uC694."));
4146
+ console.log(chalk19.yellow("\u26A0\uFE0F \uBE0C\uB77C\uC6B0\uC800\uB97C \uC5F4 \uC218 \uC5C6\uC2B5\uB2C8\uB2E4. URL\uC744 \uC9C1\uC811 \uBC29\uBB38\uD574\uC8FC\uC138\uC694."));
4164
4147
  }
4165
4148
  }
4166
4149
 
4167
4150
  // src/commands/harness.ts
4168
4151
  import { existsSync as existsSync8 } from "fs";
4169
- import chalk21 from "chalk";
4152
+ import chalk20 from "chalk";
4170
4153
  import ora2 from "ora";
4171
4154
  function detectPM() {
4172
4155
  if (existsSync8("pnpm-lock.yaml")) return "pnpm";
@@ -4208,15 +4191,15 @@ function detectChecks() {
4208
4191
  }
4209
4192
  async function harness() {
4210
4193
  if (!ensureNotHardStopped("harness")) return;
4211
- console.log(chalk21.bold("\n\u{1F527} " + t("harness.title")));
4212
- console.log(chalk21.gray("\u2500".repeat(40)));
4194
+ console.log(chalk20.bold("\n\u{1F527} " + t("harness.title")));
4195
+ console.log(chalk20.gray("\u2500".repeat(40)));
4213
4196
  const checks = detectChecks();
4214
4197
  if (checks.length === 0) {
4215
- console.log(chalk21.yellow("\n\u26A0\uFE0F \uC2E4\uD589\uD560 \uC218 \uC788\uB294 \uC2A4\uD06C\uB9BD\uD2B8\uAC00 \uC5C6\uC2B5\uB2C8\uB2E4."));
4216
- console.log(chalk21.gray(" package.json\uC5D0 lint, test, build \uC2A4\uD06C\uB9BD\uD2B8\uB97C \uCD94\uAC00\uD574\uC8FC\uC138\uC694."));
4198
+ console.log(chalk20.yellow("\n\u26A0\uFE0F \uC2E4\uD589\uD560 \uC218 \uC788\uB294 \uC2A4\uD06C\uB9BD\uD2B8\uAC00 \uC5C6\uC2B5\uB2C8\uB2E4."));
4199
+ console.log(chalk20.gray(" package.json\uC5D0 lint, test, build \uC2A4\uD06C\uB9BD\uD2B8\uB97C \uCD94\uAC00\uD574\uC8FC\uC138\uC694."));
4217
4200
  return;
4218
4201
  }
4219
- console.log(chalk21.cyan(`
4202
+ console.log(chalk20.cyan(`
4220
4203
  \u{1F3C3} ${checks.length}\uAC1C \uC810\uAC80 \uC2DC\uC791:
4221
4204
  `));
4222
4205
  const results = [];
@@ -4228,10 +4211,10 @@ async function harness() {
4228
4211
  const duration = Date.now() - start2;
4229
4212
  const sec = (duration / 1e3).toFixed(1);
4230
4213
  if (result.ok) {
4231
- spinner.succeed(`${check2.name} ${chalk21.gray(`(${sec}s)`)}`);
4214
+ spinner.succeed(`${check2.name} ${chalk20.gray(`(${sec}s)`)}`);
4232
4215
  results.push({ name: check2.name, command: display, passed: true, duration });
4233
4216
  } else {
4234
- spinner.fail(`${check2.name} ${chalk21.gray(`(${sec}s)`)}`);
4217
+ spinner.fail(`${check2.name} ${chalk20.gray(`(${sec}s)`)}`);
4235
4218
  results.push({
4236
4219
  name: check2.name,
4237
4220
  command: display,
@@ -4241,22 +4224,22 @@ async function harness() {
4241
4224
  });
4242
4225
  }
4243
4226
  }
4244
- console.log(chalk21.bold("\n\u{1F4CA} \uD1B5\uD569 \uB9AC\uD3EC\uD2B8:"));
4245
- console.log(chalk21.gray("\u2500".repeat(40)));
4227
+ console.log(chalk20.bold("\n\u{1F4CA} \uD1B5\uD569 \uB9AC\uD3EC\uD2B8:"));
4228
+ console.log(chalk20.gray("\u2500".repeat(40)));
4246
4229
  for (const r of results) {
4247
- const icon = r.passed ? chalk21.green("\u2705") : chalk21.red("\u274C");
4230
+ const icon = r.passed ? chalk20.green("\u2705") : chalk20.red("\u274C");
4248
4231
  const sec = (r.duration / 1e3).toFixed(1);
4249
- console.log(` ${icon} ${r.name.padEnd(15)} ${chalk21.gray(`${sec}s`)}`);
4232
+ console.log(` ${icon} ${r.name.padEnd(15)} ${chalk20.gray(`${sec}s`)}`);
4250
4233
  }
4251
4234
  const passed = results.filter((r) => r.passed).length;
4252
4235
  const all = passed === results.length;
4253
- console.log(chalk21.gray("\u2500".repeat(40)));
4236
+ console.log(chalk20.gray("\u2500".repeat(40)));
4254
4237
  if (all) {
4255
- console.log(chalk21.green.bold(`
4238
+ console.log(chalk20.green.bold(`
4256
4239
  \u{1F389} \uC804\uCCB4 \uD1B5\uACFC! (${passed}/${results.length})`));
4257
4240
  } else {
4258
4241
  console.log(
4259
- chalk21.red.bold(`
4242
+ chalk20.red.bold(`
4260
4243
  \u26A0\uFE0F ${results.length - passed}\uAC1C \uC2E4\uD328 (${passed}/${results.length} \uD1B5\uACFC)`)
4261
4244
  );
4262
4245
  process.exitCode = 1;
@@ -4270,7 +4253,7 @@ async function harness() {
4270
4253
 
4271
4254
  // src/commands/migrate.ts
4272
4255
  import { existsSync as existsSync9, unlinkSync, rmSync as rmSync2 } from "fs";
4273
- import chalk22 from "chalk";
4256
+ import chalk21 from "chalk";
4274
4257
  import inquirer10 from "inquirer";
4275
4258
  import ora3 from "ora";
4276
4259
  var LOCK_FILES = {
@@ -4288,10 +4271,10 @@ function isCLIAvailable(pm) {
4288
4271
  return safeExecFile(pm, ["--version"]).ok;
4289
4272
  }
4290
4273
  async function migrate(target) {
4291
- console.log(chalk22.bold("\n\u{1F504} " + t("migrate.title")));
4292
- console.log(chalk22.gray("\u2500".repeat(40)));
4274
+ console.log(chalk21.bold("\n\u{1F504} " + t("migrate.title")));
4275
+ console.log(chalk21.gray("\u2500".repeat(40)));
4293
4276
  const current = detectCurrentPM();
4294
- console.log(chalk22.cyan(`
4277
+ console.log(chalk21.cyan(`
4295
4278
  \uD604\uC7AC \uD328\uD0A4\uC9C0 \uB9E4\uB2C8\uC800: ${current ?? "\uAC10\uC9C0 \uBD88\uAC00"}`));
4296
4279
  let targetPM;
4297
4280
  if (target && ["npm", "yarn", "pnpm"].includes(target)) {
@@ -4309,14 +4292,14 @@ async function migrate(target) {
4309
4292
  targetPM = selected;
4310
4293
  }
4311
4294
  if (targetPM === current) {
4312
- console.log(chalk22.yellow(`
4295
+ console.log(chalk21.yellow(`
4313
4296
  \u26A0\uFE0F \uC774\uBBF8 ${targetPM}\uC744 \uC0AC\uC6A9 \uC911\uC785\uB2C8\uB2E4.`));
4314
4297
  return;
4315
4298
  }
4316
4299
  if (!isCLIAvailable(targetPM)) {
4317
- console.log(chalk22.red(`
4300
+ console.log(chalk21.red(`
4318
4301
  \u274C ${targetPM}\uC774 \uC124\uCE58\uB418\uC5B4 \uC788\uC9C0 \uC54A\uC2B5\uB2C8\uB2E4.`));
4319
- console.log(chalk22.yellow(` npm i -g ${targetPM}`));
4302
+ console.log(chalk21.yellow(` npm i -g ${targetPM}`));
4320
4303
  return;
4321
4304
  }
4322
4305
  const { confirm } = await inquirer10.prompt([
@@ -4328,7 +4311,7 @@ async function migrate(target) {
4328
4311
  }
4329
4312
  ]);
4330
4313
  if (!confirm) {
4331
- console.log(chalk22.gray("\uCDE8\uC18C\uB428"));
4314
+ console.log(chalk21.gray("\uCDE8\uC18C\uB428"));
4332
4315
  return;
4333
4316
  }
4334
4317
  const cleanup = ora3("\uAE30\uC874 lock \uD30C\uC77C \uC815\uB9AC \uC911...").start();
@@ -4348,10 +4331,10 @@ async function migrate(target) {
4348
4331
  install.succeed(`${targetPM} install \uC644\uB8CC!`);
4349
4332
  } else {
4350
4333
  install.fail(`${targetPM} install \uC2E4\uD328`);
4351
- console.log(chalk22.red(installResult.err.slice(0, 300)));
4334
+ console.log(chalk21.red(installResult.err.slice(0, 300)));
4352
4335
  return;
4353
4336
  }
4354
- console.log(chalk22.green.bold(`
4337
+ console.log(chalk21.green.bold(`
4355
4338
  \u{1F389} ${current ?? "\uC774\uC804"} \u2192 ${targetPM} \uC804\uD658 \uC644\uB8CC!`));
4356
4339
  printNextStep({
4357
4340
  message: "\uD328\uD0A4\uC9C0 \uB9E4\uB2C8\uC800 \uC804\uD658 \uC644\uB8CC!",
@@ -4364,7 +4347,7 @@ async function migrate(target) {
4364
4347
  import { existsSync as existsSync10 } from "fs";
4365
4348
  import { dirname as dirname2, join as join6 } from "path";
4366
4349
  import { fileURLToPath as fileURLToPath3 } from "url";
4367
- import chalk23 from "chalk";
4350
+ import chalk22 from "chalk";
4368
4351
  import ora4 from "ora";
4369
4352
  var PACKAGE = "@byh3071/vhk";
4370
4353
  function getCurrentVersion() {
@@ -4394,32 +4377,32 @@ function isUpToDate(current, latest) {
4394
4377
  return cc >= lc;
4395
4378
  }
4396
4379
  async function update() {
4397
- console.log(chalk23.bold("\n\u2B06\uFE0F " + t("update.title")));
4398
- console.log(chalk23.gray("\u2500".repeat(40)));
4380
+ console.log(chalk22.bold("\n\u2B06\uFE0F " + t("update.title")));
4381
+ console.log(chalk22.gray("\u2500".repeat(40)));
4399
4382
  const current = getCurrentVersion();
4400
- console.log(chalk23.cyan(`
4383
+ console.log(chalk22.cyan(`
4401
4384
  \u{1F4CC} \uD604\uC7AC \uBC84\uC804: v${current}`));
4402
4385
  const spinner = ora4("\uCD5C\uC2E0 \uBC84\uC804 \uD655\uC778 \uC911...").start();
4403
4386
  const latest = getLatestVersion();
4404
4387
  if (!latest) {
4405
4388
  spinner.fail("\uCD5C\uC2E0 \uBC84\uC804\uC744 \uD655\uC778\uD560 \uC218 \uC5C6\uC2B5\uB2C8\uB2E4.");
4406
- console.log(chalk23.yellow(" \uB124\uD2B8\uC6CC\uD06C\uB97C \uD655\uC778\uD558\uAC70\uB098 \uC218\uB3D9\uC73C\uB85C \uC5C5\uB370\uC774\uD2B8\uD558\uC138\uC694:"));
4407
- console.log(chalk23.gray(` npm update -g ${PACKAGE}`));
4389
+ console.log(chalk22.yellow(" \uB124\uD2B8\uC6CC\uD06C\uB97C \uD655\uC778\uD558\uAC70\uB098 \uC218\uB3D9\uC73C\uB85C \uC5C5\uB370\uC774\uD2B8\uD558\uC138\uC694:"));
4390
+ console.log(chalk22.gray(` npm update -g ${PACKAGE}`));
4408
4391
  return;
4409
4392
  }
4410
4393
  spinner.stop();
4411
- console.log(chalk23.cyan(`\u{1F195} \uCD5C\uC2E0 \uBC84\uC804: v${latest}`));
4394
+ console.log(chalk22.cyan(`\u{1F195} \uCD5C\uC2E0 \uBC84\uC804: v${latest}`));
4412
4395
  if (isUpToDate(current, latest)) {
4413
- console.log(chalk23.green("\n\u2705 \uC774\uBBF8 \uCD5C\uC2E0 \uBC84\uC804\uC785\uB2C8\uB2E4!"));
4396
+ console.log(chalk22.green("\n\u2705 \uC774\uBBF8 \uCD5C\uC2E0 \uBC84\uC804\uC785\uB2C8\uB2E4!"));
4414
4397
  return;
4415
4398
  }
4416
4399
  const updateSpinner = ora4(`v${latest}\uC73C\uB85C \uC5C5\uB370\uC774\uD2B8 \uC911...`).start();
4417
4400
  const upd = safeExecFile("npm", ["update", "-g", PACKAGE]);
4418
4401
  if (upd.ok) {
4419
4402
  updateSpinner.succeed(`v${latest}\uC73C\uB85C \uC5C5\uB370\uC774\uD2B8 \uC644\uB8CC!`);
4420
- console.log(chalk23.green.bold(`
4403
+ console.log(chalk22.green.bold(`
4421
4404
  \u{1F389} VHK CLI v${latest} \uC5C5\uB370\uC774\uD2B8 \uC644\uB8CC!`));
4422
- console.log(chalk23.gray(" \uBCC0\uACBD \uC0AC\uD56D\uC740 GitHub Releases\uB97C \uD655\uC778\uD558\uC138\uC694."));
4405
+ console.log(chalk22.gray(" \uBCC0\uACBD \uC0AC\uD56D\uC740 GitHub Releases\uB97C \uD655\uC778\uD558\uC138\uC694."));
4423
4406
  printNextStep({
4424
4407
  message: t("update.nextOkMessage"),
4425
4408
  command: "vhk --version",
@@ -4427,9 +4410,9 @@ async function update() {
4427
4410
  });
4428
4411
  } else {
4429
4412
  updateSpinner.fail("\uC5C5\uB370\uC774\uD2B8 \uC2E4\uD328");
4430
- console.log(chalk23.red(upd.err.slice(0, 300)));
4431
- console.log(chalk23.yellow("\n\uC218\uB3D9\uC73C\uB85C \uC5C5\uB370\uC774\uD2B8\uD558\uC138\uC694:"));
4432
- console.log(chalk23.gray(` npm update -g ${PACKAGE}`));
4413
+ console.log(chalk22.red(upd.err.slice(0, 300)));
4414
+ console.log(chalk22.yellow("\n\uC218\uB3D9\uC73C\uB85C \uC5C5\uB370\uC774\uD2B8\uD558\uC138\uC694:"));
4415
+ console.log(chalk22.gray(` npm update -g ${PACKAGE}`));
4433
4416
  printNextStep({
4434
4417
  message: t("update.nextFailMessage"),
4435
4418
  command: "vhk doctor",
@@ -4448,7 +4431,7 @@ import {
4448
4431
  writeFileSync as writeFileSync7
4449
4432
  } from "fs";
4450
4433
  import { join as join7 } from "path";
4451
- import chalk24 from "chalk";
4434
+ import chalk23 from "chalk";
4452
4435
  var CONTEXT_PATH = ".vhk/context.md";
4453
4436
  var IGNORE_DIRS = /* @__PURE__ */ new Set([
4454
4437
  "node_modules",
@@ -4549,8 +4532,8 @@ function getVhkCommands() {
4549
4532
  }
4550
4533
  async function context(opts = {}) {
4551
4534
  const compact = opts.compact === true;
4552
- console.log(chalk24.bold("\n\u{1F9E0} " + t("context.title")));
4553
- console.log(chalk24.gray("\u2500".repeat(40)));
4535
+ console.log(chalk23.bold("\n\u{1F9E0} " + t("context.title")));
4536
+ console.log(chalk23.gray("\u2500".repeat(40)));
4554
4537
  const stack = extractTechStack();
4555
4538
  const tree = buildTree(".", "", compact ? 2 : 3).join("\n");
4556
4539
  const commands = getVhkCommands();
@@ -4665,10 +4648,10 @@ async function context(opts = {}) {
4665
4648
  lines.push("");
4666
4649
  mkdirSync7(".vhk", { recursive: true });
4667
4650
  writeFileSync7(CONTEXT_PATH, lines.join("\n"), "utf-8");
4668
- console.log(chalk24.green(`
4651
+ console.log(chalk23.green(`
4669
4652
  \u2705 ${CONTEXT_PATH} \uC0DD\uC131 \uC644\uB8CC!`));
4670
- console.log(chalk24.gray(` \uAE30\uC220 \uC2A4\uD0DD ${Object.keys(stack).length}\uAC1C \uAC10\uC9C0`));
4671
- console.log(chalk24.gray(" AI \uC5B4\uC2DC\uC2A4\uD134\uD2B8\uC5D0\uAC8C \uC774 \uD30C\uC77C\uC744 \uCC38\uC870\uD558\uAC8C \uD558\uC138\uC694."));
4653
+ console.log(chalk23.gray(` \uAE30\uC220 \uC2A4\uD0DD ${Object.keys(stack).length}\uAC1C \uAC10\uC9C0`));
4654
+ console.log(chalk23.gray(" AI \uC5B4\uC2DC\uC2A4\uD134\uD2B8\uC5D0\uAC8C \uC774 \uD30C\uC77C\uC744 \uCC38\uC870\uD558\uAC8C \uD558\uC138\uC694."));
4672
4655
  printNextStep({
4673
4656
  message: "\uCEE8\uD14D\uC2A4\uD2B8 \uD30C\uC77C \uC0DD\uC131 \uC644\uB8CC!",
4674
4657
  command: "vhk context-show",
@@ -4676,11 +4659,11 @@ async function context(opts = {}) {
4676
4659
  });
4677
4660
  }
4678
4661
  async function contextShow() {
4679
- console.log(chalk24.bold("\n\u{1F4C4} " + t("context.showTitle")));
4680
- console.log(chalk24.gray("\u2500".repeat(40)));
4662
+ console.log(chalk23.bold("\n\u{1F4C4} " + t("context.showTitle")));
4663
+ console.log(chalk23.gray("\u2500".repeat(40)));
4681
4664
  if (!existsSync11(CONTEXT_PATH)) {
4682
- console.log(chalk24.yellow("\n\u26A0\uFE0F \uCEE8\uD14D\uC2A4\uD2B8 \uD30C\uC77C\uC774 \uC5C6\uC2B5\uB2C8\uB2E4."));
4683
- console.log(chalk24.gray(" vhk context\uB97C \uBA3C\uC800 \uC2E4\uD589\uD558\uC138\uC694."));
4665
+ console.log(chalk23.yellow("\n\u26A0\uFE0F \uCEE8\uD14D\uC2A4\uD2B8 \uD30C\uC77C\uC774 \uC5C6\uC2B5\uB2C8\uB2E4."));
4666
+ console.log(chalk23.gray(" vhk context\uB97C \uBA3C\uC800 \uC2E4\uD589\uD558\uC138\uC694."));
4684
4667
  return;
4685
4668
  }
4686
4669
  const content = readFileSync4(CONTEXT_PATH, "utf-8");
@@ -4689,7 +4672,7 @@ async function contextShow() {
4689
4672
 
4690
4673
  // src/commands/memory.ts
4691
4674
  import { existsSync as existsSync12, mkdirSync as mkdirSync8, writeFileSync as writeFileSync8 } from "fs";
4692
- import chalk25 from "chalk";
4675
+ import chalk24 from "chalk";
4693
4676
  var MEMORY_PATH = ".vhk/memory.json";
4694
4677
  function loadMemories() {
4695
4678
  if (!existsSync12(MEMORY_PATH)) return [];
@@ -4705,11 +4688,11 @@ function saveMemories(memories) {
4705
4688
  writeFileSync8(MEMORY_PATH, JSON.stringify(memories, null, 2) + "\n", "utf-8");
4706
4689
  }
4707
4690
  async function memoryAdd(content, tags) {
4708
- console.log(chalk25.bold("\n\u{1F9E0} " + t("memory.addTitle")));
4709
- console.log(chalk25.gray("\u2500".repeat(40)));
4691
+ console.log(chalk24.bold("\n\u{1F9E0} " + t("memory.addTitle")));
4692
+ console.log(chalk24.gray("\u2500".repeat(40)));
4710
4693
  if (!content) {
4711
- console.log(chalk25.red("\u274C \uAE30\uC5B5\uD560 \uB0B4\uC6A9\uC744 \uC785\uB825\uD574\uC8FC\uC138\uC694."));
4712
- console.log(chalk25.gray(' \uC608: vhk memory add "API\uB294 tRPC \uC0AC\uC6A9\uD558\uAE30\uB85C \uACB0\uC815"'));
4694
+ console.log(chalk24.red("\u274C \uAE30\uC5B5\uD560 \uB0B4\uC6A9\uC744 \uC785\uB825\uD574\uC8FC\uC138\uC694."));
4695
+ console.log(chalk24.gray(' \uC608: vhk memory add "API\uB294 tRPC \uC0AC\uC6A9\uD558\uAE30\uB85C \uACB0\uC815"'));
4713
4696
  process.exitCode = 1;
4714
4697
  return;
4715
4698
  }
@@ -4720,9 +4703,9 @@ async function memoryAdd(content, tags) {
4720
4703
  tags: tags && tags.length > 0 ? tags : []
4721
4704
  });
4722
4705
  saveMemories(memories);
4723
- console.log(chalk25.green(`
4706
+ console.log(chalk24.green(`
4724
4707
  \u2705 \uAE30\uC5B5 \uC800\uC7A5\uB428 (#${memories.length})`));
4725
- console.log(chalk25.cyan(` \u{1F4DD} ${content}`));
4708
+ console.log(chalk24.cyan(` \u{1F4DD} ${content}`));
4726
4709
  printNextStep({
4727
4710
  message: "\uAE30\uC5B5 \uC800\uC7A5 \uC644\uB8CC!",
4728
4711
  command: "vhk memory list",
@@ -4730,24 +4713,24 @@ async function memoryAdd(content, tags) {
4730
4713
  });
4731
4714
  }
4732
4715
  async function memoryList() {
4733
- console.log(chalk25.bold("\n\u{1F9E0} " + t("memory.listTitle")));
4734
- console.log(chalk25.gray("\u2500".repeat(40)));
4716
+ console.log(chalk24.bold("\n\u{1F9E0} " + t("memory.listTitle")));
4717
+ console.log(chalk24.gray("\u2500".repeat(40)));
4735
4718
  const memories = loadMemories();
4736
4719
  if (memories.length === 0) {
4737
- console.log(chalk25.yellow("\n\u{1F4ED} \uC800\uC7A5\uB41C \uAE30\uC5B5\uC774 \uC5C6\uC2B5\uB2C8\uB2E4."));
4738
- console.log(chalk25.gray(' vhk memory add "\uB0B4\uC6A9"\uC73C\uB85C \uCD94\uAC00\uD558\uC138\uC694.'));
4720
+ console.log(chalk24.yellow("\n\u{1F4ED} \uC800\uC7A5\uB41C \uAE30\uC5B5\uC774 \uC5C6\uC2B5\uB2C8\uB2E4."));
4721
+ console.log(chalk24.gray(' vhk memory add "\uB0B4\uC6A9"\uC73C\uB85C \uCD94\uAC00\uD558\uC138\uC694.'));
4739
4722
  return;
4740
4723
  }
4741
- console.log(chalk25.cyan(`
4724
+ console.log(chalk24.cyan(`
4742
4725
  \uCD1D ${memories.length}\uAC1C\uC758 \uAE30\uC5B5:
4743
4726
  `));
4744
4727
  memories.forEach((m, index) => {
4745
4728
  const date = new Date(m.addedAt).toLocaleDateString("ko-KR");
4746
- console.log(chalk25.white(` [${index + 1}] ${m.content}`));
4729
+ console.log(chalk24.white(` [${index + 1}] ${m.content}`));
4747
4730
  if (m.tags && m.tags.length > 0) {
4748
- console.log(chalk25.blue(` \u{1F3F7}\uFE0F ${m.tags.join(", ")}`));
4731
+ console.log(chalk24.blue(` \u{1F3F7}\uFE0F ${m.tags.join(", ")}`));
4749
4732
  }
4750
- console.log(chalk25.gray(` \u{1F4C5} ${date}`));
4733
+ console.log(chalk24.gray(` \u{1F4C5} ${date}`));
4751
4734
  console.log("");
4752
4735
  });
4753
4736
  }
@@ -4755,18 +4738,18 @@ async function memoryRemove(indexStr) {
4755
4738
  const memories = loadMemories();
4756
4739
  const idx = parseInt(indexStr, 10) - 1;
4757
4740
  if (Number.isNaN(idx) || idx < 0 || idx >= memories.length) {
4758
- console.log(chalk25.red(`\u274C \uC720\uD6A8\uD558\uC9C0 \uC54A\uC740 \uBC88\uD638\uC785\uB2C8\uB2E4. (1~${memories.length || 0})`));
4741
+ console.log(chalk24.red(`\u274C \uC720\uD6A8\uD558\uC9C0 \uC54A\uC740 \uBC88\uD638\uC785\uB2C8\uB2E4. (1~${memories.length || 0})`));
4759
4742
  return;
4760
4743
  }
4761
4744
  const removed = memories.splice(idx, 1)[0];
4762
4745
  saveMemories(memories);
4763
- console.log(chalk25.green("\n\u2705 \uAE30\uC5B5 \uC0AD\uC81C\uB428:"));
4764
- console.log(chalk25.gray(` ${removed.content}`));
4746
+ console.log(chalk24.green("\n\u2705 \uAE30\uC5B5 \uC0AD\uC81C\uB428:"));
4747
+ console.log(chalk24.gray(` ${removed.content}`));
4765
4748
  }
4766
4749
 
4767
4750
  // src/commands/brief.ts
4768
4751
  import { existsSync as existsSync13, mkdirSync as mkdirSync9, writeFileSync as writeFileSync9, readFileSync as readFileSync5 } from "fs";
4769
- import chalk26 from "chalk";
4752
+ import chalk25 from "chalk";
4770
4753
  var BRIEF_PATH = ".vhk/brief.md";
4771
4754
  function readProjectIdentity() {
4772
4755
  const out = {};
@@ -4791,8 +4774,8 @@ function git2(args) {
4791
4774
  return result.ok ? result.out : "";
4792
4775
  }
4793
4776
  async function brief() {
4794
- console.log(chalk26.bold("\n\u{1F4CB} " + t("brief.title")));
4795
- console.log(chalk26.gray("\u2500".repeat(40)));
4777
+ console.log(chalk25.bold("\n\u{1F4CB} " + t("brief.title")));
4778
+ console.log(chalk25.gray("\u2500".repeat(40)));
4796
4779
  const lines = [];
4797
4780
  lines.push("# \uD504\uB85C\uC81D\uD2B8 \uBE0C\uB9AC\uD551");
4798
4781
  lines.push("");
@@ -4877,7 +4860,7 @@ async function brief() {
4877
4860
  mkdirSync9(".vhk", { recursive: true });
4878
4861
  writeFileSync9(BRIEF_PATH, lines.join("\n"), "utf-8");
4879
4862
  console.log("\n" + lines.join("\n"));
4880
- console.log(chalk26.green(`
4863
+ console.log(chalk25.green(`
4881
4864
  \u2705 ${BRIEF_PATH} \uC800\uC7A5 \uC644\uB8CC`));
4882
4865
  printNextStep({
4883
4866
  message: "\uBE0C\uB9AC\uD551 \uC0DD\uC131 \uC644\uB8CC!",
@@ -4887,7 +4870,7 @@ async function brief() {
4887
4870
  }
4888
4871
 
4889
4872
  // src/commands/start.ts
4890
- import chalk27 from "chalk";
4873
+ import chalk26 from "chalk";
4891
4874
  import inquirer11 from "inquirer";
4892
4875
  import { simpleGit as simpleGit2 } from "simple-git";
4893
4876
  import { existsSync as existsSync14 } from "fs";
@@ -4929,21 +4912,21 @@ async function runStep(label, fn) {
4929
4912
  }
4930
4913
  }
4931
4914
  async function start(options = {}) {
4932
- console.log(chalk27.bold(`
4915
+ console.log(chalk26.bold(`
4933
4916
  ${ko.start.title}
4934
4917
  `));
4935
- console.log(chalk27.dim(ko.start.intro));
4936
- console.log(chalk27.dim(` ${ko.start.step1}`));
4937
- console.log(chalk27.dim(` ${ko.start.step2}`));
4938
- console.log(chalk27.dim(` ${ko.start.step3}`));
4939
- console.log(chalk27.dim(` ${ko.start.step4}`));
4918
+ console.log(chalk26.dim(ko.start.intro));
4919
+ console.log(chalk26.dim(` ${ko.start.step1}`));
4920
+ console.log(chalk26.dim(` ${ko.start.step2}`));
4921
+ console.log(chalk26.dim(` ${ko.start.step3}`));
4922
+ console.log(chalk26.dim(` ${ko.start.step4}`));
4940
4923
  console.log();
4941
4924
  const cwd = process.cwd();
4942
4925
  const footprint = detectExistingFootprint(cwd);
4943
4926
  if (footprint.length > 0 && !options.yes) {
4944
- console.log(chalk27.yellow("\u26A0\uFE0F \uC774\uBBF8 VHK \uC124\uCE58 \uD754\uC801\uC774 \uAC10\uC9C0\uB410\uC5B4\uC694:"));
4945
- for (const f of footprint) console.log(chalk27.dim(` - ${f}`));
4946
- console.log(chalk27.dim(" \uACC4\uC18D \uC9C4\uD589\uD558\uBA74 \uC77C\uBD80 \uD30C\uC77C(`.cursor/mcp.json`, `.vhk/context.md`)\uC740 \uAC31\uC2E0\xB7\uB36E\uC5B4\uC4F0\uAE30\uB429\uB2C8\uB2E4."));
4927
+ console.log(chalk26.yellow("\u26A0\uFE0F \uC774\uBBF8 VHK \uC124\uCE58 \uD754\uC801\uC774 \uAC10\uC9C0\uB410\uC5B4\uC694:"));
4928
+ for (const f of footprint) console.log(chalk26.dim(` - ${f}`));
4929
+ console.log(chalk26.dim(" \uACC4\uC18D \uC9C4\uD589\uD558\uBA74 \uC77C\uBD80 \uD30C\uC77C(`.cursor/mcp.json`, `.vhk/context.md`)\uC740 \uAC31\uC2E0\xB7\uB36E\uC5B4\uC4F0\uAE30\uB429\uB2C8\uB2E4."));
4947
4930
  const { proceedExisting } = await inquirer11.prompt([{
4948
4931
  type: "confirm",
4949
4932
  name: "proceedExisting",
@@ -4981,7 +4964,7 @@ ${ko.start.title}
4981
4964
  await runStep("[3/4] vhk mcp-init", () => mcpInit());
4982
4965
  log.step(ko.start.step4Header);
4983
4966
  await runStep("[4/4] vhk context", () => context());
4984
- console.log(chalk27.bold.green(`
4967
+ console.log(chalk26.bold.green(`
4985
4968
  ${ko.start.allDone}
4986
4969
  `));
4987
4970
  printNextStep({
@@ -4994,7 +4977,7 @@ ${ko.start.allDone}
4994
4977
  import fs12 from "fs";
4995
4978
  import os from "os";
4996
4979
  import path13 from "path";
4997
- import chalk28 from "chalk";
4980
+ import chalk27 from "chalk";
4998
4981
 
4999
4982
  // src/lib/vhk-cloud.ts
5000
4983
  var import_ignore = __toESM(require_ignore(), 1);
@@ -5086,14 +5069,14 @@ ${CLOUD_CONFIG_FILE}
5086
5069
  function ensureGhReady() {
5087
5070
  const ver = safeExecFile("gh", ["--version"]);
5088
5071
  if (!ver.ok) {
5089
- console.log(chalk28.red(` ${ko.cloud.noGh}`));
5090
- console.log(chalk28.dim(" \uC124\uCE58: https://cli.github.com/ (\uC124\uCE58 \uD6C4 `gh auth login`)"));
5072
+ console.log(chalk27.red(` ${ko.cloud.noGh}`));
5073
+ console.log(chalk27.dim(" \uC124\uCE58: https://cli.github.com/ (\uC124\uCE58 \uD6C4 `gh auth login`)"));
5091
5074
  return false;
5092
5075
  }
5093
5076
  const auth = safeExecFile("gh", ["auth", "status"]);
5094
5077
  if (!auth.ok) {
5095
- console.log(chalk28.red(` ${ko.cloud.noAuth}`));
5096
- console.log(chalk28.dim(" \uC2E4\uD589: gh auth login (gist \uAD8C\uD55C \uD544\uC694)"));
5078
+ console.log(chalk27.red(` ${ko.cloud.noAuth}`));
5079
+ console.log(chalk27.dim(" \uC2E4\uD589: gh auth login (gist \uAD8C\uD55C \uD544\uC694)"));
5097
5080
  return false;
5098
5081
  }
5099
5082
  return true;
@@ -5106,18 +5089,18 @@ function parseGistId(output) {
5106
5089
  return null;
5107
5090
  }
5108
5091
  async function cloudPush() {
5109
- console.log(chalk28.bold(`
5092
+ console.log(chalk27.bold(`
5110
5093
  ${ko.cloud.pushTitle}
5111
5094
  `));
5112
5095
  const cwd = process.cwd();
5113
5096
  if (!fs12.existsSync(path13.join(cwd, VHK_DIR2))) {
5114
- console.log(chalk28.yellow(` ${ko.cloud.noVhkDir}`));
5097
+ console.log(chalk27.yellow(` ${ko.cloud.noVhkDir}`));
5115
5098
  return;
5116
5099
  }
5117
5100
  const ig = loadVhkignore(cwd);
5118
5101
  const files = collectVhkFiles(cwd, ig);
5119
5102
  if (files.length === 0) {
5120
- console.log(chalk28.yellow(` ${ko.cloud.nothingToSync}`));
5103
+ console.log(chalk27.yellow(` ${ko.cloud.nothingToSync}`));
5121
5104
  return;
5122
5105
  }
5123
5106
  if (!ensureGhReady()) {
@@ -5125,7 +5108,7 @@ ${ko.cloud.pushTitle}
5125
5108
  return;
5126
5109
  }
5127
5110
  const filePaths = files.map((f) => path13.join(cwd, VHK_DIR2, f));
5128
- console.log(chalk28.dim(` \u{1F4E6} \uBC31\uC5C5 \uB300\uC0C1 ${files.length}\uAC1C: ${files.join(", ")}
5111
+ console.log(chalk27.dim(` \u{1F4E6} \uBC31\uC5C5 \uB300\uC0C1 ${files.length}\uAC1C: ${files.join(", ")}
5129
5112
  `));
5130
5113
  const existing = readCloudConfig(cwd);
5131
5114
  const desc = `vhk .vhk backup \u2014 ${path13.basename(cwd)}`;
@@ -5137,8 +5120,8 @@ ${ko.cloud.pushTitle}
5137
5120
  const args = gistFiles.includes(name) ? ["gist", "edit", existing.gistId, "-f", name, src] : ["gist", "edit", existing.gistId, "-a", src];
5138
5121
  const res2 = safeExecFile("gh", args);
5139
5122
  if (!res2.ok) {
5140
- console.log(chalk28.red(` ${ko.cloud.pushFail}: ${name}`));
5141
- console.log(chalk28.dim(` ${res2.err}`));
5123
+ console.log(chalk27.red(` ${ko.cloud.pushFail}: ${name}`));
5124
+ console.log(chalk27.dim(` ${res2.err}`));
5142
5125
  process.exitCode = 1;
5143
5126
  return;
5144
5127
  }
@@ -5153,15 +5136,15 @@ ${ko.cloud.pushTitle}
5153
5136
  if (!purgeFailed.includes(name)) purgeFailed.push(name);
5154
5137
  }
5155
5138
  }
5156
- console.log(chalk28.green.bold(` ${ko.cloud.pushDone}`));
5157
- console.log(chalk28.dim(` gist: ${existing.gistId} (\uAC31\uC2E0)`));
5139
+ console.log(chalk27.green.bold(` ${ko.cloud.pushDone}`));
5140
+ console.log(chalk27.dim(` gist: ${existing.gistId} (\uAC31\uC2E0)`));
5158
5141
  if (excluded.length > 0) {
5159
5142
  const purged = excluded.filter((n) => !purgeFailed.includes(n));
5160
5143
  if (purged.length > 0) {
5161
- console.log(chalk28.dim(` \u{1F512} \uC81C\uC678 \uB300\uC0C1 ${purged.length}\uAC1C gist \uC5D0\uC11C \uC81C\uAC70: ${purged.join(", ")}`));
5144
+ console.log(chalk27.dim(` \u{1F512} \uC81C\uC678 \uB300\uC0C1 ${purged.length}\uAC1C gist \uC5D0\uC11C \uC81C\uAC70: ${purged.join(", ")}`));
5162
5145
  }
5163
5146
  if (purgeFailed.length > 0) {
5164
- console.log(chalk28.yellow(` \u26A0\uFE0F \uC81C\uC678 \uB300\uC0C1 \uC81C\uAC70 \uC2E4\uD328: ${purgeFailed.join(", ")} (\uC218\uB3D9 \uC81C\uAC70 \uAD8C\uC7A5 \u2014 pull \uC2DC\uC5D4 \uBCF5\uC6D0 \uC548 \uB428)`));
5147
+ console.log(chalk27.yellow(` \u26A0\uFE0F \uC81C\uC678 \uB300\uC0C1 \uC81C\uAC70 \uC2E4\uD328: ${purgeFailed.join(", ")} (\uC218\uB3D9 \uC81C\uAC70 \uAD8C\uC7A5 \u2014 pull \uC2DC\uC5D4 \uBCF5\uC6D0 \uC548 \uB428)`));
5165
5148
  }
5166
5149
  }
5167
5150
  printPushNext();
@@ -5169,32 +5152,32 @@ ${ko.cloud.pushTitle}
5169
5152
  }
5170
5153
  const res = safeExecFile("gh", ["gist", "create", "--desc", desc, ...filePaths]);
5171
5154
  if (!res.ok) {
5172
- console.log(chalk28.red(` ${ko.cloud.pushFail}`));
5173
- console.log(chalk28.dim(` ${res.err || res.out}`));
5155
+ console.log(chalk27.red(` ${ko.cloud.pushFail}`));
5156
+ console.log(chalk27.dim(` ${res.err || res.out}`));
5174
5157
  process.exitCode = 1;
5175
5158
  return;
5176
5159
  }
5177
5160
  const gistId = parseGistId(res.out);
5178
5161
  if (!gistId) {
5179
- console.log(chalk28.red(` ${ko.cloud.pushFail} \u2014 gist id \uD30C\uC2F1 \uC2E4\uD328`));
5180
- console.log(chalk28.dim(` \uCD9C\uB825: ${res.out}`));
5162
+ console.log(chalk27.red(` ${ko.cloud.pushFail} \u2014 gist id \uD30C\uC2F1 \uC2E4\uD328`));
5163
+ console.log(chalk27.dim(` \uCD9C\uB825: ${res.out}`));
5181
5164
  process.exitCode = 1;
5182
5165
  return;
5183
5166
  }
5184
5167
  writeCloudConfig(cwd, { gistId });
5185
- console.log(chalk28.green.bold(` ${ko.cloud.pushDone}`));
5186
- console.log(chalk28.dim(` gist: ${gistId} (\uC2E0\uADDC, secret) \u2192 .vhk/cloud.json \uC800\uC7A5`));
5168
+ console.log(chalk27.green.bold(` ${ko.cloud.pushDone}`));
5169
+ console.log(chalk27.dim(` gist: ${gistId} (\uC2E0\uADDC, secret) \u2192 .vhk/cloud.json \uC800\uC7A5`));
5187
5170
  printPushNext();
5188
5171
  }
5189
5172
  async function cloudPull(gistIdArg) {
5190
- console.log(chalk28.bold(`
5173
+ console.log(chalk27.bold(`
5191
5174
  ${ko.cloud.pullTitle}
5192
5175
  `));
5193
5176
  const cwd = process.cwd();
5194
5177
  const gistId = gistIdArg || readCloudConfig(cwd)?.gistId;
5195
5178
  if (!gistId) {
5196
- console.log(chalk28.yellow(` ${ko.cloud.noGistId}`));
5197
- console.log(chalk28.dim(" \uC0AC\uC6A9\uBC95: vhk cloud pull <gistId> (\uB610\uB294 cloud.json \uC774 \uC788\uB294 \uACF3\uC5D0\uC11C \uC2E4\uD589)"));
5179
+ console.log(chalk27.yellow(` ${ko.cloud.noGistId}`));
5180
+ console.log(chalk27.dim(" \uC0AC\uC6A9\uBC95: vhk cloud pull <gistId> (\uB610\uB294 cloud.json \uC774 \uC788\uB294 \uACF3\uC5D0\uC11C \uC2E4\uD589)"));
5198
5181
  return;
5199
5182
  }
5200
5183
  if (!ensureGhReady()) {
@@ -5203,16 +5186,16 @@ ${ko.cloud.pullTitle}
5203
5186
  }
5204
5187
  const allNames = listGistFiles(gistId);
5205
5188
  if (allNames.length === 0) {
5206
- console.log(chalk28.red(` ${ko.cloud.pullFail} \u2014 gist \uBE44\uC5C8\uAC70\uB098 \uC811\uADFC \uBD88\uAC00: ${gistId}`));
5189
+ console.log(chalk27.red(` ${ko.cloud.pullFail} \u2014 gist \uBE44\uC5C8\uAC70\uB098 \uC811\uADFC \uBD88\uAC00: ${gistId}`));
5207
5190
  process.exitCode = 1;
5208
5191
  return;
5209
5192
  }
5210
5193
  const { keep: names, excluded: skipped } = partitionGistFiles(allNames, loadVhkignore(cwd));
5211
5194
  if (skipped.length > 0) {
5212
- console.log(chalk28.dim(` \u{1F512} \uC81C\uC678 \uB300\uC0C1 ${skipped.length}\uAC1C \uBCF5\uC6D0 \uC2A4\uD0B5: ${skipped.join(", ")}`));
5195
+ console.log(chalk27.dim(` \u{1F512} \uC81C\uC678 \uB300\uC0C1 ${skipped.length}\uAC1C \uBCF5\uC6D0 \uC2A4\uD0B5: ${skipped.join(", ")}`));
5213
5196
  }
5214
5197
  if (names.length === 0) {
5215
- console.log(chalk28.yellow(` \uBCF5\uC6D0 \uB300\uC0C1\uC774 \uC5C6\uC2B5\uB2C8\uB2E4 (gist \uD30C\uC77C\uC774 \uBAA8\uB450 \uC81C\uC678 \uADDC\uCE59\uC5D0 \uD574\uB2F9).`));
5198
+ console.log(chalk27.yellow(` \uBCF5\uC6D0 \uB300\uC0C1\uC774 \uC5C6\uC2B5\uB2C8\uB2E4 (gist \uD30C\uC77C\uC774 \uBAA8\uB450 \uC81C\uC678 \uADDC\uCE59\uC5D0 \uD574\uB2F9).`));
5216
5199
  return;
5217
5200
  }
5218
5201
  const vhkDir = path13.join(cwd, VHK_DIR2);
@@ -5221,16 +5204,16 @@ ${ko.cloud.pullTitle}
5221
5204
  for (const name of names) {
5222
5205
  const res = safeExecFile("gh", ["gist", "view", gistId, "-f", name, "--raw"]);
5223
5206
  if (!res.ok) {
5224
- console.log(chalk28.red(` ${ko.cloud.pullFail}: ${name}`));
5225
- console.log(chalk28.dim(` ${res.err}`));
5207
+ console.log(chalk27.red(` ${ko.cloud.pullFail}: ${name}`));
5208
+ console.log(chalk27.dim(` ${res.err}`));
5226
5209
  continue;
5227
5210
  }
5228
5211
  fs12.writeFileSync(path13.join(vhkDir, name), ensureTrailingNewline(res.out), "utf-8");
5229
5212
  restored++;
5230
5213
  }
5231
5214
  writeCloudConfig(cwd, { gistId });
5232
- console.log(chalk28.green.bold(` ${ko.cloud.pullDone}`));
5233
- console.log(chalk28.dim(` ${restored}\uAC1C \uD30C\uC77C \uBCF5\uC6D0 (gist: ${gistId})`));
5215
+ console.log(chalk27.green.bold(` ${ko.cloud.pullDone}`));
5216
+ console.log(chalk27.dim(` ${restored}\uAC1C \uD30C\uC77C \uBCF5\uC6D0 (gist: ${gistId})`));
5234
5217
  printNextStep({
5235
5218
  message: "\uD074\uB77C\uC6B0\uB4DC\uC5D0\uC11C .vhk/ \uBCF5\uC6D0 \uC644\uB8CC!",
5236
5219
  command: "vhk \uB9E5\uB77D",
@@ -5278,7 +5261,7 @@ function printPushNext() {
5278
5261
  }
5279
5262
 
5280
5263
  // src/commands/help.ts
5281
- import chalk29 from "chalk";
5264
+ import chalk28 from "chalk";
5282
5265
  var QUICK_ACTIONS = [
5283
5266
  { say: "\uC0C1\uD0DC \uC54C\uB824\uC918", does: "vhk status" },
5284
5267
  { say: "\uBB50 \uBC14\uB00C\uC5C8\uC5B4?", does: "vhk diff" },
@@ -5292,17 +5275,17 @@ var QUICK_ACTIONS = [
5292
5275
  { say: "\uC804\uCCB4 \uBA85\uB839\uC5B4 \uBCF4\uAE30", does: "vhk --help" }
5293
5276
  ];
5294
5277
  function quickActions() {
5295
- console.log(chalk29.bold("\n\u{1F9ED} VHK \u2014 \uC774\uB807\uAC8C \uB9D0\uD558\uBA74 \uB429\uB2C8\uB2E4 (quick actions)"));
5296
- console.log(chalk29.gray("\u2500".repeat(40)));
5278
+ console.log(chalk28.bold("\n\u{1F9ED} VHK \u2014 \uC774\uB807\uAC8C \uB9D0\uD558\uBA74 \uB429\uB2C8\uB2E4 (quick actions)"));
5279
+ console.log(chalk28.gray("\u2500".repeat(40)));
5297
5280
  for (const a of QUICK_ACTIONS) {
5298
- console.log(` "${chalk29.cyan(a.say)}" \u2192 ${chalk29.dim(a.does)}`);
5281
+ console.log(` "${chalk28.cyan(a.say)}" \u2192 ${chalk28.dim(a.does)}`);
5299
5282
  }
5300
- console.log(chalk29.gray("\n \uC804\uCCB4 \uBA85\uB839\uC740 `vhk --help` \uB610\uB294 COMMANDS.md \uB97C \uBCF4\uC138\uC694."));
5283
+ console.log(chalk28.gray("\n \uC804\uCCB4 \uBA85\uB839\uC740 `vhk --help` \uB610\uB294 COMMANDS.md \uB97C \uBCF4\uC138\uC694."));
5301
5284
  console.log("");
5302
5285
  }
5303
5286
 
5304
5287
  // src/commands/mode.ts
5305
- import chalk30 from "chalk";
5288
+ import chalk29 from "chalk";
5306
5289
 
5307
5290
  // src/lib/config.ts
5308
5291
  import { existsSync as existsSync15, mkdirSync as mkdirSync10, writeFileSync as writeFileSync10 } from "fs";
@@ -5343,17 +5326,17 @@ function writeConfig(config, rootDir = process.cwd()) {
5343
5326
 
5344
5327
  // src/commands/mode.ts
5345
5328
  async function mode(target) {
5346
- console.log(chalk30.bold("\n\u{1F6E1}\uFE0F Safety Mode"));
5347
- console.log(chalk30.gray("\u2500".repeat(40)));
5329
+ console.log(chalk29.bold("\n\u{1F6E1}\uFE0F Safety Mode"));
5330
+ console.log(chalk29.gray("\u2500".repeat(40)));
5348
5331
  const current = readConfig().safetyMode;
5349
5332
  if (!target) {
5350
- console.log(chalk30.cyan(`
5351
- \uD604\uC7AC \uBAA8\uB4DC: ${chalk30.bold(current)}`));
5352
- console.log(chalk30.dim(` ${SAFETY_MODE_DESC[current]}`));
5333
+ console.log(chalk29.cyan(`
5334
+ \uD604\uC7AC \uBAA8\uB4DC: ${chalk29.bold(current)}`));
5335
+ console.log(chalk29.dim(` ${SAFETY_MODE_DESC[current]}`));
5353
5336
  console.log("");
5354
5337
  for (const m of SAFETY_MODES) {
5355
5338
  const mark = m === current ? "\u25CF" : "\u25CB";
5356
- console.log(` ${mark} ${m.padEnd(9)} ${chalk30.dim(SAFETY_MODE_DESC[m])}`);
5339
+ console.log(` ${mark} ${m.padEnd(9)} ${chalk29.dim(SAFETY_MODE_DESC[m])}`);
5357
5340
  }
5358
5341
  printNextStep({
5359
5342
  message: "\uBAA8\uB4DC\uB97C \uBC14\uAFB8\uB824\uBA74:",
@@ -5363,20 +5346,20 @@ async function mode(target) {
5363
5346
  return;
5364
5347
  }
5365
5348
  if (!isSafetyMode(target)) {
5366
- console.log(chalk30.red(`
5349
+ console.log(chalk29.red(`
5367
5350
  \u274C \uC54C \uC218 \uC5C6\uB294 \uBAA8\uB4DC: ${target}`));
5368
- console.log(chalk30.dim(` \uAC00\uB2A5: ${SAFETY_MODES.join(" | ")}`));
5351
+ console.log(chalk29.dim(` \uAC00\uB2A5: ${SAFETY_MODES.join(" | ")}`));
5369
5352
  process.exitCode = 1;
5370
5353
  return;
5371
5354
  }
5372
5355
  writeConfig({ ...readConfig(), safetyMode: target });
5373
- console.log(chalk30.green(`
5374
- \u2705 Safety Mode \u2192 ${chalk30.bold(target)}`));
5375
- console.log(chalk30.dim(` ${SAFETY_MODE_DESC[target]}`));
5356
+ console.log(chalk29.green(`
5357
+ \u2705 Safety Mode \u2192 ${chalk29.bold(target)}`));
5358
+ console.log(chalk29.dim(` ${SAFETY_MODE_DESC[target]}`));
5376
5359
  }
5377
5360
 
5378
5361
  // src/commands/verify.ts
5379
- import chalk31 from "chalk";
5362
+ import chalk30 from "chalk";
5380
5363
  function verificationChecklist() {
5381
5364
  return [
5382
5365
  "\uD0C0\uC785 \uCCB4\uD06C \u2014 pnpm exec tsc --noEmit",
@@ -5386,15 +5369,15 @@ function verificationChecklist() {
5386
5369
  ];
5387
5370
  }
5388
5371
  async function verify() {
5389
- console.log(chalk31.bold("\n\u{1F50E} \uAC80\uC99D \uBB36\uC74C (verify \u2014 lite)"));
5390
- console.log(chalk31.gray("\u2500".repeat(40)));
5372
+ console.log(chalk30.bold("\n\u{1F50E} \uAC80\uC99D \uBB36\uC74C (verify \u2014 lite)"));
5373
+ console.log(chalk30.gray("\u2500".repeat(40)));
5391
5374
  const mode2 = readConfig().safetyMode;
5392
- console.log(chalk31.dim(` \uD604\uC7AC Safety Mode: ${mode2} \u2014 ${SAFETY_MODE_DESC[mode2]}`));
5393
- console.log(chalk31.cyan("\n \uC704\uD5D8 \uC791\uC5C5/\uC800\uC7A5 \uC804 \uAD8C\uC7A5 \uAC80\uC99D:"));
5375
+ console.log(chalk30.dim(` \uD604\uC7AC Safety Mode: ${mode2} \u2014 ${SAFETY_MODE_DESC[mode2]}`));
5376
+ console.log(chalk30.cyan("\n \uC704\uD5D8 \uC791\uC5C5/\uC800\uC7A5 \uC804 \uAD8C\uC7A5 \uAC80\uC99D:"));
5394
5377
  for (const item of verificationChecklist()) {
5395
5378
  console.log(` \u2610 ${item}`);
5396
5379
  }
5397
- console.log(chalk31.dim("\n \u203B \uBA54\uD0C0\uB7EC\uB108(\uC790\uB3D9 \uC2E4\uD589) \uC790\uB9AC \u2014 \uD604\uC7AC\uB294 \uBB36\uC74C \uC548\uB0B4\uB9CC(lite)."));
5380
+ console.log(chalk30.dim("\n \u203B \uBA54\uD0C0\uB7EC\uB108(\uC790\uB3D9 \uC2E4\uD589) \uC790\uB9AC \u2014 \uD604\uC7AC\uB294 \uBB36\uC74C \uC548\uB0B4\uB9CC(lite)."));
5398
5381
  printNextStep({
5399
5382
  message: "\uAC80\uC99D \uD1B5\uACFC \uD6C4 \uC800\uC7A5\uD558\uC138\uC694:",
5400
5383
  command: "vhk save",
@@ -5580,14 +5563,14 @@ function requiresConfirmation(route) {
5580
5563
  async function runNaturalLanguageRoute(input) {
5581
5564
  const route = routeNaturalLanguage(input);
5582
5565
  if (!route) {
5583
- console.log(chalk32.yellow(`
5566
+ console.log(chalk31.yellow(`
5584
5567
  \u2753 "${input}" \u2014 ${ko.nlp.notMatched}
5585
5568
  `));
5586
5569
  return;
5587
5570
  }
5588
5571
  console.log("");
5589
- console.log(chalk32.cyan(` \u{1F4AC} "${input}"`));
5590
- console.log(chalk32.cyan(` \u2192 ${route.explanation}`));
5572
+ console.log(chalk31.cyan(` \u{1F4AC} "${input}"`));
5573
+ console.log(chalk31.cyan(` \u2192 ${route.explanation}`));
5591
5574
  if (requiresConfirmation(route)) {
5592
5575
  const { confirm } = await inquirer12.prompt([{
5593
5576
  type: "confirm",
@@ -5596,7 +5579,7 @@ async function runNaturalLanguageRoute(input) {
5596
5579
  default: true
5597
5580
  }]);
5598
5581
  if (!confirm) {
5599
- console.log(chalk32.dim(` ${ko.nlp.menuHint}`));
5582
+ console.log(chalk31.dim(` ${ko.nlp.menuHint}`));
5600
5583
  return;
5601
5584
  }
5602
5585
  }
@@ -5605,7 +5588,7 @@ async function runNaturalLanguageRoute(input) {
5605
5588
  if (riskAction) {
5606
5589
  await runGuarded(
5607
5590
  riskAction,
5608
- { channel: "nl", approved: false, log: (m) => console.log(chalk32.yellow(` ${m}`)) },
5591
+ { channel: "nl", approved: false, log: (m) => console.log(chalk31.yellow(` ${m}`)) },
5609
5592
  () => dispatchNlpRoute(route, input)
5610
5593
  );
5611
5594
  return;
@@ -5614,77 +5597,77 @@ async function runNaturalLanguageRoute(input) {
5614
5597
  }
5615
5598
 
5616
5599
  // src/commands/agent.ts
5617
- import chalk33 from "chalk";
5600
+ import chalk32 from "chalk";
5618
5601
  function activeGoalId() {
5619
5602
  const goals = listGoals("goals");
5620
5603
  const id = selectActiveId(goals);
5621
5604
  return id ?? void 0;
5622
5605
  }
5623
5606
  async function blocker(description) {
5624
- console.log(chalk33.bold(`
5607
+ console.log(chalk32.bold(`
5625
5608
  ${ko.agent.blockerTitle}
5626
5609
  `));
5627
5610
  if (!description || !description.trim()) {
5628
- console.log(chalk33.red(" \u274C \uBE14\uB85C\uCEE4 \uC124\uBA85\uC744 \uC785\uB825\uD574 \uC8FC\uC138\uC694."));
5629
- console.log(chalk33.dim(' \uC608: vhk blocker "tsc \uC5D0\uB7EC \u2014 simple-git \uD0C0\uC785 \uD638\uD658"'));
5611
+ console.log(chalk32.red(" \u274C \uBE14\uB85C\uCEE4 \uC124\uBA85\uC744 \uC785\uB825\uD574 \uC8FC\uC138\uC694."));
5612
+ console.log(chalk32.dim(' \uC608: vhk blocker "tsc \uC5D0\uB7EC \u2014 simple-git \uD0C0\uC785 \uD638\uD658"'));
5630
5613
  process.exitCode = 1;
5631
5614
  return;
5632
5615
  }
5633
5616
  const goalId = activeGoalId();
5634
5617
  const r = appendBlocker(description, goalId);
5635
- console.log(chalk33.green(` \u2705 blocker \uAE30\uB85D (\uD604\uC7AC \uD65C\uC131 ${r.count}\uAC74)`));
5618
+ console.log(chalk32.green(` \u2705 blocker \uAE30\uB85D (\uD604\uC7AC \uD65C\uC131 ${r.count}\uAC74)`));
5636
5619
  if (r.hardStopTripped) {
5637
- console.log(chalk33.red.bold(" \u{1F6D1} HARD_STOP \uC790\uB3D9 \uC0DD\uC131 \u2014 \uBAA8\uB4E0 \uC790\uB3D9\uD654 \uC911\uB2E8."));
5638
- console.log(chalk33.yellow(" \uC0AC\uB78C \uAC80\uD1A0 \uD6C4 `vhk resume --confirm` \uC73C\uB85C\uB9CC \uD574\uC81C."));
5620
+ console.log(chalk32.red.bold(" \u{1F6D1} HARD_STOP \uC790\uB3D9 \uC0DD\uC131 \u2014 \uBAA8\uB4E0 \uC790\uB3D9\uD654 \uC911\uB2E8."));
5621
+ console.log(chalk32.yellow(" \uC0AC\uB78C \uAC80\uD1A0 \uD6C4 `vhk resume --confirm` \uC73C\uB85C\uB9CC \uD574\uC81C."));
5639
5622
  process.exitCode = 2;
5640
5623
  }
5641
5624
  }
5642
5625
  async function learn(lesson) {
5643
- console.log(chalk33.bold(`
5626
+ console.log(chalk32.bold(`
5644
5627
  ${ko.agent.learnTitle}
5645
5628
  `));
5646
5629
  if (!lesson || !lesson.trim()) {
5647
- console.log(chalk33.red(" \u274C \uAD50\uD6C8 \uB0B4\uC6A9\uC744 \uC785\uB825\uD574 \uC8FC\uC138\uC694."));
5648
- console.log(chalk33.dim(' \uC608: vhk learn "PowerShell \uC5D0\uC11C\uB294 ; \uC0AC\uC6A9 (&& \uBBF8\uC9C0\uC6D0)"'));
5630
+ console.log(chalk32.red(" \u274C \uAD50\uD6C8 \uB0B4\uC6A9\uC744 \uC785\uB825\uD574 \uC8FC\uC138\uC694."));
5631
+ console.log(chalk32.dim(' \uC608: vhk learn "PowerShell \uC5D0\uC11C\uB294 ; \uC0AC\uC6A9 (&& \uBBF8\uC9C0\uC6D0)"'));
5649
5632
  process.exitCode = 1;
5650
5633
  return;
5651
5634
  }
5652
5635
  const goalId = activeGoalId();
5653
5636
  appendLearning(lesson, goalId);
5654
- console.log(chalk33.green(" \u2705 learnings.md append."));
5637
+ console.log(chalk32.green(" \u2705 learnings.md append."));
5655
5638
  console.log(
5656
- chalk33.dim(" \uACB0\uC815\uC0AC\uD56D(decision)\uC740 `vhk memory add` \uB85C \uBCC4\uB3C4 \uAE30\uB85D \u2014 SoT \uBD84\uB9AC.")
5639
+ chalk32.dim(" \uACB0\uC815\uC0AC\uD56D(decision)\uC740 `vhk memory add` \uB85C \uBCC4\uB3C4 \uAE30\uB85D \u2014 SoT \uBD84\uB9AC.")
5657
5640
  );
5658
5641
  }
5659
5642
  async function resume(opts = {}) {
5660
- console.log(chalk33.bold(`
5643
+ console.log(chalk32.bold(`
5661
5644
  ${ko.agent.resumeTitle}
5662
5645
  `));
5663
5646
  if (!isHardStopActive()) {
5664
- console.log(chalk33.dim(" HARD_STOP \uD65C\uC131 \uC544\uB2D8 \u2014 \uD560 \uC77C \uC5C6\uC74C."));
5647
+ console.log(chalk32.dim(" HARD_STOP \uD65C\uC131 \uC544\uB2D8 \u2014 \uD560 \uC77C \uC5C6\uC74C."));
5665
5648
  return;
5666
5649
  }
5667
5650
  const reason = readHardStopReason();
5668
5651
  if (reason) {
5669
- console.log(chalk33.yellow(" \u{1F4CB} HARD_STOP \uC0AC\uC720:"));
5670
- console.log(chalk33.dim(` ${reason.split("\n").join("\n ")}`));
5652
+ console.log(chalk32.yellow(" \u{1F4CB} HARD_STOP \uC0AC\uC720:"));
5653
+ console.log(chalk32.dim(` ${reason.split("\n").join("\n ")}`));
5671
5654
  console.log("");
5672
5655
  }
5673
5656
  if (!opts.confirm) {
5674
5657
  console.log(
5675
- chalk33.red(
5658
+ chalk32.red(
5676
5659
  " \u274C --confirm \uD50C\uB798\uADF8 \uC5C6\uC774\uB294 \uD574\uC81C\uD560 \uC218 \uC5C6\uC2B5\uB2C8\uB2E4 (\uC790\uB3D9 \uD638\uCD9C \uAE08\uC9C0)."
5677
5660
  )
5678
5661
  );
5679
- console.log(chalk33.yellow(" \uC0AC\uC720\uB97C \uD655\uC778\uD55C \uD6C4 \uB2E4\uC2DC: vhk resume --confirm"));
5662
+ console.log(chalk32.yellow(" \uC0AC\uC720\uB97C \uD655\uC778\uD55C \uD6C4 \uB2E4\uC2DC: vhk resume --confirm"));
5680
5663
  process.exitCode = 1;
5681
5664
  return;
5682
5665
  }
5683
5666
  const removed = clearHardStop();
5684
5667
  if (removed) {
5685
- console.log(chalk33.green(" \u2705 HARD_STOP \uD574\uC81C. \uC790\uB3D9\uD654 \uC7AC\uAC1C \uAC00\uB2A5."));
5668
+ console.log(chalk32.green(" \u2705 HARD_STOP \uD574\uC81C. \uC790\uB3D9\uD654 \uC7AC\uAC1C \uAC00\uB2A5."));
5686
5669
  } else {
5687
- console.log(chalk33.dim(" \uD30C\uC77C\uC774 \uC774\uBBF8 \uC5C6\uC74C \u2014 no-op."));
5670
+ console.log(chalk32.dim(" \uD30C\uC77C\uC774 \uC774\uBBF8 \uC5C6\uC74C \u2014 no-op."));
5688
5671
  }
5689
5672
  }
5690
5673
 
@@ -5705,7 +5688,7 @@ async function guardCli(action, approved, run) {
5705
5688
  }]);
5706
5689
  return ok;
5707
5690
  },
5708
- log: (m) => console.log(chalk34.yellow(` ${m}`))
5691
+ log: (m) => console.log(chalk33.yellow(` ${m}`))
5709
5692
  },
5710
5693
  run
5711
5694
  );
@@ -5718,7 +5701,7 @@ async function guardCliDefer(action, approved, run) {
5718
5701
  approved,
5719
5702
  // TTY 면 통과(명령이 자체 확인), 비대화형은 confirm 불가 → 가드가 차단.
5720
5703
  confirm: async () => !!process.stdout.isTTY,
5721
- log: (m) => console.log(chalk34.yellow(` ${m}`))
5704
+ log: (m) => console.log(chalk33.yellow(` ${m}`))
5722
5705
  },
5723
5706
  run
5724
5707
  );
@@ -5845,8 +5828,8 @@ program.command("design").alias("\uB514\uC790\uC778").description("\uB514\uC790\
5845
5828
  program.command("design-palette").alias("\uD314\uB808\uD2B8").description("\uCEEC\uB7EC \uD314\uB808\uD2B8 \uD504\uB9AC\uC14B \uC120\uD0DD + \uC801\uC6A9").action(async () => {
5846
5829
  await designPalette();
5847
5830
  });
5848
- program.command("theme").alias("\uD14C\uB9C8").description("\uB2E4\uD06C/\uB77C\uC774\uD2B8 \uBAA8\uB4DC CSS + \uD1A0\uAE00 \uC720\uD2F8\uB9AC\uD2F0 \uC0DD\uC131").action(async () => {
5849
- await theme();
5831
+ program.command("theme").alias("\uD14C\uB9C8").option("-y, --yes", "\uAE30\uC874 \uD30C\uC77C \uB36E\uC5B4\uC4F0\uAE30 \uD655\uC778 \uC2A4\uD0B5 (\uBE44\uB300\uD654\uD615 \uC790\uB3D9 \uB36E\uC5B4\uC4F0\uAE30)").description("\uB2E4\uD06C/\uB77C\uC774\uD2B8 \uBAA8\uB4DC CSS + \uD1A0\uAE00 \uC720\uD2F8\uB9AC\uD2F0 \uC0DD\uC131").action(async (opts) => {
5832
+ await theme(opts);
5850
5833
  });
5851
5834
  var refCmd = program.command("ref").alias("\uB808\uD37C\uB7F0\uC2A4").description("\uB808\uD37C\uB7F0\uC2A4 URL \uAD00\uB9AC (add / list / open)").action(async () => {
5852
5835
  await refList();
@@ -5995,9 +5978,9 @@ if (isMainModule) {
5995
5978
  }
5996
5979
  } catch (err) {
5997
5980
  if (isPromptAbortError(err)) {
5998
- console.error(chalk34.yellow("\n \u26A0\uFE0F \uB300\uD654\uD615 \uC785\uB825\uC774 \uCDE8\uC18C/\uC885\uB8CC\uB410\uC2B5\uB2C8\uB2E4. (\uBE44\uB300\uD654\uD615 \uD658\uACBD\uC5D0\uC11C\uB294 \uD574\uB2F9 \uBA85\uB839\uC744 \uC4F8 \uC218 \uC5C6\uC5B4\uC694)"));
5981
+ console.error(chalk33.yellow("\n \u26A0\uFE0F \uB300\uD654\uD615 \uC785\uB825\uC774 \uCDE8\uC18C/\uC885\uB8CC\uB410\uC2B5\uB2C8\uB2E4. (\uBE44\uB300\uD654\uD615 \uD658\uACBD\uC5D0\uC11C\uB294 \uD574\uB2F9 \uBA85\uB839\uC744 \uC4F8 \uC218 \uC5C6\uC5B4\uC694)"));
5999
5982
  } else {
6000
- console.error(chalk34.red(`
5983
+ console.error(chalk33.red(`
6001
5984
  \u274C ${err instanceof Error ? err.message : String(err)}`));
6002
5985
  }
6003
5986
  process.exitCode = 1;