@mks2508/coolify-mks-cli-mcp 0.6.3 → 0.9.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (75) hide show
  1. package/dist/cli/coolify-state.d.ts +101 -5
  2. package/dist/cli/coolify-state.d.ts.map +1 -1
  3. package/dist/cli/index.js +23165 -11543
  4. package/dist/cli/ui/highlighter.d.ts +28 -0
  5. package/dist/cli/ui/highlighter.d.ts.map +1 -0
  6. package/dist/cli/ui/index.d.ts +9 -0
  7. package/dist/cli/ui/index.d.ts.map +1 -0
  8. package/dist/cli/ui/spinners.d.ts +100 -0
  9. package/dist/cli/ui/spinners.d.ts.map +1 -0
  10. package/dist/cli/ui/tables.d.ts +103 -0
  11. package/dist/cli/ui/tables.d.ts.map +1 -0
  12. package/dist/coolify/config.d.ts +25 -0
  13. package/dist/coolify/config.d.ts.map +1 -1
  14. package/dist/coolify/index.d.ts +139 -12
  15. package/dist/coolify/index.d.ts.map +1 -1
  16. package/dist/coolify/types.d.ts +160 -2
  17. package/dist/coolify/types.d.ts.map +1 -1
  18. package/dist/examples/demo-ui.d.ts +8 -0
  19. package/dist/examples/demo-ui.d.ts.map +1 -0
  20. package/dist/index.cjs +2580 -230
  21. package/dist/index.cjs.map +1 -1
  22. package/dist/index.js +2598 -226
  23. package/dist/index.js.map +1 -1
  24. package/dist/sdk.d.ts +96 -7
  25. package/dist/sdk.d.ts.map +1 -1
  26. package/dist/server/stdio.js +475 -73
  27. package/dist/tools/definitions.d.ts.map +1 -1
  28. package/dist/tools/handlers.d.ts.map +1 -1
  29. package/dist/utils/env-parser.d.ts +24 -0
  30. package/dist/utils/env-parser.d.ts.map +1 -0
  31. package/dist/utils/format.d.ts +32 -0
  32. package/dist/utils/format.d.ts.map +1 -1
  33. package/package.json +17 -4
  34. package/src/cli/actions.ts +9 -2
  35. package/src/cli/commands/create.ts +332 -24
  36. package/src/cli/commands/db.ts +37 -0
  37. package/src/cli/commands/delete.ts +6 -2
  38. package/src/cli/commands/deploy.ts +347 -49
  39. package/src/cli/commands/deployments.ts +6 -2
  40. package/src/cli/commands/diagnose.ts +3 -3
  41. package/src/cli/commands/env.ts +424 -31
  42. package/src/cli/commands/exec.ts +6 -2
  43. package/src/cli/commands/init.ts +991 -0
  44. package/src/cli/commands/logs.ts +224 -24
  45. package/src/cli/commands/main-menu.ts +21 -0
  46. package/src/cli/commands/projects.ts +312 -29
  47. package/src/cli/commands/restart.ts +6 -2
  48. package/src/cli/commands/service-logs.ts +14 -0
  49. package/src/cli/commands/show.ts +45 -12
  50. package/src/cli/commands/start.ts +6 -2
  51. package/src/cli/commands/status.ts +554 -0
  52. package/src/cli/commands/stop.ts +6 -2
  53. package/src/cli/commands/svc.ts +7 -1
  54. package/src/cli/commands/update.ts +79 -2
  55. package/src/cli/commands/volumes.ts +293 -0
  56. package/src/cli/coolify-state.ts +203 -12
  57. package/src/cli/index.ts +138 -11
  58. package/src/cli/name-resolver.ts +228 -0
  59. package/src/cli/ui/banner.ts +276 -0
  60. package/src/cli/ui/highlighter.ts +176 -0
  61. package/src/cli/ui/index.ts +9 -0
  62. package/src/cli/ui/prompts.ts +155 -0
  63. package/src/cli/ui/screen.ts +630 -0
  64. package/src/cli/ui/select.ts +280 -0
  65. package/src/cli/ui/spinners.ts +256 -0
  66. package/src/cli/ui/tables.ts +407 -0
  67. package/src/coolify/config.ts +75 -0
  68. package/src/coolify/index.ts +565 -101
  69. package/src/coolify/types.ts +165 -2
  70. package/src/examples/demo-ui.ts +78 -0
  71. package/src/sdk.ts +211 -1
  72. package/src/tools/definitions.ts +22 -0
  73. package/src/tools/handlers.ts +19 -0
  74. package/src/utils/env-parser.ts +45 -0
  75. package/src/utils/format.ts +178 -0
package/dist/index.cjs CHANGED
@@ -8,6 +8,9 @@ var __hasOwnProp = Object.prototype.hasOwnProperty;
8
8
  var __esm = (fn, res) => function() {
9
9
  return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res;
10
10
  };
11
+ var __commonJS = (cb, mod) => function() {
12
+ return mod || (0, cb[__getOwnPropNames(cb)[0]])((mod = { exports: {} }).exports, mod), mod.exports;
13
+ };
11
14
  var __export = (target, all) => {
12
15
  for (var name in all) __defProp(target, name, {
13
16
  get: all[name],
@@ -533,10 +536,10 @@ function isRunningInTerminal() {
533
536
  return Boolean(isTTY || hasTerminalEnv || isTerminalProgram);
534
537
  }
535
538
  function supportsANSI() {
536
- const env = getEnvironment();
537
- if (env === "browser") return false;
538
- if (env === "terminal") return true;
539
- if (env === "server") return checkServerANSISupport();
539
+ const env$1 = getEnvironment();
540
+ if (env$1 === "browser") return false;
541
+ if (env$1 === "terminal") return true;
542
+ if (env$1 === "server") return checkServerANSISupport();
540
543
  return false;
541
544
  }
542
545
  function checkServerANSISupport() {
@@ -545,8 +548,8 @@ function checkServerANSISupport() {
545
548
  return Boolean(supportsANSI2);
546
549
  }
547
550
  function getColorCapability() {
548
- const env = getEnvironment();
549
- if (env === "browser") return "full";
551
+ const env$1 = getEnvironment();
552
+ if (env$1 === "browser") return "full";
550
553
  if (!supportsANSI()) return "none";
551
554
  if (typeof process !== "undefined" && process.env) {
552
555
  const hasTrueColor = process.env.COLORTERM === "truecolor" || process.env.COLORTERM === "24bit";
@@ -956,7 +959,7 @@ var TerminalRenderer = class {
956
959
  /**
957
960
  * Get ANSI style codes
958
961
  */
959
- getStyleCode(styles) {
962
+ getStyleCode(styles$2) {
960
963
  const styleCodes = {
961
964
  "bold": "1",
962
965
  "dim": "2",
@@ -964,27 +967,27 @@ var TerminalRenderer = class {
964
967
  "underline": "4",
965
968
  "reset": "0"
966
969
  };
967
- const codes = styles.map((style) => styleCodes[style] || "0").join(";");
968
- return codes ? `\x1B[${codes}m` : "";
970
+ const codes$1 = styles$2.map((style) => styleCodes[style] || "0").join(";");
971
+ return codes$1 ? `\x1B[${codes$1}m` : "";
969
972
  }
970
973
  /**
971
974
  * Convert log styles to ANSI formatting
972
975
  */
973
- renderTerminal(level, message, timestamp, prefix, location, styles) {
976
+ renderTerminal(level$1, message, timestamp, prefix, location, styles$2) {
974
977
  const reset = "\x1B[0m";
975
978
  const result = {
976
979
  text: "",
977
980
  reset
978
981
  };
979
- if (styles) {
980
- result.timestamp = this.styleTimestamp(timestamp, styles.timestamp);
981
- result.level = this.styleLevel(level, styles.level);
982
- result.prefix = this.stylePrefix(prefix, styles.prefix);
983
- result.message = this.styleMessage(message, styles.message);
984
- result.location = this.styleLocation(location, styles.location);
982
+ if (styles$2) {
983
+ result.timestamp = this.styleTimestamp(timestamp, styles$2.timestamp);
984
+ result.level = this.styleLevel(level$1, styles$2.level);
985
+ result.prefix = this.stylePrefix(prefix, styles$2.prefix);
986
+ result.message = this.styleMessage(message, styles$2.message);
987
+ result.location = this.styleLocation(location, styles$2.location);
985
988
  } else {
986
989
  result.timestamp = this.styleTimestamp(timestamp);
987
- result.level = this.styleLevel(level);
990
+ result.level = this.styleLevel(level$1);
988
991
  result.prefix = this.stylePrefix(prefix);
989
992
  result.message = this.styleMessage(message);
990
993
  result.location = this.styleLocation(location);
@@ -1010,9 +1013,9 @@ var TerminalRenderer = class {
1010
1013
  /**
1011
1014
  * Style level with appropriate colors and formatting
1012
1015
  */
1013
- styleLevel(level, style) {
1016
+ styleLevel(level$1, style) {
1014
1017
  if (!style?.show) return "";
1015
- const levelText = this.getLevelText(level);
1018
+ const levelText = this.getLevelText(level$1);
1016
1019
  const levelColors = {
1017
1020
  "debug": "magenta",
1018
1021
  "info": "blue",
@@ -1021,7 +1024,7 @@ var TerminalRenderer = class {
1021
1024
  "critical": "red"
1022
1025
  };
1023
1026
  if (this.colorCapability === "none") return `[${levelText}]`;
1024
- const color = levelColors[level] || "white";
1027
+ const color = levelColors[level$1] || "white";
1025
1028
  const colorCode = this.getColorCode(color);
1026
1029
  const boldStyle = this.getStyleCode(["bold"]);
1027
1030
  if (style?.style === "compact") return `${colorCode}[${levelText}]`;
@@ -1060,7 +1063,7 @@ var TerminalRenderer = class {
1060
1063
  /**
1061
1064
  * Get text representation of log level
1062
1065
  */
1063
- getLevelText(level) {
1066
+ getLevelText(level$1) {
1064
1067
  const levelMap = {
1065
1068
  "debug": "DEBUG",
1066
1069
  "info": "INFO",
@@ -1068,12 +1071,12 @@ var TerminalRenderer = class {
1068
1071
  "error": "ERROR",
1069
1072
  "critical": "CRITICAL"
1070
1073
  };
1071
- return levelMap[level] || String(level).toUpperCase();
1074
+ return levelMap[level$1] || String(level$1).toUpperCase();
1072
1075
  }
1073
1076
  /**
1074
1077
  * Create cyberpunk-style ANSI rendering with truecolor support
1075
1078
  */
1076
- renderCyberpunk(level, message, timestamp, prefix, location) {
1079
+ renderCyberpunk(level$1, message, timestamp, prefix, location) {
1077
1080
  const reset = ANSI.reset;
1078
1081
  const cyberpunkColors = {
1079
1082
  "debug": "#ff00ff",
@@ -1084,10 +1087,10 @@ var TerminalRenderer = class {
1084
1087
  };
1085
1088
  const parts = [];
1086
1089
  if (timestamp) parts.push(`${ANSI.dim}${timestamp}${reset}`);
1087
- const levelColor = this.getColorCode(cyberpunkColors[level] || "#ffffff");
1090
+ const levelColor = this.getColorCode(cyberpunkColors[level$1] || "#ffffff");
1088
1091
  const bgBlack = ANSI.bg.black;
1089
- const bold = level === "critical" ? ANSI.bold : "";
1090
- parts.push(`${bgBlack}${levelColor}${bold} ${this.getLevelText(level)} ${reset}`);
1092
+ const bold = level$1 === "critical" ? ANSI.bold : "";
1093
+ parts.push(`${bgBlack}${levelColor}${bold} ${this.getLevelText(level$1)} ${reset}`);
1091
1094
  if (prefix) {
1092
1095
  const cyanColor = this.getColorCode("#00ffff");
1093
1096
  parts.push(`${bgBlack}${cyanColor}[${prefix.toUpperCase()}]${reset}`);
@@ -1102,7 +1105,7 @@ var TerminalRenderer = class {
1102
1105
  /**
1103
1106
  * Create minimal ANSI rendering with truecolor support
1104
1107
  */
1105
- renderMinimal(level, message, timestamp, prefix) {
1108
+ renderMinimal(level$1, message, timestamp, prefix) {
1106
1109
  const reset = ANSI.reset;
1107
1110
  const minimalColors = {
1108
1111
  "debug": "#c678dd",
@@ -1113,9 +1116,9 @@ var TerminalRenderer = class {
1113
1116
  };
1114
1117
  const parts = [];
1115
1118
  if (timestamp) parts.push(`${ANSI.dim}${timestamp}${reset}`);
1116
- const levelColor = this.getColorCode(minimalColors[level] || "#abb2bf");
1117
- const bold = level === "critical" ? ANSI.bold : "";
1118
- parts.push(`${levelColor}${bold}${this.getLevelText(level)}:${reset}`);
1119
+ const levelColor = this.getColorCode(minimalColors[level$1] || "#abb2bf");
1120
+ const bold = level$1 === "critical" ? ANSI.bold : "";
1121
+ parts.push(`${levelColor}${bold}${this.getLevelText(level$1)}:${reset}`);
1119
1122
  if (prefix) {
1120
1123
  const cyanColor = this.getColorCode("#56b6c2");
1121
1124
  parts.push(`${cyanColor}[${prefix.toUpperCase()}]${reset}`);
@@ -1129,7 +1132,7 @@ var TerminalRenderer = class {
1129
1132
  /**
1130
1133
  * Get chalk-like interface for log level with truecolor support
1131
1134
  */
1132
- getChalkForLevel(level) {
1135
+ getChalkForLevel(level$1) {
1133
1136
  const levelColors = {
1134
1137
  "debug": "#c678dd",
1135
1138
  "info": "#61afef",
@@ -1140,7 +1143,7 @@ var TerminalRenderer = class {
1140
1143
  const reset = ANSI.reset;
1141
1144
  return {
1142
1145
  color: (text) => {
1143
- const color = levelColors[level] || "#abb2bf";
1146
+ const color = levelColors[level$1] || "#abb2bf";
1144
1147
  const colorCode = this.getColorCode(color);
1145
1148
  return `${colorCode}${text}${reset}`;
1146
1149
  },
@@ -1175,28 +1178,28 @@ var CSS2ANSIAdapter = class {
1175
1178
  /**
1176
1179
  * Convert LogStyles to ANSIStyle for terminal rendering
1177
1180
  */
1178
- adaptStyles(level, message, timestamp, prefix, location, styles, presetName) {
1181
+ adaptStyles(level$1, message, timestamp, prefix, location, styles$2, presetName) {
1179
1182
  if (presetName) switch (presetName) {
1180
- case "cyberpunk": return this.renderer.renderCyberpunk(level, message, timestamp, prefix, location);
1181
- case "minimal": return this.renderer.renderMinimal(level, message, timestamp, prefix);
1182
- case "production": return this.adaptProductionStyles(level, message, timestamp, prefix, location, styles);
1183
- case "debug": return this.adaptDebugStyles(level, message, timestamp, prefix, location, styles);
1184
- case "glassmorphism": return this.adaptGlassmorphismStyles(level, message, timestamp, prefix, location, styles);
1183
+ case "cyberpunk": return this.renderer.renderCyberpunk(level$1, message, timestamp, prefix, location);
1184
+ case "minimal": return this.renderer.renderMinimal(level$1, message, timestamp, prefix);
1185
+ case "production": return this.adaptProductionStyles(level$1, message, timestamp, prefix, location, styles$2);
1186
+ case "debug": return this.adaptDebugStyles(level$1, message, timestamp, prefix, location, styles$2);
1187
+ case "glassmorphism": return this.adaptGlassmorphismStyles(level$1, message, timestamp, prefix, location, styles$2);
1185
1188
  }
1186
- return this.renderer.renderTerminal(level, message, timestamp, prefix, location, styles);
1189
+ return this.renderer.renderTerminal(level$1, message, timestamp, prefix, location, styles$2);
1187
1190
  }
1188
1191
  /**
1189
1192
  * Adapt production preset for terminal
1190
1193
  */
1191
- adaptProductionStyles(level, message, timestamp, prefix, location, styles) {
1194
+ adaptProductionStyles(level$1, message, timestamp, prefix, location, styles$2) {
1192
1195
  const reset = "\x1B[0m";
1193
- const levelChalk = this.renderer.getChalkForLevel(level);
1196
+ const levelChalk = this.renderer.getChalkForLevel(level$1);
1194
1197
  const parts = [];
1195
- if (timestamp && styles?.timestamp?.show) parts.push(levelChalk.dim(timestamp));
1196
- if (styles?.level?.show) parts.push(levelChalk.color(`[${this.renderer["getLevelText"](level)}]`));
1197
- if (prefix && styles?.prefix?.show) parts.push(levelChalk.dim(`[${prefix}]`));
1198
- if (message && styles?.message?.show) parts.push(levelChalk.reset(message));
1199
- if (location && styles?.location?.show) parts.push(levelChalk.dim(`(${location})`));
1198
+ if (timestamp && styles$2?.timestamp?.show) parts.push(levelChalk.dim(timestamp));
1199
+ if (styles$2?.level?.show) parts.push(levelChalk.color(`[${this.renderer["getLevelText"](level$1)}]`));
1200
+ if (prefix && styles$2?.prefix?.show) parts.push(levelChalk.dim(`[${prefix}]`));
1201
+ if (message && styles$2?.message?.show) parts.push(levelChalk.reset(message));
1202
+ if (location && styles$2?.location?.show) parts.push(levelChalk.dim(`(${location})`));
1200
1203
  return {
1201
1204
  text: parts.join(" ") + reset,
1202
1205
  reset
@@ -1205,17 +1208,17 @@ var CSS2ANSIAdapter = class {
1205
1208
  /**
1206
1209
  * Adapt debug preset for terminal
1207
1210
  */
1208
- adaptDebugStyles(level, message, timestamp, prefix, location, styles) {
1211
+ adaptDebugStyles(level$1, message, timestamp, prefix, location, styles$2) {
1209
1212
  const reset = "\x1B[0m";
1210
- const levelChalk = this.renderer.getChalkForLevel(level);
1213
+ const levelChalk = this.renderer.getChalkForLevel(level$1);
1211
1214
  const parts = [];
1212
- if (timestamp && styles?.timestamp?.show) parts.push(levelChalk.dim(timestamp));
1213
- if (styles?.level?.show) if (styles?.level?.style === "compact") parts.push(levelChalk.color(`[${this.renderer["getLevelText"](level)}]`));
1214
- else parts.push(levelChalk.bold(`[${this.renderer["getLevelText"](level)}]`));
1215
- if (prefix && styles?.prefix?.show) if (styles?.prefix?.style === "compact") parts.push(levelChalk.cyan.dim(`[${prefix}]`));
1215
+ if (timestamp && styles$2?.timestamp?.show) parts.push(levelChalk.dim(timestamp));
1216
+ if (styles$2?.level?.show) if (styles$2?.level?.style === "compact") parts.push(levelChalk.color(`[${this.renderer["getLevelText"](level$1)}]`));
1217
+ else parts.push(levelChalk.bold(`[${this.renderer["getLevelText"](level$1)}]`));
1218
+ if (prefix && styles$2?.prefix?.show) if (styles$2?.prefix?.style === "compact") parts.push(levelChalk.cyan.dim(`[${prefix}]`));
1216
1219
  else parts.push(levelChalk.cyan.bold(`[${prefix}]`));
1217
- if (message && styles?.message?.show) parts.push(levelChalk.reset(message));
1218
- if (location && styles?.location?.show) if (styles?.location?.style === "clickable") parts.push(levelChalk.dim(`${location} (clickable)`));
1220
+ if (message && styles$2?.message?.show) parts.push(levelChalk.reset(message));
1221
+ if (location && styles$2?.location?.show) if (styles$2?.location?.style === "clickable") parts.push(levelChalk.dim(`${location} (clickable)`));
1219
1222
  else parts.push(levelChalk.dim(`(${location})`));
1220
1223
  return {
1221
1224
  text: parts.join(" ") + reset,
@@ -1225,15 +1228,15 @@ var CSS2ANSIAdapter = class {
1225
1228
  /**
1226
1229
  * Adapt glassmorphism preset for terminal
1227
1230
  */
1228
- adaptGlassmorphismStyles(level, message, timestamp, prefix, location, styles) {
1231
+ adaptGlassmorphismStyles(level$1, message, timestamp, prefix, location, styles$2) {
1229
1232
  const reset = "\x1B[0m";
1230
- const levelChalk = this.renderer.getChalkForLevel(level);
1233
+ const levelChalk = this.renderer.getChalkForLevel(level$1);
1231
1234
  const parts = [];
1232
- if (timestamp && styles?.timestamp?.show) parts.push(levelChalk.dim(timestamp));
1233
- if (styles?.level?.show) parts.push(levelChalk.bgGray(` ${this.renderer["getLevelText"](level)} `));
1234
- if (prefix && styles?.prefix?.show) parts.push(levelChalk.bgBlue(`[${prefix}]`));
1235
- if (message && styles?.message?.show) parts.push(levelChalk.reset(message));
1236
- if (location && styles?.location?.show) parts.push(levelChalk.dim(`(${location})`));
1235
+ if (timestamp && styles$2?.timestamp?.show) parts.push(levelChalk.dim(timestamp));
1236
+ if (styles$2?.level?.show) parts.push(levelChalk.bgGray(` ${this.renderer["getLevelText"](level$1)} `));
1237
+ if (prefix && styles$2?.prefix?.show) parts.push(levelChalk.bgBlue(`[${prefix}]`));
1238
+ if (message && styles$2?.message?.show) parts.push(levelChalk.reset(message));
1239
+ if (location && styles$2?.location?.show) parts.push(levelChalk.dim(`(${location})`));
1237
1240
  return {
1238
1241
  text: parts.join(" ") + reset,
1239
1242
  reset
@@ -1284,9 +1287,9 @@ var CSS2ANSIAdapter = class {
1284
1287
  /**
1285
1288
  * Check if a style should be rendered in terminal
1286
1289
  */
1287
- shouldRenderStyle(styleType, styles) {
1288
- if (!styles) return true;
1289
- const styleConfig = styles[styleType];
1290
+ shouldRenderStyle(styleType, styles$2) {
1291
+ if (!styles$2) return true;
1292
+ const styleConfig = styles$2[styleType];
1290
1293
  return styleConfig?.show !== false;
1291
1294
  }
1292
1295
  /**
@@ -1297,8 +1300,8 @@ var CSS2ANSIAdapter = class {
1297
1300
  }
1298
1301
  };
1299
1302
  const css2ansiAdapter = new CSS2ANSIAdapter();
1300
- function adaptToTerminal(level, message, timestamp, prefix, location, styles, presetName) {
1301
- return css2ansiAdapter.adaptStyles(level, message, timestamp, prefix, location, styles, presetName);
1303
+ function adaptToTerminal(level$1, message, timestamp, prefix, location, styles$2, presetName) {
1304
+ return css2ansiAdapter.adaptStyles(level$1, message, timestamp, prefix, location, styles$2, presetName);
1302
1305
  }
1303
1306
  function detectDevToolsTheme() {
1304
1307
  try {
@@ -1310,9 +1313,9 @@ function detectDevToolsTheme() {
1310
1313
  return "light";
1311
1314
  }
1312
1315
  }
1313
- function getAdaptiveColor(colors, theme) {
1316
+ function getAdaptiveColor(colors$2, theme) {
1314
1317
  const currentTheme = theme ?? detectDevToolsTheme();
1315
- return colors[currentTheme];
1318
+ return colors$2[currentTheme];
1316
1319
  }
1317
1320
  function setupThemeChangeListener(callback) {
1318
1321
  try {
@@ -1334,11 +1337,11 @@ function setupThemeChangeListener(callback) {
1334
1337
  return null;
1335
1338
  }
1336
1339
  }
1337
- function createStyledOutput(level, levelStyles, prefix, message, stackInfo, autoDetectTheme = true, presetStyles, presetName) {
1338
- const levelConfig = levelStyles[level];
1340
+ function createStyledOutput(level$1, levelStyles, prefix, message, stackInfo, autoDetectTheme = true, presetStyles, presetName) {
1341
+ const levelConfig = levelStyles[level$1];
1339
1342
  const timestamp = formatTimestamp();
1340
1343
  const environment = getEnvironment();
1341
- if (environment !== "browser" && supportsANSI()) return createTerminalOutput(level, message, timestamp, prefix, stackInfo, presetStyles, presetName);
1344
+ if (environment !== "browser" && supportsANSI()) return createTerminalOutput(level$1, message, timestamp, prefix, stackInfo, presetStyles, presetName);
1342
1345
  const currentTheme = autoDetectTheme ? detectDevToolsTheme() : "light";
1343
1346
  const timestampStyle = new StyleBuilder().color(getAdaptiveColor(ADAPTIVE_COLORS.timestamp, currentTheme)).size("11px").font("Monaco, Consolas, monospace").build();
1344
1347
  const levelStyle = new StyleBuilder().bg(levelConfig.background).color(levelConfig.color).border(levelConfig.border).shadow(levelConfig.shadow).padding("2px 8px").rounded("4px").bold().font("Monaco, Consolas, monospace").size("12px").build();
@@ -1346,18 +1349,18 @@ function createStyledOutput(level, levelStyles, prefix, message, stackInfo, auto
1346
1349
  const messageStyle = new StyleBuilder().color(getAdaptiveColor(ADAPTIVE_COLORS.messageText, currentTheme)).font("system-ui, -apple-system, sans-serif").size("14px").build();
1347
1350
  const locationStyle = new StyleBuilder().color(getAdaptiveColor(ADAPTIVE_COLORS.location, currentTheme)).size("11px").font("Monaco, Consolas, monospace").build();
1348
1351
  let format = `%c${timestamp.slice(11, 23)} %c${levelConfig.emoji} ${levelConfig.label}`;
1349
- const styles = [timestampStyle, levelStyle];
1352
+ const styles$2 = [timestampStyle, levelStyle];
1350
1353
  if (prefix) {
1351
1354
  format += ` %c${prefix}`;
1352
- styles.push(prefixStyle);
1355
+ styles$2.push(prefixStyle);
1353
1356
  }
1354
1357
  format += ` %c${message}`;
1355
- styles.push(messageStyle);
1358
+ styles$2.push(messageStyle);
1356
1359
  if (stackInfo) {
1357
1360
  format += ` %c(${stackInfo.file}:${stackInfo.line}:${stackInfo.column})`;
1358
- styles.push(locationStyle);
1361
+ styles$2.push(locationStyle);
1359
1362
  }
1360
- return [format, ...styles];
1363
+ return [format, ...styles$2];
1361
1364
  }
1362
1365
  function generateLogId() {
1363
1366
  return `${Date.now()}-${Math.random().toString(36).substr(2, 9)}`;
@@ -1380,9 +1383,9 @@ function safeStringify(obj, _maxDepth = 3) {
1380
1383
  return String(obj);
1381
1384
  }
1382
1385
  }
1383
- function createTerminalOutput(level, message, timestamp, prefix, stackInfo, presetStyles, presetName) {
1386
+ function createTerminalOutput(level$1, message, timestamp, prefix, stackInfo, presetStyles, presetName) {
1384
1387
  const location = stackInfo ? `${stackInfo.file}:${stackInfo.line}:${stackInfo.column}` : void 0;
1385
- const ansiStyle = adaptToTerminal(level, message, timestamp, prefix, location, presetStyles, presetName);
1388
+ const ansiStyle = adaptToTerminal(level$1, message, timestamp, prefix, location, presetStyles, presetName);
1386
1389
  return [ansiStyle.text];
1387
1390
  }
1388
1391
  const isNode = typeof process !== "undefined" && process.versions && process.versions.node;
@@ -1419,9 +1422,9 @@ var SerializerRegistry = class {
1419
1422
  pattern: regex.source,
1420
1423
  flags: regex.flags
1421
1424
  }), 90);
1422
- this.add(Map, (map, ctx) => {
1425
+ this.add(Map, (map$1, ctx) => {
1423
1426
  const obj = {};
1424
- map.forEach((value, key) => {
1427
+ map$1.forEach((value, key) => {
1425
1428
  const keyStr = typeof key === "object" ? JSON.stringify(key) : String(key);
1426
1429
  obj[keyStr] = this.serializeInternal(value, {
1427
1430
  ...ctx,
@@ -1649,7 +1652,7 @@ var TransportManager = class {
1649
1652
  }
1650
1653
  add(target) {
1651
1654
  const id = generateTransportId();
1652
- const level = target.level || this.defaultLevel;
1655
+ const level$1 = target.level || this.defaultLevel;
1653
1656
  let transport;
1654
1657
  if (typeof target.target === "string") throw new Error(`String transport targets not supported. Use inline transport object.`);
1655
1658
  else transport = target.target;
@@ -1657,8 +1660,8 @@ var TransportManager = class {
1657
1660
  id,
1658
1661
  transport,
1659
1662
  options: target.options || {},
1660
- level,
1661
- levelValue: LOG_LEVELS[level]
1663
+ level: level$1,
1664
+ levelValue: LOG_LEVELS[level$1]
1662
1665
  };
1663
1666
  this.transports.set(id, entry);
1664
1667
  return id;
@@ -2516,10 +2519,10 @@ var LogStyleBuilder = class {
2516
2519
  /**
2517
2520
  * Internal method to update part configuration
2518
2521
  */
2519
- _updatePartConfig(part, styles) {
2522
+ _updatePartConfig(part, styles$2) {
2520
2523
  if (part === "layout" || part === "backdrop" || part === "transparency") return;
2521
2524
  if (!this.logStyles[part]) this.logStyles[part] = {};
2522
- this.logStyles[part].style = styles;
2525
+ this.logStyles[part].style = styles$2;
2523
2526
  }
2524
2527
  };
2525
2528
  var PartStyleBuilderProxy = class {
@@ -2545,8 +2548,8 @@ var PartStyleBuilderProxy = class {
2545
2548
  * Helper to apply styles to the parent builder
2546
2549
  */
2547
2550
  applyStyles(styler) {
2548
- const styles = styler.build();
2549
- this.parentBuilder._updatePartConfig(this.partName, styles);
2551
+ const styles$2 = styler.build();
2552
+ this.parentBuilder._updatePartConfig(this.partName, styles$2);
2550
2553
  return this;
2551
2554
  }
2552
2555
  };
@@ -3090,11 +3093,11 @@ var ExportLogHandler = class {
3090
3093
  /**
3091
3094
  * Handle incoming log and store in buffer
3092
3095
  */
3093
- handle(level, message, args, metadata) {
3096
+ handle(level$1, message, args, metadata) {
3094
3097
  const entry = {
3095
3098
  id: generateLogId(),
3096
3099
  timestamp: metadata.timestamp,
3097
- level,
3100
+ level: level$1,
3098
3101
  prefix: metadata.prefix,
3099
3102
  message,
3100
3103
  args,
@@ -3254,15 +3257,15 @@ var ExportLogHandler = class {
3254
3257
  }
3255
3258
  if (options.groupBy === "level") {
3256
3259
  const grouped = logs.reduce((acc, entry) => {
3257
- const level = entry.level;
3258
- if (!acc[level]) acc[level] = [];
3259
- const levelArray = acc[level];
3260
+ const level$1 = entry.level;
3261
+ if (!acc[level$1]) acc[level$1] = [];
3262
+ const levelArray = acc[level$1];
3260
3263
  if (levelArray) levelArray.push(entry);
3261
3264
  return acc;
3262
3265
  }, {});
3263
- Object.entries(grouped).forEach(([level, entries]) => {
3264
- const emoji = this.getLevelEmoji(level);
3265
- content += `## ${emoji} ${level.toUpperCase()} (${entries.length})
3266
+ Object.entries(grouped).forEach(([level$1, entries]) => {
3267
+ const emoji = this.getLevelEmoji(level$1);
3268
+ content += `## ${emoji} ${level$1.toUpperCase()} (${entries.length})
3266
3269
 
3267
3270
  `;
3268
3271
  entries.forEach((entry) => {
@@ -3293,10 +3296,10 @@ var ExportLogHandler = class {
3293
3296
  exportPlain(logs, options) {
3294
3297
  return logs.map((entry) => {
3295
3298
  const time = formatDisplayTime(new Date(entry.timestamp), options.minimal ? "time-only" : "short");
3296
- const level = entry.level.toUpperCase().padEnd(8);
3299
+ const level$1 = entry.level.toUpperCase().padEnd(8);
3297
3300
  const prefix = entry.prefix ? `[${entry.prefix}] ` : "";
3298
3301
  const location = !options.minimal && entry.location ? ` (${entry.location.file}:${entry.location.line})` : "";
3299
- return `${time} ${level} ${prefix}${entry.message}${location}`;
3302
+ return `${time} ${level$1} ${prefix}${entry.message}${location}`;
3300
3303
  }).join("\n");
3301
3304
  }
3302
3305
  /**
@@ -3358,7 +3361,7 @@ var ExportLogHandler = class {
3358
3361
  /**
3359
3362
  * Get emoji for log level
3360
3363
  */
3361
- getLevelEmoji(level) {
3364
+ getLevelEmoji(level$1) {
3362
3365
  const emojis = {
3363
3366
  debug: "🐞",
3364
3367
  info: "ℹ️",
@@ -3366,7 +3369,7 @@ var ExportLogHandler = class {
3366
3369
  error: "❌",
3367
3370
  critical: "🔥"
3368
3371
  };
3369
- return emojis[level] || "";
3372
+ return emojis[level$1] || "";
3370
3373
  }
3371
3374
  /**
3372
3375
  * Main export function
@@ -4431,8 +4434,8 @@ var Logger = class {
4431
4434
  *
4432
4435
  * @since 0.3.0
4433
4436
  */
4434
- setVerbosity(level) {
4435
- this.config.verbosity = level;
4437
+ setVerbosity(level$1) {
4438
+ this.config.verbosity = level$1;
4436
4439
  }
4437
4440
  /**
4438
4441
  * Establece el tema del logger
@@ -4948,7 +4951,7 @@ var Logger = class {
4948
4951
  * @param {LogLevel} level - Nivel de log a verificar
4949
4952
  * @returns {boolean} True si debe mostrarse, false si no
4950
4953
  */
4951
- shouldLog(level) {
4954
+ shouldLog(level$1) {
4952
4955
  if (this.config.verbosity === "silent") return false;
4953
4956
  const levels = {
4954
4957
  debug: 0,
@@ -4957,7 +4960,7 @@ var Logger = class {
4957
4960
  error: 3,
4958
4961
  critical: 4
4959
4962
  };
4960
- return levels[level] >= levels[this.config.verbosity];
4963
+ return levels[level$1] >= levels[this.config.verbosity];
4961
4964
  }
4962
4965
  /**
4963
4966
  * Obtiene el prefijo efectivo (global + scope)
@@ -4974,8 +4977,8 @@ var Logger = class {
4974
4977
  * @param {LogLevel} level - Nivel del log
4975
4978
  * @param {...any} args - Argumentos a loggear
4976
4979
  */
4977
- log(level, ...args) {
4978
- if (!this.shouldLog(level)) return;
4980
+ log(level$1, ...args) {
4981
+ if (!this.shouldLog(level$1)) return;
4979
4982
  const stackInfo = this.config.enableStackTrace ? parseStackTrace() : null;
4980
4983
  const prefix = this.getEffectivePrefix();
4981
4984
  const timestamp = formatTimestamp();
@@ -4987,7 +4990,7 @@ var Logger = class {
4987
4990
  }
4988
4991
  const additionalArgs = serializedArgs.slice(1);
4989
4992
  let hookEntry = {
4990
- level,
4993
+ level: level$1,
4991
4994
  message,
4992
4995
  args: serializedArgs,
4993
4996
  timestamp,
@@ -4997,20 +5000,20 @@ var Logger = class {
4997
5000
  this.hookManager.emit("beforeLog", hookEntry).then((processed) => {
4998
5001
  message = processed.message;
4999
5002
  }).catch(() => {});
5000
- const [format, ...styles2] = createStyledOutput(level, LEVEL_STYLES, prefix, message, this.displaySettings.showLocation ? stackInfo : null, this.config.autoDetectTheme, this._activePreset, this._activePresetName);
5003
+ const [format, ...styles2] = createStyledOutput(level$1, LEVEL_STYLES, prefix, message, this.displaySettings.showLocation ? stackInfo : null, this.config.autoDetectTheme, this._activePreset, this._activePresetName);
5001
5004
  const groupIndent = " ".repeat(this.groupDepth);
5002
5005
  const finalFormat = groupIndent + format;
5003
- this.writeOutput(finalFormat, level, styles2, additionalArgs);
5006
+ this.writeOutput(finalFormat, level$1, styles2, additionalArgs);
5004
5007
  if (this.exportHandler) this.exportHandler.setGroupInfo(this.groupDepth);
5005
5008
  const metadata = {
5006
5009
  timestamp,
5007
- level,
5010
+ level: level$1,
5008
5011
  prefix,
5009
5012
  stackInfo: stackInfo ? stackInfo : void 0
5010
5013
  };
5011
5014
  this.handlers.forEach((handler) => {
5012
5015
  try {
5013
- handler.handle(level, message, serializedArgs, metadata);
5016
+ handler.handle(level$1, message, serializedArgs, metadata);
5014
5017
  } catch (error2) {
5015
5018
  console.error("Log handler failed:", error2);
5016
5019
  }
@@ -5024,8 +5027,8 @@ var Logger = class {
5024
5027
  critical: 4
5025
5028
  };
5026
5029
  const record = {
5027
- level,
5028
- levelValue: levelValues[level],
5030
+ level: level$1,
5031
+ levelValue: levelValues[level$1],
5029
5032
  time: Date.now(),
5030
5033
  msg: message,
5031
5034
  prefix,
@@ -5040,14 +5043,14 @@ var Logger = class {
5040
5043
  }
5041
5044
  this.hookManager.emit("afterLog", hookEntry).catch(() => {});
5042
5045
  }
5043
- logWithBindings(bindings, level, ...args) {
5044
- if (!this.shouldLog(level)) return;
5046
+ logWithBindings(bindings, level$1, ...args) {
5047
+ if (!this.shouldLog(level$1)) return;
5045
5048
  let prefix = "";
5046
5049
  const colorCapability = getColorCapability();
5047
5050
  if (bindings.badges?.length) prefix += bindings.badges.map((b) => formatBadge(b, "pill", colorCapability, "#00ff88")).join(" ") + " ";
5048
5051
  if (bindings.scope) prefix += formatBadge(bindings.scope, "pill", colorCapability, "#00ffff") + " ";
5049
5052
  if (prefix && args.length > 0) args[0] = prefix + String(args[0]);
5050
- this.log(level, ...args);
5053
+ this.log(level$1, ...args);
5051
5054
  }
5052
5055
  debug(...args) {
5053
5056
  this.log("debug", ...args);
@@ -5407,12 +5410,12 @@ var Logger = class {
5407
5410
  * @param {any[]} additionalArgs - Additional arguments to log
5408
5411
  * @since 4.0.0
5409
5412
  */
5410
- writeOutput(message, level, styles2, additionalArgs) {
5413
+ writeOutput(message, level$1, styles2, additionalArgs) {
5411
5414
  const mode = this.config.outputMode ?? "console";
5412
5415
  if (mode === "silent") return;
5413
5416
  if (mode === "custom" && this.config.outputWriter) {
5414
5417
  const fullMessage = additionalArgs.length > 0 ? `${message} ${additionalArgs.map((a) => String(a)).join(" ")}` : message;
5415
- this.config.outputWriter.write(fullMessage, level, styles2);
5418
+ this.config.outputWriter.write(fullMessage, level$1, styles2);
5416
5419
  return;
5417
5420
  }
5418
5421
  if (additionalArgs.length > 0) console.log(message, ...styles2, ...additionalArgs);
@@ -5577,6 +5580,7 @@ async function loadConfig() {
5577
5580
  return err(error instanceof Error ? error : new Error(String(error)));
5578
5581
  }
5579
5582
  }
5583
+ const SETTINGS_CACHE_FILE = (0, node_path.join)(CONFIG_DIR, "app-settings-cache.json");
5580
5584
 
5581
5585
  //#endregion
5582
5586
  //#region src/coolify/index.ts
@@ -5672,12 +5676,20 @@ var CoolifyService = class {
5672
5676
  let data;
5673
5677
  try {
5674
5678
  data = text ? JSON.parse(text) : void 0;
5675
- } catch {
5679
+ } catch (parseErr) {
5680
+ const preview = text ? text.slice(0, 200) : "(empty body)";
5681
+ const method = options.method ?? "GET";
5682
+ log.warn(`Failed to parse JSON response from ${method} ${endpoint} (status ${response.status}): ${parseErr instanceof Error ? parseErr.message : String(parseErr)}. Body preview: ${preview}`);
5676
5683
  if (!response.ok) return {
5677
5684
  error: text || `HTTP ${response.status}`,
5678
5685
  status: response.status,
5679
5686
  durationMs
5680
5687
  };
5688
+ return {
5689
+ error: `Response was not valid JSON (status ${response.status}): ${preview}`,
5690
+ status: response.status,
5691
+ durationMs
5692
+ };
5681
5693
  }
5682
5694
  if (!response.ok) {
5683
5695
  const parsed = data;
@@ -5771,8 +5783,8 @@ var CoolifyService = class {
5771
5783
  "private-github-app": "/applications/private-github-app",
5772
5784
  "private-deploy-key": "/applications/private-deploy-key",
5773
5785
  dockerfile: "/applications/dockerfile",
5774
- "docker-image": "/applications/docker-image",
5775
- "docker-compose": "/applications/docker-compose",
5786
+ "docker-image": "/applications/dockerimage",
5787
+ "docker-compose": "/applications/dockercompose",
5776
5788
  dockerimage: "/applications/dockerimage",
5777
5789
  dockercompose: "/applications/dockercompose"
5778
5790
  };
@@ -5782,19 +5794,30 @@ var CoolifyService = class {
5782
5794
  description: options.description,
5783
5795
  project_uuid: options.projectUuid,
5784
5796
  environment_uuid: options.environmentUuid,
5797
+ environment_name: options.environmentName,
5785
5798
  server_uuid: options.serverUuid
5786
5799
  };
5800
+ if (options.githubRepoUrl) body.git_repository = options.githubRepoUrl;
5787
5801
  if (appType === "public" || appType === "private-github-app" || appType === "private-deploy-key") {
5788
- if (options.githubRepoUrl) body.git_repository = options.githubRepoUrl.replace(/^https?:\/\/github\.com\//, "").replace(/\.git$/, "");
5789
5802
  if (options.githubAppUuid) body.github_app_uuid = options.githubAppUuid;
5803
+ if (appType === "private-deploy-key" && options.privateKeyUuid) body.private_key_uuid = options.privateKeyUuid;
5790
5804
  body.git_branch = options.branch || "main";
5791
5805
  body.build_pack = options.buildPack || "dockerfile";
5792
5806
  if (options.portsExposes) body.ports_exposes = options.portsExposes;
5793
- if (options.dockerfileLocation) body.dockerfile_location = options.dockerfileLocation;
5794
- if (options.dockerComposeLocation) body.docker_compose_location = options.dockerComposeLocation;
5795
- if (options.baseDirectory) body.base_directory = options.baseDirectory;
5796
- } else if (appType === "docker-image" && options.dockerImage) body.docker_image = options.dockerImage;
5797
- else if (appType === "docker-compose" && options.dockerCompose) body.docker_compose = options.dockerCompose;
5807
+ if (options.dockerfileLocation) {
5808
+ const p = options.dockerfileLocation;
5809
+ body.dockerfile_location = p.startsWith("/") ? p : `/${p}`;
5810
+ }
5811
+ if (options.dockerComposeLocation) {
5812
+ const p = options.dockerComposeLocation;
5813
+ body.docker_compose_location = p.startsWith("/") ? p : `/${p}`;
5814
+ }
5815
+ if (options.baseDirectory) {
5816
+ const p = options.baseDirectory;
5817
+ body.base_directory = p.startsWith("/") ? p : `/${p}`;
5818
+ }
5819
+ } else if (appType === "docker-image" && options.dockerImage) body.docker_registry_image_name = options.dockerImage;
5820
+ else if (appType === "docker-compose" && options.dockerCompose) body.docker_compose_raw = options.dockerCompose;
5798
5821
  log.debug(`Create application body: ${JSON.stringify(body, null, 2)}`);
5799
5822
  log.debug(`Endpoint: POST ${endpoint}`);
5800
5823
  const result = await this.request(endpoint, {
@@ -5815,49 +5838,30 @@ var CoolifyService = class {
5815
5838
  /**
5816
5839
  * Sets environment variables for an application.
5817
5840
  *
5841
+ * Delegates to {@link bulkUpdateEnvironmentVariables} so the same
5842
+ * create-or-update logic applies. This fixes the post-delete scenario
5843
+ * (where the variable was deleted via the API and only its base value
5844
+ * from docker-compose/git remains visible) and prevents duplicates
5845
+ * that the singular POST endpoint would create when called for a key
5846
+ * that already exists. Also eliminates the N+1 API calls and the
5847
+ * TOCTOU race between the DELETE and the re-POST that the previous
5848
+ * per-key POST -> DELETE -> re-POST dance had.
5849
+ *
5818
5850
  * @param appUuid - Application UUID
5819
5851
  * @param envVars - Environment variables to set
5820
5852
  * @returns Result indicating success or error
5821
5853
  */
5822
5854
  async setEnvironmentVariables(appUuid, envVars) {
5823
5855
  log.info(`Setting ${Object.keys(envVars).length} environment variables for ${appUuid}`);
5824
- for (const [key, value] of Object.entries(envVars)) {
5825
- const result = await this.request(`/applications/${appUuid}/envs`, {
5826
- method: "POST",
5827
- body: JSON.stringify({
5828
- key,
5829
- value,
5830
- is_preview: false
5831
- })
5832
- });
5833
- if (result.error && result.error.includes("already exists")) {
5834
- const listResult = await this.request(`/applications/${appUuid}/envs`);
5835
- const existing = listResult.data?.find((v) => v.key === key);
5836
- if (existing) {
5837
- await this.request(`/applications/${appUuid}/envs/${existing.uuid}`, { method: "DELETE" });
5838
- const repost = await this.request(`/applications/${appUuid}/envs`, {
5839
- method: "POST",
5840
- body: JSON.stringify({
5841
- key,
5842
- value,
5843
- is_preview: false
5844
- })
5845
- });
5846
- if (repost.error) {
5847
- log.error(`Failed to update env var ${key}: ${repost.error}`);
5848
- return err(new Error(`Failed to update ${key}: ${repost.error}`));
5849
- }
5850
- log.debug(`Updated existing env var: ${key}`);
5851
- } else {
5852
- log.error(`Failed to set env var ${key}: ${result.error}`);
5853
- return err(new Error(`Failed to set ${key}: ${result.error}`));
5854
- }
5855
- } else if (result.error) {
5856
- log.error(`Failed to set env var ${key}: ${result.error}`);
5857
- return err(new Error(`Failed to set ${key}: ${result.error}`));
5858
- }
5859
- }
5860
- log.success(`${Object.keys(envVars).length} environment variables set`);
5856
+ const vars = Object.entries(envVars).map(([key, value]) => ({
5857
+ key,
5858
+ value,
5859
+ is_buildtime: false,
5860
+ is_runtime: true
5861
+ }));
5862
+ const result = await this.bulkUpdateEnvironmentVariables(appUuid, vars);
5863
+ if (isErr(result)) return err(result.error);
5864
+ log.success(`${vars.length} environment variables set`);
5861
5865
  return ok(void 0);
5862
5866
  }
5863
5867
  /**
@@ -5878,46 +5882,31 @@ var CoolifyService = class {
5878
5882
  }
5879
5883
  /**
5880
5884
  * Sets a single environment variable for an application.
5881
- * Uses PATCH if variable exists, POST if it doesn't.
5885
+ *
5886
+ * Delegates to {@link bulkUpdateEnvironmentVariables} so the same
5887
+ * create-or-update logic applies. This fixes the post-delete scenario
5888
+ * (where the variable was deleted via the API and only its base value
5889
+ * from docker-compose/git remains visible) and prevents duplicates
5890
+ * that the singular PATCH endpoint would create when called without
5891
+ * the variable's UUID.
5882
5892
  *
5883
5893
  * @param appUuid - Application UUID
5884
5894
  * @param key - Variable name
5885
5895
  * @param value - Variable value
5886
- * @param isBuildTime - Whether the variable is available at build time (only for new vars)
5896
+ * @param isBuildTime - Whether the variable is available at build time
5897
+ * (only for new vars; existing runtime-only vars will be flipped to
5898
+ * build-time and vice versa).
5887
5899
  * @returns Result indicating success or error
5888
5900
  */
5889
- async setEnvironmentVariable(appUuid, key, value, _isBuildTime = false) {
5890
- log.info(`Setting environment variable ${key} for ${appUuid}`);
5891
- const existingVars = await this.getEnvironmentVariables(appUuid);
5892
- if (isErr(existingVars)) return err(existingVars.error);
5893
- const exists = existingVars.value.some((ev) => ev.key === key);
5894
- if (exists) {
5895
- log.debug(`Variable ${key} exists, using PATCH to update`);
5896
- const result = await this.request(`/applications/${appUuid}/envs`, {
5897
- method: "PATCH",
5898
- body: JSON.stringify({
5899
- key,
5900
- value
5901
- })
5902
- });
5903
- if (result.error) {
5904
- log.error(`Failed to update env var: ${result.error}`);
5905
- return err(new Error(result.error));
5906
- }
5907
- } else {
5908
- log.debug(`Variable ${key} does not exist, using POST to create`);
5909
- const result = await this.request(`/applications/${appUuid}/envs`, {
5910
- method: "POST",
5911
- body: JSON.stringify({
5912
- key,
5913
- value
5914
- })
5915
- });
5916
- if (result.error) {
5917
- log.error(`Failed to create env var: ${result.error}`);
5918
- return err(new Error(result.error));
5919
- }
5920
- }
5901
+ async setEnvironmentVariable(appUuid, key, value, isBuildTime = false) {
5902
+ log.info(`Setting environment variable ${key} for ${appUuid} (buildtime: ${isBuildTime})`);
5903
+ const result = await this.bulkUpdateEnvironmentVariables(appUuid, [{
5904
+ key,
5905
+ value,
5906
+ is_buildtime: isBuildTime,
5907
+ is_runtime: !isBuildTime
5908
+ }]);
5909
+ if (isErr(result)) return err(result.error);
5921
5910
  log.success(`Environment variable ${key} set for ${appUuid}`);
5922
5911
  return ok(void 0);
5923
5912
  }
@@ -6007,6 +5996,27 @@ var CoolifyService = class {
6007
5996
  return ok(result.data || []);
6008
5997
  }
6009
5998
  /**
5999
+ * Lists all GitHub Apps configured in Coolify.
6000
+ * Fetches all pages internally and returns a flat list.
6001
+ *
6002
+ * @param perPage - Items per page for each request (default: 50)
6003
+ * @returns Result with all GitHub Apps or error
6004
+ */
6005
+ async listGithubAppsAll(perPage = 50) {
6006
+ const allApps = [];
6007
+ let page = 1;
6008
+ while (true) {
6009
+ const result = await this.listGithubApps(page, perPage);
6010
+ if (isErr(result)) return err(result.error);
6011
+ const apps = result.value;
6012
+ if (apps.length === 0) break;
6013
+ allApps.push(...apps);
6014
+ if (apps.length < perPage) break;
6015
+ page++;
6016
+ }
6017
+ return ok(allApps);
6018
+ }
6019
+ /**
6010
6020
  * Lists all projects.
6011
6021
  *
6012
6022
  * @param page - Optional page number for pagination
@@ -6165,8 +6175,19 @@ var CoolifyService = class {
6165
6175
  if (options.baseDirectory) body.base_directory = options.baseDirectory;
6166
6176
  if (options.domains) body.domains = options.domains;
6167
6177
  if (options.dockerComposeDomains) body.docker_compose_domains = options.dockerComposeDomains;
6178
+ if (options.dockerComposeRaw !== void 0) body.docker_compose_raw = options.dockerComposeRaw;
6168
6179
  if (options.isForceHttpsEnabled !== void 0) body.is_force_https_enabled = options.isForceHttpsEnabled;
6169
6180
  if (options.isAutoDeployEnabled !== void 0) body.is_auto_deploy_enabled = options.isAutoDeployEnabled;
6181
+ if (options.watchPaths !== void 0) body.watch_paths = options.watchPaths;
6182
+ if (options.healthCheckEnabled !== void 0) body.health_check_enabled = options.healthCheckEnabled;
6183
+ if (options.healthCheckPath) body.health_check_path = options.healthCheckPath;
6184
+ if (options.healthCheckPort) body.health_check_port = String(options.healthCheckPort);
6185
+ if (options.healthCheckMethod) body.health_check_method = options.healthCheckMethod;
6186
+ if (options.healthCheckInterval) body.health_check_interval = options.healthCheckInterval;
6187
+ if (options.healthCheckTimeout) body.health_check_timeout = options.healthCheckTimeout;
6188
+ if (options.healthCheckRetries) body.health_check_retries = options.healthCheckRetries;
6189
+ if (options.healthCheckStartPeriod) body.health_check_start_period = options.healthCheckStartPeriod;
6190
+ if (options.healthCheckReturnCode) body.health_check_return_code = options.healthCheckReturnCode;
6170
6191
  const result = await this.request(`/applications/${appUuid}`, {
6171
6192
  method: "PATCH",
6172
6193
  body: JSON.stringify(body)
@@ -6228,15 +6249,22 @@ var CoolifyService = class {
6228
6249
  /**
6229
6250
  * Bulk updates environment variables for an application.
6230
6251
  *
6252
+ * Uses the bulk endpoint `PATCH /applications/{appUuid}/envs/bulk` which
6253
+ * has create-or-update semantics: if the variable exists in the override
6254
+ * table, its value is updated; otherwise a new override is created. This
6255
+ * is the only reliable way to update a variable that has been deleted
6256
+ * (i.e. its base value from docker-compose/git is still visible in
6257
+ * `getEnvironmentVariables` but no override row exists).
6258
+ *
6231
6259
  * @param appUuid - Application UUID
6232
- * @param envVars - Array of { key, value, is_preview? } objects
6260
+ * @param envVars - Array of variable definitions to upsert
6233
6261
  * @returns Result indicating success or error
6234
6262
  */
6235
6263
  async bulkUpdateEnvironmentVariables(appUuid, envVars) {
6236
6264
  log.info(`Bulk updating ${envVars.length} env vars for ${appUuid}`);
6237
6265
  const result = await this.request(`/applications/${appUuid}/envs/bulk`, {
6238
6266
  method: "PATCH",
6239
- body: JSON.stringify(envVars)
6267
+ body: JSON.stringify({ data: envVars })
6240
6268
  });
6241
6269
  if (result.error) {
6242
6270
  log.error(`Failed to bulk update env vars: ${result.error}`);
@@ -6246,6 +6274,32 @@ var CoolifyService = class {
6246
6274
  return ok(result.data || { message: "Environment variables updated" });
6247
6275
  }
6248
6276
  /**
6277
+ * Bulk updates environment variables for a database.
6278
+ *
6279
+ * Uses the bulk endpoint `PATCH /databases/{databaseUuid}/envs/bulk` which
6280
+ * has create-or-update semantics. Note: the database schema is narrower
6281
+ * than applications — it accepts `key`, `value`, `is_literal`,
6282
+ * `is_multiline`, `is_shown_once` but does NOT accept `is_preview`,
6283
+ * `is_buildtime` or `is_runtime` (those flags are application-only).
6284
+ *
6285
+ * @param databaseUuid - Database UUID
6286
+ * @param envVars - Array of variable definitions to upsert
6287
+ * @returns Result indicating success or error
6288
+ */
6289
+ async bulkUpdateDatabaseEnvVars(databaseUuid, envVars) {
6290
+ log.info(`Bulk updating ${envVars.length} env vars for database ${databaseUuid}`);
6291
+ const result = await this.request(`/databases/${databaseUuid}/envs/bulk`, {
6292
+ method: "PATCH",
6293
+ body: JSON.stringify({ data: envVars })
6294
+ });
6295
+ if (result.error) {
6296
+ log.error(`Failed to bulk update database env vars: ${result.error}`);
6297
+ return err(new Error(result.error));
6298
+ }
6299
+ log.success(`Bulk updated ${envVars.length} env vars for database ${databaseUuid}`);
6300
+ return ok(result.data || { message: "Environment variables updated" });
6301
+ }
6302
+ /**
6249
6303
  * Gets deployment history for an application.
6250
6304
  *
6251
6305
  * @param appUuid - Application UUID
@@ -6625,6 +6679,125 @@ var CoolifyService = class {
6625
6679
  });
6626
6680
  }
6627
6681
  /**
6682
+ * Gets the full infrastructure tree: Projects → Environments → Resources.
6683
+ *
6684
+ * Fetches all projects, apps, databases, and services in parallel,
6685
+ * then groups them by environment_id into a hierarchical tree.
6686
+ *
6687
+ * @returns Result with the full infrastructure tree or error
6688
+ */
6689
+ async getInfrastructureTree() {
6690
+ log.info("Building infrastructure tree");
6691
+ const [projectsResult, appsResult, dbsResult, svcsResult, serversResult] = await Promise.all([
6692
+ this.listProjects(),
6693
+ this.listApplications(),
6694
+ this.listDatabases(),
6695
+ this.listServices(),
6696
+ this.listServers()
6697
+ ]);
6698
+ if (isErr(projectsResult)) return err(projectsResult.error);
6699
+ if (isErr(appsResult)) return err(appsResult.error);
6700
+ if (isErr(serversResult)) return err(serversResult.error);
6701
+ const projects = projectsResult.value;
6702
+ const apps = appsResult.value;
6703
+ const dbs = isErr(dbsResult) ? [] : dbsResult.value;
6704
+ const svcs = isErr(svcsResult) ? [] : svcsResult.value;
6705
+ const servers = serversResult.value;
6706
+ const envResults = await Promise.allSettled(projects.map((p) => this.getProjectEnvironments(p.uuid)));
6707
+ const envIdMap = new Map();
6708
+ for (let i = 0; i < projects.length; i++) {
6709
+ const envResult = envResults[i];
6710
+ if (envResult.status === "fulfilled" && !isErr(envResult.value)) for (const env$1 of envResult.value.value) envIdMap.set(env$1.id, {
6711
+ projectUuid: projects[i].uuid,
6712
+ envName: env$1.name,
6713
+ envUuid: env$1.uuid
6714
+ });
6715
+ }
6716
+ const projectNodes = projects.map((p) => ({
6717
+ uuid: p.uuid,
6718
+ name: p.name,
6719
+ description: p.description,
6720
+ environments: []
6721
+ }));
6722
+ const projectMap = new Map();
6723
+ for (const node of projectNodes) projectMap.set(node.uuid, node);
6724
+ const envNodeMap = new Map();
6725
+ for (const [envId, info$1] of envIdMap) {
6726
+ const project = projectMap.get(info$1.projectUuid);
6727
+ if (!project) continue;
6728
+ let envNode = project.environments.find((e) => e.id === envId);
6729
+ if (!envNode) {
6730
+ envNode = {
6731
+ id: envId,
6732
+ uuid: info$1.envUuid,
6733
+ name: info$1.envName,
6734
+ resources: []
6735
+ };
6736
+ project.environments.push(envNode);
6737
+ }
6738
+ envNodeMap.set(envId, envNode);
6739
+ }
6740
+ for (const app of apps) {
6741
+ const envNode = app.environment_id ? envNodeMap.get(app.environment_id) : void 0;
6742
+ const resource = {
6743
+ uuid: app.uuid,
6744
+ name: app.name,
6745
+ kind: "app",
6746
+ status: app.status,
6747
+ fqdn: app.fqdn
6748
+ };
6749
+ if (envNode) envNode.resources.push(resource);
6750
+ }
6751
+ for (const db of dbs) {
6752
+ const envNode = db.environment_id ? envNodeMap.get(db.environment_id) : void 0;
6753
+ const resource = {
6754
+ uuid: db.uuid,
6755
+ name: db.name,
6756
+ kind: "database",
6757
+ status: db.status,
6758
+ dbType: db.type
6759
+ };
6760
+ if (envNode) envNode.resources.push(resource);
6761
+ }
6762
+ for (const svc of svcs) {
6763
+ const envNode = svc.environment_id ? envNodeMap.get(svc.environment_id) : void 0;
6764
+ const resource = {
6765
+ uuid: svc.uuid,
6766
+ name: svc.name,
6767
+ kind: "service",
6768
+ status: svc.status
6769
+ };
6770
+ if (envNode) envNode.resources.push(resource);
6771
+ }
6772
+ const populatedProjects = projectNodes.filter((p) => p.environments.some((e) => e.resources.length > 0));
6773
+ const allStatuses = [
6774
+ ...apps.map((a) => a.status),
6775
+ ...dbs.map((d) => d.status),
6776
+ ...svcs.map((s) => s.status)
6777
+ ];
6778
+ const counts = {
6779
+ projects: populatedProjects.length,
6780
+ apps: apps.length,
6781
+ databases: dbs.length,
6782
+ services: svcs.length,
6783
+ healthy: allStatuses.filter((s) => s.includes("healthy")).length,
6784
+ running: allStatuses.filter((s) => s.startsWith("running") && !s.includes("healthy")).length,
6785
+ stopped: allStatuses.filter((s) => s.includes("exited")).length,
6786
+ unhealthy: allStatuses.filter((s) => s.includes("unhealthy")).length
6787
+ };
6788
+ const server = servers[0] || { name: "Unknown" };
6789
+ log.success(`Infrastructure tree built: ${counts.projects} projects, ${counts.apps} apps, ${counts.databases} dbs, ${counts.services} svcs`);
6790
+ return ok({
6791
+ server: {
6792
+ name: server.name,
6793
+ ip: server.ip,
6794
+ uuid: server.uuid
6795
+ },
6796
+ projects: populatedProjects,
6797
+ counts
6798
+ });
6799
+ }
6800
+ /**
6628
6801
  * Starts a service.
6629
6802
  * Note: Coolify API uses GET for service start/stop/restart.
6630
6803
  *
@@ -6678,8 +6851,46 @@ var CoolifyService = class {
6678
6851
  return ok(result.data || []);
6679
6852
  }
6680
6853
  /**
6854
+ * Bulk updates environment variables for a service.
6855
+ *
6856
+ * Uses the bulk endpoint `PATCH /services/{uuid}/envs/bulk` which has
6857
+ * create-or-update semantics: if the variable exists in the override
6858
+ * table, its value is updated; otherwise a new override is created.
6859
+ *
6860
+ * This is the only reliable way to update a variable that has been
6861
+ * deleted (i.e. its base value from docker-compose/git is still visible
6862
+ * in `listServiceEnvVars` but no override row exists), and the only way
6863
+ * to set the same key twice without the `POST /services/{uuid}/envs`
6864
+ * returning 409 "already exists".
6865
+ *
6866
+ * @param serviceUuid - Service UUID
6867
+ * @param envVars - Array of variable definitions to upsert
6868
+ * @returns Result indicating success or error
6869
+ */
6870
+ async bulkUpdateServiceEnvVars(serviceUuid, envVars) {
6871
+ log.info(`Bulk updating ${envVars.length} env vars for service ${serviceUuid}`);
6872
+ const result = await this.request(`/services/${serviceUuid}/envs/bulk`, {
6873
+ method: "PATCH",
6874
+ body: JSON.stringify({ data: envVars })
6875
+ });
6876
+ if (result.error) {
6877
+ log.error(`Failed to bulk update service env vars: ${result.error}`);
6878
+ return err(new Error(result.error));
6879
+ }
6880
+ log.success(`Bulk updated ${envVars.length} env vars for service ${serviceUuid}`);
6881
+ return ok(result.data || { message: "Environment variables updated" });
6882
+ }
6883
+ /**
6681
6884
  * Creates an environment variable for a service.
6682
6885
  *
6886
+ * NOTE: Prefer `bulkUpdateServiceEnvVars` for any non-trivial use case.
6887
+ * This endpoint uses `POST /services/{uuid}/envs` and returns 409
6888
+ * "already exists" when the key is already present as an override,
6889
+ * with no recovery path on the server side. Bulk has create-or-update
6890
+ * semantics and handles both new and existing keys reliably.
6891
+ *
6892
+ * Kept for callers that explicitly want a strict create-only operation.
6893
+ *
6683
6894
  * @param uuid - Service UUID
6684
6895
  * @param data - Env var data (key, value, is_preview)
6685
6896
  * @returns Result with created env var UUID or error
@@ -6693,6 +6904,69 @@ var CoolifyService = class {
6693
6904
  return ok(result.data);
6694
6905
  }
6695
6906
  /**
6907
+ * Deletes an environment variable from a service.
6908
+ *
6909
+ * @param serviceUuid - Service UUID
6910
+ * @param key - Variable name to delete
6911
+ * @returns Result indicating success or error
6912
+ */
6913
+ async deleteServiceEnvVar(serviceUuid, key) {
6914
+ log.info(`Deleting environment variable ${key} from service ${serviceUuid}`);
6915
+ const envVarsResult = await this.listServiceEnvVars(serviceUuid);
6916
+ if (isErr(envVarsResult)) return err(envVarsResult.error);
6917
+ const envVar = envVarsResult.value.find((ev) => ev.key === key);
6918
+ if (!envVar) {
6919
+ log.error(`Environment variable ${key} not found on service ${serviceUuid}`);
6920
+ return err(new Error(`Environment variable ${key} not found`));
6921
+ }
6922
+ const result = await this.request(`/services/${serviceUuid}/envs/${envVar.uuid}`, { method: "DELETE" });
6923
+ if (result.error) {
6924
+ log.error(`Failed to delete service env var: ${result.error}`);
6925
+ return err(new Error(result.error));
6926
+ }
6927
+ log.success(`Environment variable ${key} deleted from service ${serviceUuid}`);
6928
+ return ok(void 0);
6929
+ }
6930
+ /**
6931
+ * Lists environment variables for a database.
6932
+ *
6933
+ * @param databaseUuid - Database UUID
6934
+ * @returns Result with env vars list or error
6935
+ */
6936
+ async listDatabaseEnvVars(databaseUuid) {
6937
+ log.info(`Listing env vars for database ${databaseUuid}`);
6938
+ const result = await this.request(`/databases/${databaseUuid}/envs`);
6939
+ if (result.error) {
6940
+ log.error(`Failed to list database env vars: ${result.error}`);
6941
+ return err(new Error(result.error));
6942
+ }
6943
+ return ok(result.data || []);
6944
+ }
6945
+ /**
6946
+ * Deletes an environment variable from a database.
6947
+ *
6948
+ * @param databaseUuid - Database UUID
6949
+ * @param key - Variable name to delete
6950
+ * @returns Result indicating success or error
6951
+ */
6952
+ async deleteDatabaseEnvVar(databaseUuid, key) {
6953
+ log.info(`Deleting environment variable ${key} from database ${databaseUuid}`);
6954
+ const envVarsResult = await this.listDatabaseEnvVars(databaseUuid);
6955
+ if (isErr(envVarsResult)) return err(envVarsResult.error);
6956
+ const envVar = envVarsResult.value.find((ev) => ev.key === key);
6957
+ if (!envVar) {
6958
+ log.error(`Environment variable ${key} not found on database ${databaseUuid}`);
6959
+ return err(new Error(`Environment variable ${key} not found`));
6960
+ }
6961
+ const result = await this.request(`/databases/${databaseUuid}/envs/${envVar.uuid}`, { method: "DELETE" });
6962
+ if (result.error) {
6963
+ log.error(`Failed to delete database env var: ${result.error}`);
6964
+ return err(new Error(result.error));
6965
+ }
6966
+ log.success(`Environment variable ${key} deleted from database ${databaseUuid}`);
6967
+ return ok(void 0);
6968
+ }
6969
+ /**
6696
6970
  * Gets resources deployed on a server.
6697
6971
  *
6698
6972
  * @param serverUuid - Server UUID
@@ -7063,6 +7337,22 @@ var CoolifyService = class {
7063
7337
  return ok(deployments);
7064
7338
  }
7065
7339
  /**
7340
+ * Gets full application details by UUID.
7341
+ *
7342
+ * Makes a direct GET request to /api/v1/applications/{uuid} which returns
7343
+ * complete application data including project_uuid and environment_uuid.
7344
+ *
7345
+ * @param appUuid - Application UUID
7346
+ * @returns Result with full application details or error
7347
+ */
7348
+ async getApplication(appUuid) {
7349
+ log.info(`Getting application details: ${appUuid}`);
7350
+ const result = await this.request(`/applications/${appUuid}`);
7351
+ if (result.error) return err(new Error(result.error));
7352
+ if (!result.data) return err(new Error("Application not found"));
7353
+ return ok(result.data);
7354
+ }
7355
+ /**
7066
7356
  * Resolves an application by UUID, name, or domain (FQDN).
7067
7357
  *
7068
7358
  * @param query - UUID, name, or domain to search for
@@ -7381,6 +7671,45 @@ function getCoolifyService() {
7381
7671
  return instance;
7382
7672
  }
7383
7673
 
7674
+ //#endregion
7675
+ //#region src/utils/env-parser.ts
7676
+ /**
7677
+ * .env file parser shared between the SDK (syncEnv) and the CLI (--sync stdin).
7678
+ *
7679
+ * Kept as a standalone exported function (not a class method) so both the
7680
+ * SDK's ApplicationsResource and the CLI's stdin sync handler can use the
7681
+ * same implementation without coupling to either.
7682
+ *
7683
+ * @module
7684
+ */
7685
+ /**
7686
+ * Parses .env-style content into a Map.
7687
+ *
7688
+ * Handles:
7689
+ * - Comments (lines starting with `#`)
7690
+ * - Empty lines (skipped)
7691
+ * - Quoted values (`"value"` or `'value'`)
7692
+ * - Values containing `=` (only the first `=` is the separator)
7693
+ * - Lines without `=` (skipped — invalid)
7694
+ *
7695
+ * @param content - File contents in KEY=VALUE format
7696
+ * @returns Map of key → value (empty string for `KEY=` with no value)
7697
+ */
7698
+ function parseEnvContent(content) {
7699
+ const envVars = new Map();
7700
+ for (const line of content.split("\n")) {
7701
+ const trimmed = line.trim();
7702
+ if (!trimmed || trimmed.startsWith("#")) continue;
7703
+ const eq = trimmed.indexOf("=");
7704
+ if (eq === -1) continue;
7705
+ const key = trimmed.slice(0, eq).trim();
7706
+ let value = trimmed.slice(eq + 1).trim();
7707
+ if (value.startsWith("\"") && value.endsWith("\"") || value.startsWith("'") && value.endsWith("'")) value = value.slice(1, -1);
7708
+ if (key) envVars.set(key, value);
7709
+ }
7710
+ return envVars;
7711
+ }
7712
+
7384
7713
  //#endregion
7385
7714
  //#region src/sdk.ts
7386
7715
  init_dist();
@@ -7399,6 +7728,10 @@ var ApplicationsResource = class {
7399
7728
  async listSummaries() {
7400
7729
  return unwrap(await this.svc.listApplicationSummaries());
7401
7730
  }
7731
+ /** Get a single application by UUID with full details (including settings and watch_paths). */
7732
+ async get(uuid) {
7733
+ return unwrap(await this.svc.getApplication(uuid));
7734
+ }
7402
7735
  /** Resolve application by name, domain, or UUID. */
7403
7736
  async resolve(query) {
7404
7737
  return unwrap(await this.svc.resolveApplication(query));
@@ -7455,6 +7788,111 @@ var ApplicationsResource = class {
7455
7788
  async deleteEnv(uuid, key) {
7456
7789
  return unwrap(await this.svc.deleteEnvironmentVariable(uuid, key));
7457
7790
  }
7791
+ /**
7792
+ * Sync environment variables from a local .env file to Coolify.
7793
+ *
7794
+ * @param uuid - Application UUID
7795
+ * @param options - Sync options
7796
+ * @returns Sync result with changes applied
7797
+ */
7798
+ async syncEnv(uuid, options = {}) {
7799
+ const { filePath, dryRun = false, prune = false, onProgress } = options;
7800
+ let envContent;
7801
+ const { readFileSync: readFileSync$1 } = await import("node:fs");
7802
+ const { resolve, isAbsolute } = await import("node:path");
7803
+ const target = filePath || ".env";
7804
+ const absoluteTarget = isAbsolute(target) ? target : resolve(process.cwd(), target);
7805
+ try {
7806
+ envContent = readFileSync$1(absoluteTarget, "utf-8");
7807
+ } catch (err$1) {
7808
+ const msg = err$1 instanceof Error ? err$1.message : String(err$1);
7809
+ throw new Error(`Cannot read env file at ${absoluteTarget} (resolved from ${target}): ${msg}`);
7810
+ }
7811
+ const localVars = this.parseEnvContent(envContent);
7812
+ if (localVars.size === 0) return {
7813
+ added: [],
7814
+ updated: [],
7815
+ removed: [],
7816
+ skipped: 0
7817
+ };
7818
+ const currentVarsList = await this.envVars(uuid);
7819
+ const currentVars = new Map(currentVarsList.map((v) => [v.key, v.value]));
7820
+ const toAdd = [];
7821
+ const toUpdate = [];
7822
+ const toRemove = [];
7823
+ for (const [key, value] of localVars.entries()) {
7824
+ const currentValue = currentVars.get(key);
7825
+ if (!currentValue) toAdd.push({
7826
+ key,
7827
+ value
7828
+ });
7829
+ else if (currentValue !== value) toUpdate.push({
7830
+ key,
7831
+ value,
7832
+ oldValue: currentValue
7833
+ });
7834
+ }
7835
+ if (prune) {
7836
+ for (const key of currentVars.keys()) if (!localVars.has(key)) toRemove.push(key);
7837
+ }
7838
+ if (!dryRun) {
7839
+ for (const { key, value } of toAdd) {
7840
+ await this.setEnv(uuid, key, value, false);
7841
+ onProgress?.({
7842
+ type: "add",
7843
+ key,
7844
+ value
7845
+ });
7846
+ }
7847
+ for (const { key, value } of toUpdate) {
7848
+ await this.setEnv(uuid, key, value, false);
7849
+ onProgress?.({
7850
+ type: "update",
7851
+ key,
7852
+ value
7853
+ });
7854
+ }
7855
+ for (const key of toRemove) {
7856
+ await this.deleteEnv(uuid, key);
7857
+ onProgress?.({
7858
+ type: "remove",
7859
+ key
7860
+ });
7861
+ }
7862
+ } else {
7863
+ for (const { key, value } of toAdd) onProgress?.({
7864
+ type: "add",
7865
+ key,
7866
+ value
7867
+ });
7868
+ for (const { key, value } of toUpdate) onProgress?.({
7869
+ type: "update",
7870
+ key,
7871
+ value
7872
+ });
7873
+ for (const key of toRemove) onProgress?.({
7874
+ type: "remove",
7875
+ key
7876
+ });
7877
+ }
7878
+ return {
7879
+ added: toAdd,
7880
+ updated: toUpdate,
7881
+ removed: toRemove,
7882
+ skipped: currentVars.size - toUpdate.length - toRemove.length
7883
+ };
7884
+ }
7885
+ /**
7886
+ * Parse .env file content into a Map.
7887
+ * Delegates to the shared utility in `./utils/env-parser.js` so the SDK
7888
+ * and CLI use a single implementation.
7889
+ *
7890
+ * @param content - The .env file content
7891
+ * @returns Map of environment variables
7892
+ */
7893
+ parseEnvContent(content) {
7894
+ return parseEnvContent(content);
7895
+ }
7458
7896
  };
7459
7897
  var DatabasesResource = class {
7460
7898
  constructor(svc) {
@@ -7500,6 +7938,24 @@ var DatabasesResource = class {
7500
7938
  async deleteBackup(dbUuid, backupUuid) {
7501
7939
  return unwrap(await this.svc.deleteDatabaseBackup(dbUuid, backupUuid));
7502
7940
  }
7941
+ /** List env vars for a database. */
7942
+ async envVars(uuid) {
7943
+ return unwrap(await this.svc.listDatabaseEnvVars(uuid));
7944
+ }
7945
+ /**
7946
+ * Bulk set (create-or-update) env vars for a database.
7947
+ *
7948
+ * Note: the database schema is narrower than applications — only
7949
+ * `is_literal`, `is_multiline`, `is_shown_once` are accepted. No
7950
+ * `is_preview` / `is_buildtime` / `is_runtime`.
7951
+ */
7952
+ async bulkSetEnv(uuid, vars) {
7953
+ return unwrap(await this.svc.bulkUpdateDatabaseEnvVars(uuid, vars));
7954
+ }
7955
+ /** Delete a database env var by key. Resolves key → UUID, then DELETE. */
7956
+ async deleteEnv(uuid, key) {
7957
+ return unwrap(await this.svc.deleteDatabaseEnvVar(uuid, key));
7958
+ }
7503
7959
  };
7504
7960
  var ServicesResource = class {
7505
7961
  constructor(svc) {
@@ -7536,8 +7992,34 @@ var ServicesResource = class {
7536
7992
  async envVars(uuid) {
7537
7993
  return unwrap(await this.svc.listServiceEnvVars(uuid));
7538
7994
  }
7995
+ /**
7996
+ * Sets (creates or updates) a single env var for a service.
7997
+ *
7998
+ * Delegates to the bulk endpoint `PATCH /services/{uuid}/envs/bulk`,
7999
+ * which has create-or-update semantics — calling this for the same key
8000
+ * a second time updates the override value rather than failing with
8001
+ * 409 "already exists" (which is what the raw `POST /services/{uuid}/envs`
8002
+ * endpoint does). Mirrors `ApplicationsResource.setEnv`.
8003
+ *
8004
+ * @param uuid - Service UUID
8005
+ * @param data - Env var data (key, value, is_preview)
8006
+ */
7539
8007
  async setEnv(uuid, data) {
7540
- return unwrap(await this.svc.createServiceEnvVar(uuid, data));
8008
+ return unwrap(await this.svc.bulkUpdateServiceEnvVars(uuid, [data]));
8009
+ }
8010
+ /**
8011
+ * Bulk set (create-or-update) env vars for a service.
8012
+ * Mirrors `ApplicationsResource.bulkSetEnv`.
8013
+ *
8014
+ * @param uuid - Service UUID
8015
+ * @param vars - Array of env var definitions to upsert
8016
+ */
8017
+ async bulkSetEnv(uuid, vars) {
8018
+ return unwrap(await this.svc.bulkUpdateServiceEnvVars(uuid, vars));
8019
+ }
8020
+ /** Delete a service env var by key. Resolves key → UUID, then DELETE. */
8021
+ async deleteEnv(uuid, key) {
8022
+ return unwrap(await this.svc.deleteServiceEnvVar(uuid, key));
7541
8023
  }
7542
8024
  };
7543
8025
  var ServersResource = class {
@@ -8082,6 +8564,11 @@ Redeploy after updating to apply changes.`,
8082
8564
  type: "string",
8083
8565
  description: "Base directory for build context (default: \"/\")"
8084
8566
  },
8567
+ watchPaths: {
8568
+ type: "string",
8569
+ description: "Watch paths for selective auto-deploy. Newline-separated globs (e.g. \"src/**\\npackages/**\"). Set to empty string or null to clear.",
8570
+ nullable: true
8571
+ },
8085
8572
  dockerComposeDomains: {
8086
8573
  type: "string",
8087
8574
  description: "Docker Compose domains JSON: { \"service-name\": { \"domain\": \"https://...\" } }"
@@ -8090,6 +8577,20 @@ Redeploy after updating to apply changes.`,
8090
8577
  required: ["uuid"]
8091
8578
  }
8092
8579
  },
8580
+ {
8581
+ name: "get_application",
8582
+ description: `Get detailed information about a Coolify application including settings (auto-deploy, force HTTPS) and watch paths.
8583
+
8584
+ Returns full application details that list_applications doesn't include.`,
8585
+ inputSchema: {
8586
+ type: "object",
8587
+ properties: { uuid: {
8588
+ type: "string",
8589
+ description: "Application UUID"
8590
+ } },
8591
+ required: ["uuid"]
8592
+ }
8593
+ },
8093
8594
  {
8094
8595
  name: "set_domains",
8095
8596
  description: `Set domains/FQDN for a Coolify application.
@@ -8958,11 +9459,25 @@ async function handleToolCall(name, args) {
8958
9459
  startCommand: a.startCommand,
8959
9460
  domains: a.domains,
8960
9461
  isForceHttpsEnabled: a.isForceHttpsEnabled,
8961
- isAutoDeployEnabled: a.isAutoDeployEnabled
9462
+ isAutoDeployEnabled: a.isAutoDeployEnabled,
9463
+ watchPaths: a.watchPaths
8962
9464
  }).then((app) => ({
8963
9465
  message: `Application ${a.uuid} updated`,
8964
9466
  application: app
8965
9467
  })), "Failed to update application");
9468
+ case "get_application": return mcpCall((s) => s.applications.get(a.uuid).then((app) => ({
9469
+ uuid: app.uuid,
9470
+ name: app.name,
9471
+ status: app.status,
9472
+ fqdn: app.fqdn,
9473
+ git_repository: app.git_repository,
9474
+ git_branch: app.git_branch,
9475
+ build_pack: app.build_pack,
9476
+ dockerfile_location: app.dockerfile_location,
9477
+ base_directory: app.base_directory,
9478
+ watch_paths: app.watch_paths,
9479
+ settings: app.settings
9480
+ })), "Failed to get application");
8966
9481
  case "get_application_logs": return mcpCall((s) => s.applications.logs(a.uuid, {
8967
9482
  tail: a.tail,
8968
9483
  serviceName: a.serviceName
@@ -9323,38 +9838,1873 @@ var init_network = __esm({ "src/network.ts"() {
9323
9838
  } });
9324
9839
 
9325
9840
  //#endregion
9326
- //#region src/cli/coolify-state.ts
9327
- const STATE_FILE = ".coolify.json";
9328
- /**
9329
- * Loads .coolify.json from the current working directory.
9330
- *
9331
- * @returns The deploy state if found, null otherwise
9332
- */
9333
- function loadCoolifyState() {
9334
- const statePath = (0, node_path.join)(process.cwd(), STATE_FILE);
9335
- if (!(0, node_fs.existsSync)(statePath)) return null;
9336
- try {
9337
- const content = (0, node_fs.readFileSync)(statePath, "utf-8");
9338
- const state = JSON.parse(content);
9339
- if (!state.appUuid) return null;
9340
- return state;
9341
- } catch {
9342
- return null;
9343
- }
9344
- }
9345
- /**
9346
- * Resolves a UUID argument — if not provided, tries to read from .coolify.json.
9347
- *
9348
- * @param uuid - UUID from CLI argument (may be undefined)
9349
- * @param field - Which field to read from .coolify.json (default: appUuid)
9350
- * @returns The resolved UUID or null if not found
9841
+ //#region ../../../node_modules/.bun/cli-table3@0.6.5/node_modules/cli-table3/src/debug.js
9842
+ var require_debug = __commonJS({ "../../../node_modules/.bun/cli-table3@0.6.5/node_modules/cli-table3/src/debug.js"(exports, module) {
9843
+ let messages = [];
9844
+ let level = 0;
9845
+ const debug$3 = (msg, min) => {
9846
+ if (level >= min) messages.push(msg);
9847
+ };
9848
+ debug$3.WARN = 1;
9849
+ debug$3.INFO = 2;
9850
+ debug$3.DEBUG = 3;
9851
+ debug$3.reset = () => {
9852
+ messages = [];
9853
+ };
9854
+ debug$3.setDebugLevel = (v) => {
9855
+ level = v;
9856
+ };
9857
+ debug$3.warn = (msg) => debug$3(msg, debug$3.WARN);
9858
+ debug$3.info = (msg) => debug$3(msg, debug$3.INFO);
9859
+ debug$3.debug = (msg) => debug$3(msg, debug$3.DEBUG);
9860
+ debug$3.debugMessages = () => messages;
9861
+ module.exports = debug$3;
9862
+ } });
9863
+
9864
+ //#endregion
9865
+ //#region ../../../node_modules/.bun/ansi-regex@5.0.1/node_modules/ansi-regex/index.js
9866
+ var require_ansi_regex = __commonJS({ "../../../node_modules/.bun/ansi-regex@5.0.1/node_modules/ansi-regex/index.js"(exports, module) {
9867
+ module.exports = ({ onlyFirst = false } = {}) => {
9868
+ const pattern = ["[\\u001B\\u009B][[\\]()#;?]*(?:(?:(?:(?:;[-a-zA-Z\\d\\/#&.:=?%@~_]+)*|[a-zA-Z\\d]+(?:;[-a-zA-Z\\d\\/#&.:=?%@~_]*)*)?\\u0007)", "(?:(?:\\d{1,4}(?:;\\d{0,4})*)?[\\dA-PR-TZcf-ntqry=><~]))"].join("|");
9869
+ return new RegExp(pattern, onlyFirst ? void 0 : "g");
9870
+ };
9871
+ } });
9872
+
9873
+ //#endregion
9874
+ //#region ../../../node_modules/.bun/strip-ansi@6.0.1/node_modules/strip-ansi/index.js
9875
+ var require_strip_ansi = __commonJS({ "../../../node_modules/.bun/strip-ansi@6.0.1/node_modules/strip-ansi/index.js"(exports, module) {
9876
+ const ansiRegex = require_ansi_regex();
9877
+ module.exports = (string) => typeof string === "string" ? string.replace(ansiRegex(), "") : string;
9878
+ } });
9879
+
9880
+ //#endregion
9881
+ //#region ../../../node_modules/.bun/is-fullwidth-code-point@3.0.0/node_modules/is-fullwidth-code-point/index.js
9882
+ var require_is_fullwidth_code_point = __commonJS({ "../../../node_modules/.bun/is-fullwidth-code-point@3.0.0/node_modules/is-fullwidth-code-point/index.js"(exports, module) {
9883
+ const isFullwidthCodePoint$1 = (codePoint) => {
9884
+ if (Number.isNaN(codePoint)) return false;
9885
+ if (codePoint >= 4352 && (codePoint <= 4447 || codePoint === 9001 || codePoint === 9002 || 11904 <= codePoint && codePoint <= 12871 && codePoint !== 12351 || 12880 <= codePoint && codePoint <= 19903 || 19968 <= codePoint && codePoint <= 42182 || 43360 <= codePoint && codePoint <= 43388 || 44032 <= codePoint && codePoint <= 55203 || 63744 <= codePoint && codePoint <= 64255 || 65040 <= codePoint && codePoint <= 65049 || 65072 <= codePoint && codePoint <= 65131 || 65281 <= codePoint && codePoint <= 65376 || 65504 <= codePoint && codePoint <= 65510 || 110592 <= codePoint && codePoint <= 110593 || 127488 <= codePoint && codePoint <= 127569 || 131072 <= codePoint && codePoint <= 262141)) return true;
9886
+ return false;
9887
+ };
9888
+ module.exports = isFullwidthCodePoint$1;
9889
+ module.exports.default = isFullwidthCodePoint$1;
9890
+ } });
9891
+
9892
+ //#endregion
9893
+ //#region ../../../node_modules/.bun/emoji-regex@8.0.0/node_modules/emoji-regex/index.js
9894
+ var require_emoji_regex = __commonJS({ "../../../node_modules/.bun/emoji-regex@8.0.0/node_modules/emoji-regex/index.js"(exports, module) {
9895
+ module.exports = function() {
9896
+ return /\uD83C\uDFF4\uDB40\uDC67\uDB40\uDC62(?:\uDB40\uDC65\uDB40\uDC6E\uDB40\uDC67|\uDB40\uDC73\uDB40\uDC63\uDB40\uDC74|\uDB40\uDC77\uDB40\uDC6C\uDB40\uDC73)\uDB40\uDC7F|\uD83D\uDC68(?:\uD83C\uDFFC\u200D(?:\uD83E\uDD1D\u200D\uD83D\uDC68\uD83C\uDFFB|\uD83C[\uDF3E\uDF73\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFF\u200D(?:\uD83E\uDD1D\u200D\uD83D\uDC68(?:\uD83C[\uDFFB-\uDFFE])|\uD83C[\uDF3E\uDF73\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFE\u200D(?:\uD83E\uDD1D\u200D\uD83D\uDC68(?:\uD83C[\uDFFB-\uDFFD])|\uD83C[\uDF3E\uDF73\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFD\u200D(?:\uD83E\uDD1D\u200D\uD83D\uDC68(?:\uD83C[\uDFFB\uDFFC])|\uD83C[\uDF3E\uDF73\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\u200D(?:\u2764\uFE0F\u200D(?:\uD83D\uDC8B\u200D)?\uD83D\uDC68|(?:\uD83D[\uDC68\uDC69])\u200D(?:\uD83D\uDC66\u200D\uD83D\uDC66|\uD83D\uDC67\u200D(?:\uD83D[\uDC66\uDC67]))|\uD83D\uDC66\u200D\uD83D\uDC66|\uD83D\uDC67\u200D(?:\uD83D[\uDC66\uDC67])|(?:\uD83D[\uDC68\uDC69])\u200D(?:\uD83D[\uDC66\uDC67])|[\u2695\u2696\u2708]\uFE0F|\uD83D[\uDC66\uDC67]|\uD83C[\uDF3E\uDF73\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|(?:\uD83C\uDFFB\u200D[\u2695\u2696\u2708]|\uD83C\uDFFF\u200D[\u2695\u2696\u2708]|\uD83C\uDFFE\u200D[\u2695\u2696\u2708]|\uD83C\uDFFD\u200D[\u2695\u2696\u2708]|\uD83C\uDFFC\u200D[\u2695\u2696\u2708])\uFE0F|\uD83C\uDFFB\u200D(?:\uD83C[\uDF3E\uDF73\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C[\uDFFB-\uDFFF])|(?:\uD83E\uDDD1\uD83C\uDFFB\u200D\uD83E\uDD1D\u200D\uD83E\uDDD1|\uD83D\uDC69\uD83C\uDFFC\u200D\uD83E\uDD1D\u200D\uD83D\uDC69)\uD83C\uDFFB|\uD83E\uDDD1(?:\uD83C\uDFFF\u200D\uD83E\uDD1D\u200D\uD83E\uDDD1(?:\uD83C[\uDFFB-\uDFFF])|\u200D\uD83E\uDD1D\u200D\uD83E\uDDD1)|(?:\uD83E\uDDD1\uD83C\uDFFE\u200D\uD83E\uDD1D\u200D\uD83E\uDDD1|\uD83D\uDC69\uD83C\uDFFF\u200D\uD83E\uDD1D\u200D(?:\uD83D[\uDC68\uDC69]))(?:\uD83C[\uDFFB-\uDFFE])|(?:\uD83E\uDDD1\uD83C\uDFFC\u200D\uD83E\uDD1D\u200D\uD83E\uDDD1|\uD83D\uDC69\uD83C\uDFFD\u200D\uD83E\uDD1D\u200D\uD83D\uDC69)(?:\uD83C[\uDFFB\uDFFC])|\uD83D\uDC69(?:\uD83C\uDFFE\u200D(?:\uD83E\uDD1D\u200D\uD83D\uDC68(?:\uD83C[\uDFFB-\uDFFD\uDFFF])|\uD83C[\uDF3E\uDF73\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFC\u200D(?:\uD83E\uDD1D\u200D\uD83D\uDC68(?:\uD83C[\uDFFB\uDFFD-\uDFFF])|\uD83C[\uDF3E\uDF73\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFB\u200D(?:\uD83E\uDD1D\u200D\uD83D\uDC68(?:\uD83C[\uDFFC-\uDFFF])|\uD83C[\uDF3E\uDF73\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFD\u200D(?:\uD83E\uDD1D\u200D\uD83D\uDC68(?:\uD83C[\uDFFB\uDFFC\uDFFE\uDFFF])|\uD83C[\uDF3E\uDF73\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\u200D(?:\u2764\uFE0F\u200D(?:\uD83D\uDC8B\u200D(?:\uD83D[\uDC68\uDC69])|\uD83D[\uDC68\uDC69])|\uD83C[\uDF3E\uDF73\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFF\u200D(?:\uD83C[\uDF3E\uDF73\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD]))|\uD83D\uDC69\u200D\uD83D\uDC69\u200D(?:\uD83D\uDC66\u200D\uD83D\uDC66|\uD83D\uDC67\u200D(?:\uD83D[\uDC66\uDC67]))|(?:\uD83E\uDDD1\uD83C\uDFFD\u200D\uD83E\uDD1D\u200D\uD83E\uDDD1|\uD83D\uDC69\uD83C\uDFFE\u200D\uD83E\uDD1D\u200D\uD83D\uDC69)(?:\uD83C[\uDFFB-\uDFFD])|\uD83D\uDC69\u200D\uD83D\uDC66\u200D\uD83D\uDC66|\uD83D\uDC69\u200D\uD83D\uDC69\u200D(?:\uD83D[\uDC66\uDC67])|(?:\uD83D\uDC41\uFE0F\u200D\uD83D\uDDE8|\uD83D\uDC69(?:\uD83C\uDFFF\u200D[\u2695\u2696\u2708]|\uD83C\uDFFE\u200D[\u2695\u2696\u2708]|\uD83C\uDFFC\u200D[\u2695\u2696\u2708]|\uD83C\uDFFB\u200D[\u2695\u2696\u2708]|\uD83C\uDFFD\u200D[\u2695\u2696\u2708]|\u200D[\u2695\u2696\u2708])|(?:(?:\u26F9|\uD83C[\uDFCB\uDFCC]|\uD83D\uDD75)\uFE0F|\uD83D\uDC6F|\uD83E[\uDD3C\uDDDE\uDDDF])\u200D[\u2640\u2642]|(?:\u26F9|\uD83C[\uDFCB\uDFCC]|\uD83D\uDD75)(?:\uD83C[\uDFFB-\uDFFF])\u200D[\u2640\u2642]|(?:\uD83C[\uDFC3\uDFC4\uDFCA]|\uD83D[\uDC6E\uDC71\uDC73\uDC77\uDC81\uDC82\uDC86\uDC87\uDE45-\uDE47\uDE4B\uDE4D\uDE4E\uDEA3\uDEB4-\uDEB6]|\uD83E[\uDD26\uDD37-\uDD39\uDD3D\uDD3E\uDDB8\uDDB9\uDDCD-\uDDCF\uDDD6-\uDDDD])(?:(?:\uD83C[\uDFFB-\uDFFF])\u200D[\u2640\u2642]|\u200D[\u2640\u2642])|\uD83C\uDFF4\u200D\u2620)\uFE0F|\uD83D\uDC69\u200D\uD83D\uDC67\u200D(?:\uD83D[\uDC66\uDC67])|\uD83C\uDFF3\uFE0F\u200D\uD83C\uDF08|\uD83D\uDC15\u200D\uD83E\uDDBA|\uD83D\uDC69\u200D\uD83D\uDC66|\uD83D\uDC69\u200D\uD83D\uDC67|\uD83C\uDDFD\uD83C\uDDF0|\uD83C\uDDF4\uD83C\uDDF2|\uD83C\uDDF6\uD83C\uDDE6|[#\*0-9]\uFE0F\u20E3|\uD83C\uDDE7(?:\uD83C[\uDDE6\uDDE7\uDDE9-\uDDEF\uDDF1-\uDDF4\uDDF6-\uDDF9\uDDFB\uDDFC\uDDFE\uDDFF])|\uD83C\uDDF9(?:\uD83C[\uDDE6\uDDE8\uDDE9\uDDEB-\uDDED\uDDEF-\uDDF4\uDDF7\uDDF9\uDDFB\uDDFC\uDDFF])|\uD83C\uDDEA(?:\uD83C[\uDDE6\uDDE8\uDDEA\uDDEC\uDDED\uDDF7-\uDDFA])|\uD83E\uDDD1(?:\uD83C[\uDFFB-\uDFFF])|\uD83C\uDDF7(?:\uD83C[\uDDEA\uDDF4\uDDF8\uDDFA\uDDFC])|\uD83D\uDC69(?:\uD83C[\uDFFB-\uDFFF])|\uD83C\uDDF2(?:\uD83C[\uDDE6\uDDE8-\uDDED\uDDF0-\uDDFF])|\uD83C\uDDE6(?:\uD83C[\uDDE8-\uDDEC\uDDEE\uDDF1\uDDF2\uDDF4\uDDF6-\uDDFA\uDDFC\uDDFD\uDDFF])|\uD83C\uDDF0(?:\uD83C[\uDDEA\uDDEC-\uDDEE\uDDF2\uDDF3\uDDF5\uDDF7\uDDFC\uDDFE\uDDFF])|\uD83C\uDDED(?:\uD83C[\uDDF0\uDDF2\uDDF3\uDDF7\uDDF9\uDDFA])|\uD83C\uDDE9(?:\uD83C[\uDDEA\uDDEC\uDDEF\uDDF0\uDDF2\uDDF4\uDDFF])|\uD83C\uDDFE(?:\uD83C[\uDDEA\uDDF9])|\uD83C\uDDEC(?:\uD83C[\uDDE6\uDDE7\uDDE9-\uDDEE\uDDF1-\uDDF3\uDDF5-\uDDFA\uDDFC\uDDFE])|\uD83C\uDDF8(?:\uD83C[\uDDE6-\uDDEA\uDDEC-\uDDF4\uDDF7-\uDDF9\uDDFB\uDDFD-\uDDFF])|\uD83C\uDDEB(?:\uD83C[\uDDEE-\uDDF0\uDDF2\uDDF4\uDDF7])|\uD83C\uDDF5(?:\uD83C[\uDDE6\uDDEA-\uDDED\uDDF0-\uDDF3\uDDF7-\uDDF9\uDDFC\uDDFE])|\uD83C\uDDFB(?:\uD83C[\uDDE6\uDDE8\uDDEA\uDDEC\uDDEE\uDDF3\uDDFA])|\uD83C\uDDF3(?:\uD83C[\uDDE6\uDDE8\uDDEA-\uDDEC\uDDEE\uDDF1\uDDF4\uDDF5\uDDF7\uDDFA\uDDFF])|\uD83C\uDDE8(?:\uD83C[\uDDE6\uDDE8\uDDE9\uDDEB-\uDDEE\uDDF0-\uDDF5\uDDF7\uDDFA-\uDDFF])|\uD83C\uDDF1(?:\uD83C[\uDDE6-\uDDE8\uDDEE\uDDF0\uDDF7-\uDDFB\uDDFE])|\uD83C\uDDFF(?:\uD83C[\uDDE6\uDDF2\uDDFC])|\uD83C\uDDFC(?:\uD83C[\uDDEB\uDDF8])|\uD83C\uDDFA(?:\uD83C[\uDDE6\uDDEC\uDDF2\uDDF3\uDDF8\uDDFE\uDDFF])|\uD83C\uDDEE(?:\uD83C[\uDDE8-\uDDEA\uDDF1-\uDDF4\uDDF6-\uDDF9])|\uD83C\uDDEF(?:\uD83C[\uDDEA\uDDF2\uDDF4\uDDF5])|(?:\uD83C[\uDFC3\uDFC4\uDFCA]|\uD83D[\uDC6E\uDC71\uDC73\uDC77\uDC81\uDC82\uDC86\uDC87\uDE45-\uDE47\uDE4B\uDE4D\uDE4E\uDEA3\uDEB4-\uDEB6]|\uD83E[\uDD26\uDD37-\uDD39\uDD3D\uDD3E\uDDB8\uDDB9\uDDCD-\uDDCF\uDDD6-\uDDDD])(?:\uD83C[\uDFFB-\uDFFF])|(?:\u26F9|\uD83C[\uDFCB\uDFCC]|\uD83D\uDD75)(?:\uD83C[\uDFFB-\uDFFF])|(?:[\u261D\u270A-\u270D]|\uD83C[\uDF85\uDFC2\uDFC7]|\uD83D[\uDC42\uDC43\uDC46-\uDC50\uDC66\uDC67\uDC6B-\uDC6D\uDC70\uDC72\uDC74-\uDC76\uDC78\uDC7C\uDC83\uDC85\uDCAA\uDD74\uDD7A\uDD90\uDD95\uDD96\uDE4C\uDE4F\uDEC0\uDECC]|\uD83E[\uDD0F\uDD18-\uDD1C\uDD1E\uDD1F\uDD30-\uDD36\uDDB5\uDDB6\uDDBB\uDDD2-\uDDD5])(?:\uD83C[\uDFFB-\uDFFF])|(?:[\u231A\u231B\u23E9-\u23EC\u23F0\u23F3\u25FD\u25FE\u2614\u2615\u2648-\u2653\u267F\u2693\u26A1\u26AA\u26AB\u26BD\u26BE\u26C4\u26C5\u26CE\u26D4\u26EA\u26F2\u26F3\u26F5\u26FA\u26FD\u2705\u270A\u270B\u2728\u274C\u274E\u2753-\u2755\u2757\u2795-\u2797\u27B0\u27BF\u2B1B\u2B1C\u2B50\u2B55]|\uD83C[\uDC04\uDCCF\uDD8E\uDD91-\uDD9A\uDDE6-\uDDFF\uDE01\uDE1A\uDE2F\uDE32-\uDE36\uDE38-\uDE3A\uDE50\uDE51\uDF00-\uDF20\uDF2D-\uDF35\uDF37-\uDF7C\uDF7E-\uDF93\uDFA0-\uDFCA\uDFCF-\uDFD3\uDFE0-\uDFF0\uDFF4\uDFF8-\uDFFF]|\uD83D[\uDC00-\uDC3E\uDC40\uDC42-\uDCFC\uDCFF-\uDD3D\uDD4B-\uDD4E\uDD50-\uDD67\uDD7A\uDD95\uDD96\uDDA4\uDDFB-\uDE4F\uDE80-\uDEC5\uDECC\uDED0-\uDED2\uDED5\uDEEB\uDEEC\uDEF4-\uDEFA\uDFE0-\uDFEB]|\uD83E[\uDD0D-\uDD3A\uDD3C-\uDD45\uDD47-\uDD71\uDD73-\uDD76\uDD7A-\uDDA2\uDDA5-\uDDAA\uDDAE-\uDDCA\uDDCD-\uDDFF\uDE70-\uDE73\uDE78-\uDE7A\uDE80-\uDE82\uDE90-\uDE95])|(?:[#\*0-9\xA9\xAE\u203C\u2049\u2122\u2139\u2194-\u2199\u21A9\u21AA\u231A\u231B\u2328\u23CF\u23E9-\u23F3\u23F8-\u23FA\u24C2\u25AA\u25AB\u25B6\u25C0\u25FB-\u25FE\u2600-\u2604\u260E\u2611\u2614\u2615\u2618\u261D\u2620\u2622\u2623\u2626\u262A\u262E\u262F\u2638-\u263A\u2640\u2642\u2648-\u2653\u265F\u2660\u2663\u2665\u2666\u2668\u267B\u267E\u267F\u2692-\u2697\u2699\u269B\u269C\u26A0\u26A1\u26AA\u26AB\u26B0\u26B1\u26BD\u26BE\u26C4\u26C5\u26C8\u26CE\u26CF\u26D1\u26D3\u26D4\u26E9\u26EA\u26F0-\u26F5\u26F7-\u26FA\u26FD\u2702\u2705\u2708-\u270D\u270F\u2712\u2714\u2716\u271D\u2721\u2728\u2733\u2734\u2744\u2747\u274C\u274E\u2753-\u2755\u2757\u2763\u2764\u2795-\u2797\u27A1\u27B0\u27BF\u2934\u2935\u2B05-\u2B07\u2B1B\u2B1C\u2B50\u2B55\u3030\u303D\u3297\u3299]|\uD83C[\uDC04\uDCCF\uDD70\uDD71\uDD7E\uDD7F\uDD8E\uDD91-\uDD9A\uDDE6-\uDDFF\uDE01\uDE02\uDE1A\uDE2F\uDE32-\uDE3A\uDE50\uDE51\uDF00-\uDF21\uDF24-\uDF93\uDF96\uDF97\uDF99-\uDF9B\uDF9E-\uDFF0\uDFF3-\uDFF5\uDFF7-\uDFFF]|\uD83D[\uDC00-\uDCFD\uDCFF-\uDD3D\uDD49-\uDD4E\uDD50-\uDD67\uDD6F\uDD70\uDD73-\uDD7A\uDD87\uDD8A-\uDD8D\uDD90\uDD95\uDD96\uDDA4\uDDA5\uDDA8\uDDB1\uDDB2\uDDBC\uDDC2-\uDDC4\uDDD1-\uDDD3\uDDDC-\uDDDE\uDDE1\uDDE3\uDDE8\uDDEF\uDDF3\uDDFA-\uDE4F\uDE80-\uDEC5\uDECB-\uDED2\uDED5\uDEE0-\uDEE5\uDEE9\uDEEB\uDEEC\uDEF0\uDEF3-\uDEFA\uDFE0-\uDFEB]|\uD83E[\uDD0D-\uDD3A\uDD3C-\uDD45\uDD47-\uDD71\uDD73-\uDD76\uDD7A-\uDDA2\uDDA5-\uDDAA\uDDAE-\uDDCA\uDDCD-\uDDFF\uDE70-\uDE73\uDE78-\uDE7A\uDE80-\uDE82\uDE90-\uDE95])\uFE0F|(?:[\u261D\u26F9\u270A-\u270D]|\uD83C[\uDF85\uDFC2-\uDFC4\uDFC7\uDFCA-\uDFCC]|\uD83D[\uDC42\uDC43\uDC46-\uDC50\uDC66-\uDC78\uDC7C\uDC81-\uDC83\uDC85-\uDC87\uDC8F\uDC91\uDCAA\uDD74\uDD75\uDD7A\uDD90\uDD95\uDD96\uDE45-\uDE47\uDE4B-\uDE4F\uDEA3\uDEB4-\uDEB6\uDEC0\uDECC]|\uD83E[\uDD0F\uDD18-\uDD1F\uDD26\uDD30-\uDD39\uDD3C-\uDD3E\uDDB5\uDDB6\uDDB8\uDDB9\uDDBB\uDDCD-\uDDCF\uDDD1-\uDDDD])/g;
9897
+ };
9898
+ } });
9899
+
9900
+ //#endregion
9901
+ //#region ../../../node_modules/.bun/string-width@4.2.3/node_modules/string-width/index.js
9902
+ var require_string_width = __commonJS({ "../../../node_modules/.bun/string-width@4.2.3/node_modules/string-width/index.js"(exports, module) {
9903
+ const stripAnsi = require_strip_ansi();
9904
+ const isFullwidthCodePoint = require_is_fullwidth_code_point();
9905
+ const emojiRegex = require_emoji_regex();
9906
+ const stringWidth$1 = (string) => {
9907
+ if (typeof string !== "string" || string.length === 0) return 0;
9908
+ string = stripAnsi(string);
9909
+ if (string.length === 0) return 0;
9910
+ string = string.replace(emojiRegex(), " ");
9911
+ let width = 0;
9912
+ for (let i = 0; i < string.length; i++) {
9913
+ const code = string.codePointAt(i);
9914
+ if (code <= 31 || code >= 127 && code <= 159) continue;
9915
+ if (code >= 768 && code <= 879) continue;
9916
+ if (code > 65535) i++;
9917
+ width += isFullwidthCodePoint(code) ? 2 : 1;
9918
+ }
9919
+ return width;
9920
+ };
9921
+ module.exports = stringWidth$1;
9922
+ module.exports.default = stringWidth$1;
9923
+ } });
9924
+
9925
+ //#endregion
9926
+ //#region ../../../node_modules/.bun/cli-table3@0.6.5/node_modules/cli-table3/src/utils.js
9927
+ var require_utils = __commonJS({ "../../../node_modules/.bun/cli-table3@0.6.5/node_modules/cli-table3/src/utils.js"(exports, module) {
9928
+ const stringWidth = require_string_width();
9929
+ function codeRegex(capture) {
9930
+ return capture ? /\u001b\[((?:\d*;){0,5}\d*)m/g : /\u001b\[(?:\d*;){0,5}\d*m/g;
9931
+ }
9932
+ function strlen(str) {
9933
+ let code = codeRegex();
9934
+ let stripped = ("" + str).replace(code, "");
9935
+ let split = stripped.split("\n");
9936
+ return split.reduce(function(memo, s) {
9937
+ return stringWidth(s) > memo ? stringWidth(s) : memo;
9938
+ }, 0);
9939
+ }
9940
+ function repeat(str, times) {
9941
+ return Array(times + 1).join(str);
9942
+ }
9943
+ function pad(str, len, pad$1, dir) {
9944
+ let length = strlen(str);
9945
+ if (len + 1 >= length) {
9946
+ let padlen = len - length;
9947
+ switch (dir) {
9948
+ case "right": {
9949
+ str = repeat(pad$1, padlen) + str;
9950
+ break;
9951
+ }
9952
+ case "center": {
9953
+ let right = Math.ceil(padlen / 2);
9954
+ let left = padlen - right;
9955
+ str = repeat(pad$1, left) + str + repeat(pad$1, right);
9956
+ break;
9957
+ }
9958
+ default: {
9959
+ str = str + repeat(pad$1, padlen);
9960
+ break;
9961
+ }
9962
+ }
9963
+ }
9964
+ return str;
9965
+ }
9966
+ let codeCache = {};
9967
+ function addToCodeCache(name, on, off) {
9968
+ on = "\x1B[" + on + "m";
9969
+ off = "\x1B[" + off + "m";
9970
+ codeCache[on] = {
9971
+ set: name,
9972
+ to: true
9973
+ };
9974
+ codeCache[off] = {
9975
+ set: name,
9976
+ to: false
9977
+ };
9978
+ codeCache[name] = {
9979
+ on,
9980
+ off
9981
+ };
9982
+ }
9983
+ addToCodeCache("bold", 1, 22);
9984
+ addToCodeCache("italics", 3, 23);
9985
+ addToCodeCache("underline", 4, 24);
9986
+ addToCodeCache("inverse", 7, 27);
9987
+ addToCodeCache("strikethrough", 9, 29);
9988
+ function updateState(state, controlChars) {
9989
+ let controlCode = controlChars[1] ? parseInt(controlChars[1].split(";")[0]) : 0;
9990
+ if (controlCode >= 30 && controlCode <= 39 || controlCode >= 90 && controlCode <= 97) {
9991
+ state.lastForegroundAdded = controlChars[0];
9992
+ return;
9993
+ }
9994
+ if (controlCode >= 40 && controlCode <= 49 || controlCode >= 100 && controlCode <= 107) {
9995
+ state.lastBackgroundAdded = controlChars[0];
9996
+ return;
9997
+ }
9998
+ if (controlCode === 0) {
9999
+ for (let i in state)
10000
+ /* istanbul ignore else */
10001
+ if (Object.prototype.hasOwnProperty.call(state, i)) delete state[i];
10002
+ return;
10003
+ }
10004
+ let info$1 = codeCache[controlChars[0]];
10005
+ if (info$1) state[info$1.set] = info$1.to;
10006
+ }
10007
+ function readState(line) {
10008
+ let code = codeRegex(true);
10009
+ let controlChars = code.exec(line);
10010
+ let state = {};
10011
+ while (controlChars !== null) {
10012
+ updateState(state, controlChars);
10013
+ controlChars = code.exec(line);
10014
+ }
10015
+ return state;
10016
+ }
10017
+ function unwindState(state, ret) {
10018
+ let lastBackgroundAdded = state.lastBackgroundAdded;
10019
+ let lastForegroundAdded = state.lastForegroundAdded;
10020
+ delete state.lastBackgroundAdded;
10021
+ delete state.lastForegroundAdded;
10022
+ Object.keys(state).forEach(function(key) {
10023
+ if (state[key]) ret += codeCache[key].off;
10024
+ });
10025
+ if (lastBackgroundAdded && lastBackgroundAdded != "\x1B[49m") ret += "\x1B[49m";
10026
+ if (lastForegroundAdded && lastForegroundAdded != "\x1B[39m") ret += "\x1B[39m";
10027
+ return ret;
10028
+ }
10029
+ function rewindState(state, ret) {
10030
+ let lastBackgroundAdded = state.lastBackgroundAdded;
10031
+ let lastForegroundAdded = state.lastForegroundAdded;
10032
+ delete state.lastBackgroundAdded;
10033
+ delete state.lastForegroundAdded;
10034
+ Object.keys(state).forEach(function(key) {
10035
+ if (state[key]) ret = codeCache[key].on + ret;
10036
+ });
10037
+ if (lastBackgroundAdded && lastBackgroundAdded != "\x1B[49m") ret = lastBackgroundAdded + ret;
10038
+ if (lastForegroundAdded && lastForegroundAdded != "\x1B[39m") ret = lastForegroundAdded + ret;
10039
+ return ret;
10040
+ }
10041
+ function truncateWidth(str, desiredLength) {
10042
+ if (str.length === strlen(str)) return str.substr(0, desiredLength);
10043
+ while (strlen(str) > desiredLength) str = str.slice(0, -1);
10044
+ return str;
10045
+ }
10046
+ function truncateWidthWithAnsi(str, desiredLength) {
10047
+ let code = codeRegex(true);
10048
+ let split = str.split(codeRegex());
10049
+ let splitIndex = 0;
10050
+ let retLen = 0;
10051
+ let ret = "";
10052
+ let myArray;
10053
+ let state = {};
10054
+ while (retLen < desiredLength) {
10055
+ myArray = code.exec(str);
10056
+ let toAdd = split[splitIndex];
10057
+ splitIndex++;
10058
+ if (retLen + strlen(toAdd) > desiredLength) toAdd = truncateWidth(toAdd, desiredLength - retLen);
10059
+ ret += toAdd;
10060
+ retLen += strlen(toAdd);
10061
+ if (retLen < desiredLength) {
10062
+ if (!myArray) break;
10063
+ ret += myArray[0];
10064
+ updateState(state, myArray);
10065
+ }
10066
+ }
10067
+ return unwindState(state, ret);
10068
+ }
10069
+ function truncate(str, desiredLength, truncateChar) {
10070
+ truncateChar = truncateChar || "…";
10071
+ let lengthOfStr = strlen(str);
10072
+ if (lengthOfStr <= desiredLength) return str;
10073
+ desiredLength -= strlen(truncateChar);
10074
+ let ret = truncateWidthWithAnsi(str, desiredLength);
10075
+ ret += truncateChar;
10076
+ const hrefTag = "\x1B]8;;\x07";
10077
+ if (str.includes(hrefTag) && !ret.includes(hrefTag)) ret += hrefTag;
10078
+ return ret;
10079
+ }
10080
+ function defaultOptions() {
10081
+ return {
10082
+ chars: {
10083
+ top: "─",
10084
+ "top-mid": "┬",
10085
+ "top-left": "┌",
10086
+ "top-right": "┐",
10087
+ bottom: "─",
10088
+ "bottom-mid": "┴",
10089
+ "bottom-left": "└",
10090
+ "bottom-right": "┘",
10091
+ left: "│",
10092
+ "left-mid": "├",
10093
+ mid: "─",
10094
+ "mid-mid": "┼",
10095
+ right: "│",
10096
+ "right-mid": "┤",
10097
+ middle: "│"
10098
+ },
10099
+ truncate: "…",
10100
+ colWidths: [],
10101
+ rowHeights: [],
10102
+ colAligns: [],
10103
+ rowAligns: [],
10104
+ style: {
10105
+ "padding-left": 1,
10106
+ "padding-right": 1,
10107
+ head: ["red"],
10108
+ border: ["grey"],
10109
+ compact: false
10110
+ },
10111
+ head: []
10112
+ };
10113
+ }
10114
+ function mergeOptions(options, defaults) {
10115
+ options = options || {};
10116
+ defaults = defaults || defaultOptions();
10117
+ let ret = Object.assign({}, defaults, options);
10118
+ ret.chars = Object.assign({}, defaults.chars, options.chars);
10119
+ ret.style = Object.assign({}, defaults.style, options.style);
10120
+ return ret;
10121
+ }
10122
+ function wordWrap(maxLength, input) {
10123
+ let lines = [];
10124
+ let split = input.split(/(\s+)/g);
10125
+ let line = [];
10126
+ let lineLength = 0;
10127
+ let whitespace;
10128
+ for (let i = 0; i < split.length; i += 2) {
10129
+ let word = split[i];
10130
+ let newLength = lineLength + strlen(word);
10131
+ if (lineLength > 0 && whitespace) newLength += whitespace.length;
10132
+ if (newLength > maxLength) {
10133
+ if (lineLength !== 0) lines.push(line.join(""));
10134
+ line = [word];
10135
+ lineLength = strlen(word);
10136
+ } else {
10137
+ line.push(whitespace || "", word);
10138
+ lineLength = newLength;
10139
+ }
10140
+ whitespace = split[i + 1];
10141
+ }
10142
+ if (lineLength) lines.push(line.join(""));
10143
+ return lines;
10144
+ }
10145
+ function textWrap(maxLength, input) {
10146
+ let lines = [];
10147
+ let line = "";
10148
+ function pushLine(str, ws) {
10149
+ if (line.length && ws) line += ws;
10150
+ line += str;
10151
+ while (line.length > maxLength) {
10152
+ lines.push(line.slice(0, maxLength));
10153
+ line = line.slice(maxLength);
10154
+ }
10155
+ }
10156
+ let split = input.split(/(\s+)/g);
10157
+ for (let i = 0; i < split.length; i += 2) pushLine(split[i], i && split[i - 1]);
10158
+ if (line.length) lines.push(line);
10159
+ return lines;
10160
+ }
10161
+ function multiLineWordWrap(maxLength, input, wrapOnWordBoundary = true) {
10162
+ let output = [];
10163
+ input = input.split("\n");
10164
+ const handler = wrapOnWordBoundary ? wordWrap : textWrap;
10165
+ for (let i = 0; i < input.length; i++) output.push.apply(output, handler(maxLength, input[i]));
10166
+ return output;
10167
+ }
10168
+ function colorizeLines(input) {
10169
+ let state = {};
10170
+ let output = [];
10171
+ for (let i = 0; i < input.length; i++) {
10172
+ let line = rewindState(state, input[i]);
10173
+ state = readState(line);
10174
+ let temp = Object.assign({}, state);
10175
+ output.push(unwindState(temp, line));
10176
+ }
10177
+ return output;
10178
+ }
10179
+ /**
10180
+ * Credit: Matheus Sampaio https://github.com/matheussampaio
10181
+ */
10182
+ function hyperlink(url, text) {
10183
+ const OSC = "\x1B]";
10184
+ const BEL = "\x07";
10185
+ const SEP = ";";
10186
+ return [
10187
+ OSC,
10188
+ "8",
10189
+ SEP,
10190
+ SEP,
10191
+ url || text,
10192
+ BEL,
10193
+ text,
10194
+ OSC,
10195
+ "8",
10196
+ SEP,
10197
+ SEP,
10198
+ BEL
10199
+ ].join("");
10200
+ }
10201
+ module.exports = {
10202
+ strlen,
10203
+ repeat,
10204
+ pad,
10205
+ truncate,
10206
+ mergeOptions,
10207
+ wordWrap: multiLineWordWrap,
10208
+ colorizeLines,
10209
+ hyperlink
10210
+ };
10211
+ } });
10212
+
10213
+ //#endregion
10214
+ //#region ../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/styles.js
10215
+ var require_styles = __commonJS({ "../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/styles.js"(exports, module) {
10216
+ var styles$1 = {};
10217
+ module["exports"] = styles$1;
10218
+ var codes = {
10219
+ reset: [0, 0],
10220
+ bold: [1, 22],
10221
+ dim: [2, 22],
10222
+ italic: [3, 23],
10223
+ underline: [4, 24],
10224
+ inverse: [7, 27],
10225
+ hidden: [8, 28],
10226
+ strikethrough: [9, 29],
10227
+ black: [30, 39],
10228
+ red: [31, 39],
10229
+ green: [32, 39],
10230
+ yellow: [33, 39],
10231
+ blue: [34, 39],
10232
+ magenta: [35, 39],
10233
+ cyan: [36, 39],
10234
+ white: [37, 39],
10235
+ gray: [90, 39],
10236
+ grey: [90, 39],
10237
+ brightRed: [91, 39],
10238
+ brightGreen: [92, 39],
10239
+ brightYellow: [93, 39],
10240
+ brightBlue: [94, 39],
10241
+ brightMagenta: [95, 39],
10242
+ brightCyan: [96, 39],
10243
+ brightWhite: [97, 39],
10244
+ bgBlack: [40, 49],
10245
+ bgRed: [41, 49],
10246
+ bgGreen: [42, 49],
10247
+ bgYellow: [43, 49],
10248
+ bgBlue: [44, 49],
10249
+ bgMagenta: [45, 49],
10250
+ bgCyan: [46, 49],
10251
+ bgWhite: [47, 49],
10252
+ bgGray: [100, 49],
10253
+ bgGrey: [100, 49],
10254
+ bgBrightRed: [101, 49],
10255
+ bgBrightGreen: [102, 49],
10256
+ bgBrightYellow: [103, 49],
10257
+ bgBrightBlue: [104, 49],
10258
+ bgBrightMagenta: [105, 49],
10259
+ bgBrightCyan: [106, 49],
10260
+ bgBrightWhite: [107, 49],
10261
+ blackBG: [40, 49],
10262
+ redBG: [41, 49],
10263
+ greenBG: [42, 49],
10264
+ yellowBG: [43, 49],
10265
+ blueBG: [44, 49],
10266
+ magentaBG: [45, 49],
10267
+ cyanBG: [46, 49],
10268
+ whiteBG: [47, 49]
10269
+ };
10270
+ Object.keys(codes).forEach(function(key) {
10271
+ var val = codes[key];
10272
+ var style = styles$1[key] = [];
10273
+ style.open = "\x1B[" + val[0] + "m";
10274
+ style.close = "\x1B[" + val[1] + "m";
10275
+ });
10276
+ } });
10277
+
10278
+ //#endregion
10279
+ //#region ../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/system/has-flag.js
10280
+ var require_has_flag = __commonJS({ "../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/system/has-flag.js"(exports, module) {
10281
+ module.exports = function(flag, argv) {
10282
+ argv = argv || process.argv;
10283
+ var terminatorPos = argv.indexOf("--");
10284
+ var prefix = /^-{1,2}/.test(flag) ? "" : "--";
10285
+ var pos = argv.indexOf(prefix + flag);
10286
+ return pos !== -1 && (terminatorPos === -1 ? true : pos < terminatorPos);
10287
+ };
10288
+ } });
10289
+
10290
+ //#endregion
10291
+ //#region ../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/system/supports-colors.js
10292
+ var require_supports_colors = __commonJS({ "../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/system/supports-colors.js"(exports, module) {
10293
+ var os = require("os");
10294
+ var hasFlag = require_has_flag();
10295
+ var env = process.env;
10296
+ var forceColor = void 0;
10297
+ if (hasFlag("no-color") || hasFlag("no-colors") || hasFlag("color=false")) forceColor = false;
10298
+ else if (hasFlag("color") || hasFlag("colors") || hasFlag("color=true") || hasFlag("color=always")) forceColor = true;
10299
+ if ("FORCE_COLOR" in env) forceColor = env.FORCE_COLOR.length === 0 || parseInt(env.FORCE_COLOR, 10) !== 0;
10300
+ function translateLevel(level$1) {
10301
+ if (level$1 === 0) return false;
10302
+ return {
10303
+ level: level$1,
10304
+ hasBasic: true,
10305
+ has256: level$1 >= 2,
10306
+ has16m: level$1 >= 3
10307
+ };
10308
+ }
10309
+ function supportsColor(stream) {
10310
+ if (forceColor === false) return 0;
10311
+ if (hasFlag("color=16m") || hasFlag("color=full") || hasFlag("color=truecolor")) return 3;
10312
+ if (hasFlag("color=256")) return 2;
10313
+ if (stream && !stream.isTTY && forceColor !== true) return 0;
10314
+ var min = forceColor ? 1 : 0;
10315
+ if (process.platform === "win32") {
10316
+ var osRelease = os.release().split(".");
10317
+ if (Number(process.versions.node.split(".")[0]) >= 8 && Number(osRelease[0]) >= 10 && Number(osRelease[2]) >= 10586) return Number(osRelease[2]) >= 14931 ? 3 : 2;
10318
+ return 1;
10319
+ }
10320
+ if ("CI" in env) {
10321
+ if ([
10322
+ "TRAVIS",
10323
+ "CIRCLECI",
10324
+ "APPVEYOR",
10325
+ "GITLAB_CI"
10326
+ ].some(function(sign) {
10327
+ return sign in env;
10328
+ }) || env.CI_NAME === "codeship") return 1;
10329
+ return min;
10330
+ }
10331
+ if ("TEAMCITY_VERSION" in env) return /^(9\.(0*[1-9]\d*)\.|\d{2,}\.)/.test(env.TEAMCITY_VERSION) ? 1 : 0;
10332
+ if ("TERM_PROGRAM" in env) {
10333
+ var version = parseInt((env.TERM_PROGRAM_VERSION || "").split(".")[0], 10);
10334
+ switch (env.TERM_PROGRAM) {
10335
+ case "iTerm.app": return version >= 3 ? 3 : 2;
10336
+ case "Hyper": return 3;
10337
+ case "Apple_Terminal": return 2;
10338
+ }
10339
+ }
10340
+ if (/-256(color)?$/i.test(env.TERM)) return 2;
10341
+ if (/^screen|^xterm|^vt100|^rxvt|color|ansi|cygwin|linux/i.test(env.TERM)) return 1;
10342
+ if ("COLORTERM" in env) return 1;
10343
+ if (env.TERM === "dumb") return min;
10344
+ return min;
10345
+ }
10346
+ function getSupportLevel(stream) {
10347
+ var level$1 = supportsColor(stream);
10348
+ return translateLevel(level$1);
10349
+ }
10350
+ module.exports = {
10351
+ supportsColor: getSupportLevel,
10352
+ stdout: getSupportLevel(process.stdout),
10353
+ stderr: getSupportLevel(process.stderr)
10354
+ };
10355
+ } });
10356
+
10357
+ //#endregion
10358
+ //#region ../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/custom/trap.js
10359
+ var require_trap = __commonJS({ "../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/custom/trap.js"(exports, module) {
10360
+ module["exports"] = function runTheTrap(text, options) {
10361
+ var result = "";
10362
+ text = text || "Run the trap, drop the bass";
10363
+ text = text.split("");
10364
+ var trap = {
10365
+ a: [
10366
+ "@",
10367
+ "Ą",
10368
+ "Ⱥ",
10369
+ "Ʌ",
10370
+ "Δ",
10371
+ "Λ",
10372
+ "Д"
10373
+ ],
10374
+ b: [
10375
+ "ß",
10376
+ "Ɓ",
10377
+ "Ƀ",
10378
+ "ɮ",
10379
+ "β",
10380
+ "฿"
10381
+ ],
10382
+ c: [
10383
+ "©",
10384
+ "Ȼ",
10385
+ "Ͼ"
10386
+ ],
10387
+ d: [
10388
+ "Ð",
10389
+ "Ɗ",
10390
+ "Ԁ",
10391
+ "ԁ",
10392
+ "Ԃ",
10393
+ "ԃ"
10394
+ ],
10395
+ e: [
10396
+ "Ë",
10397
+ "ĕ",
10398
+ "Ǝ",
10399
+ "ɘ",
10400
+ "Σ",
10401
+ "ξ",
10402
+ "Ҽ",
10403
+ "੬"
10404
+ ],
10405
+ f: ["Ӻ"],
10406
+ g: ["ɢ"],
10407
+ h: [
10408
+ "Ħ",
10409
+ "ƕ",
10410
+ "Ң",
10411
+ "Һ",
10412
+ "Ӈ",
10413
+ "Ԋ"
10414
+ ],
10415
+ i: ["༏"],
10416
+ j: ["Ĵ"],
10417
+ k: [
10418
+ "ĸ",
10419
+ "Ҡ",
10420
+ "Ӄ",
10421
+ "Ԟ"
10422
+ ],
10423
+ l: ["Ĺ"],
10424
+ m: [
10425
+ "ʍ",
10426
+ "Ӎ",
10427
+ "ӎ",
10428
+ "Ԡ",
10429
+ "ԡ",
10430
+ "൩"
10431
+ ],
10432
+ n: [
10433
+ "Ñ",
10434
+ "ŋ",
10435
+ "Ɲ",
10436
+ "Ͷ",
10437
+ "Π",
10438
+ "Ҋ"
10439
+ ],
10440
+ o: [
10441
+ "Ø",
10442
+ "õ",
10443
+ "ø",
10444
+ "Ǿ",
10445
+ "ʘ",
10446
+ "Ѻ",
10447
+ "ם",
10448
+ "۝",
10449
+ "๏"
10450
+ ],
10451
+ p: ["Ƿ", "Ҏ"],
10452
+ q: ["্"],
10453
+ r: [
10454
+ "®",
10455
+ "Ʀ",
10456
+ "Ȑ",
10457
+ "Ɍ",
10458
+ "ʀ",
10459
+ "Я"
10460
+ ],
10461
+ s: [
10462
+ "§",
10463
+ "Ϟ",
10464
+ "ϟ",
10465
+ "Ϩ"
10466
+ ],
10467
+ t: [
10468
+ "Ł",
10469
+ "Ŧ",
10470
+ "ͳ"
10471
+ ],
10472
+ u: ["Ʊ", "Ս"],
10473
+ v: ["ט"],
10474
+ w: [
10475
+ "Ш",
10476
+ "Ѡ",
10477
+ "Ѽ",
10478
+ "൰"
10479
+ ],
10480
+ x: [
10481
+ "Ҳ",
10482
+ "Ӿ",
10483
+ "Ӽ",
10484
+ "ӽ"
10485
+ ],
10486
+ y: [
10487
+ "¥",
10488
+ "Ұ",
10489
+ "Ӌ"
10490
+ ],
10491
+ z: ["Ƶ", "ɀ"]
10492
+ };
10493
+ text.forEach(function(c) {
10494
+ c = c.toLowerCase();
10495
+ var chars = trap[c] || [" "];
10496
+ var rand = Math.floor(Math.random() * chars.length);
10497
+ if (typeof trap[c] !== "undefined") result += trap[c][rand];
10498
+ else result += c;
10499
+ });
10500
+ return result;
10501
+ };
10502
+ } });
10503
+
10504
+ //#endregion
10505
+ //#region ../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/custom/zalgo.js
10506
+ var require_zalgo = __commonJS({ "../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/custom/zalgo.js"(exports, module) {
10507
+ module["exports"] = function zalgo(text, options) {
10508
+ text = text || " he is here ";
10509
+ var soul = {
10510
+ "up": [
10511
+ "̍",
10512
+ "̎",
10513
+ "̄",
10514
+ "̅",
10515
+ "̿",
10516
+ "̑",
10517
+ "̆",
10518
+ "̐",
10519
+ "͒",
10520
+ "͗",
10521
+ "͑",
10522
+ "̇",
10523
+ "̈",
10524
+ "̊",
10525
+ "͂",
10526
+ "̓",
10527
+ "̈",
10528
+ "͊",
10529
+ "͋",
10530
+ "͌",
10531
+ "̃",
10532
+ "̂",
10533
+ "̌",
10534
+ "͐",
10535
+ "̀",
10536
+ "́",
10537
+ "̋",
10538
+ "̏",
10539
+ "̒",
10540
+ "̓",
10541
+ "̔",
10542
+ "̽",
10543
+ "̉",
10544
+ "ͣ",
10545
+ "ͤ",
10546
+ "ͥ",
10547
+ "ͦ",
10548
+ "ͧ",
10549
+ "ͨ",
10550
+ "ͩ",
10551
+ "ͪ",
10552
+ "ͫ",
10553
+ "ͬ",
10554
+ "ͭ",
10555
+ "ͮ",
10556
+ "ͯ",
10557
+ "̾",
10558
+ "͛",
10559
+ "͆",
10560
+ "̚"
10561
+ ],
10562
+ "down": [
10563
+ "̖",
10564
+ "̗",
10565
+ "̘",
10566
+ "̙",
10567
+ "̜",
10568
+ "̝",
10569
+ "̞",
10570
+ "̟",
10571
+ "̠",
10572
+ "̤",
10573
+ "̥",
10574
+ "̦",
10575
+ "̩",
10576
+ "̪",
10577
+ "̫",
10578
+ "̬",
10579
+ "̭",
10580
+ "̮",
10581
+ "̯",
10582
+ "̰",
10583
+ "̱",
10584
+ "̲",
10585
+ "̳",
10586
+ "̹",
10587
+ "̺",
10588
+ "̻",
10589
+ "̼",
10590
+ "ͅ",
10591
+ "͇",
10592
+ "͈",
10593
+ "͉",
10594
+ "͍",
10595
+ "͎",
10596
+ "͓",
10597
+ "͔",
10598
+ "͕",
10599
+ "͖",
10600
+ "͙",
10601
+ "͚",
10602
+ "̣"
10603
+ ],
10604
+ "mid": [
10605
+ "̕",
10606
+ "̛",
10607
+ "̀",
10608
+ "́",
10609
+ "͘",
10610
+ "̡",
10611
+ "̢",
10612
+ "̧",
10613
+ "̨",
10614
+ "̴",
10615
+ "̵",
10616
+ "̶",
10617
+ "͜",
10618
+ "͝",
10619
+ "͞",
10620
+ "͟",
10621
+ "͠",
10622
+ "͢",
10623
+ "̸",
10624
+ "̷",
10625
+ "͡",
10626
+ " ҉"
10627
+ ]
10628
+ };
10629
+ var all = [].concat(soul.up, soul.down, soul.mid);
10630
+ function randomNumber(range) {
10631
+ var r = Math.floor(Math.random() * range);
10632
+ return r;
10633
+ }
10634
+ function isChar(character) {
10635
+ var bool = false;
10636
+ all.filter(function(i) {
10637
+ bool = i === character;
10638
+ });
10639
+ return bool;
10640
+ }
10641
+ function heComes(text$1, options$1) {
10642
+ var result = "";
10643
+ var counts;
10644
+ var l;
10645
+ options$1 = options$1 || {};
10646
+ options$1["up"] = typeof options$1["up"] !== "undefined" ? options$1["up"] : true;
10647
+ options$1["mid"] = typeof options$1["mid"] !== "undefined" ? options$1["mid"] : true;
10648
+ options$1["down"] = typeof options$1["down"] !== "undefined" ? options$1["down"] : true;
10649
+ options$1["size"] = typeof options$1["size"] !== "undefined" ? options$1["size"] : "maxi";
10650
+ text$1 = text$1.split("");
10651
+ for (l in text$1) {
10652
+ if (isChar(l)) continue;
10653
+ result = result + text$1[l];
10654
+ counts = {
10655
+ "up": 0,
10656
+ "down": 0,
10657
+ "mid": 0
10658
+ };
10659
+ switch (options$1.size) {
10660
+ case "mini":
10661
+ counts.up = randomNumber(8);
10662
+ counts.mid = randomNumber(2);
10663
+ counts.down = randomNumber(8);
10664
+ break;
10665
+ case "maxi":
10666
+ counts.up = randomNumber(16) + 3;
10667
+ counts.mid = randomNumber(4) + 1;
10668
+ counts.down = randomNumber(64) + 3;
10669
+ break;
10670
+ default:
10671
+ counts.up = randomNumber(8) + 1;
10672
+ counts.mid = randomNumber(6) / 2;
10673
+ counts.down = randomNumber(8) + 1;
10674
+ break;
10675
+ }
10676
+ var arr = [
10677
+ "up",
10678
+ "mid",
10679
+ "down"
10680
+ ];
10681
+ for (var d in arr) {
10682
+ var index$1 = arr[d];
10683
+ for (var i = 0; i <= counts[index$1]; i++) if (options$1[index$1]) result = result + soul[index$1][randomNumber(soul[index$1].length)];
10684
+ }
10685
+ }
10686
+ return result;
10687
+ }
10688
+ return heComes(text, options);
10689
+ };
10690
+ } });
10691
+
10692
+ //#endregion
10693
+ //#region ../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/maps/america.js
10694
+ var require_america = __commonJS({ "../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/maps/america.js"(exports, module) {
10695
+ module["exports"] = function(colors$2) {
10696
+ return function(letter, i, exploded) {
10697
+ if (letter === " ") return letter;
10698
+ switch (i % 3) {
10699
+ case 0: return colors$2.red(letter);
10700
+ case 1: return colors$2.white(letter);
10701
+ case 2: return colors$2.blue(letter);
10702
+ }
10703
+ };
10704
+ };
10705
+ } });
10706
+
10707
+ //#endregion
10708
+ //#region ../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/maps/zebra.js
10709
+ var require_zebra = __commonJS({ "../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/maps/zebra.js"(exports, module) {
10710
+ module["exports"] = function(colors$2) {
10711
+ return function(letter, i, exploded) {
10712
+ return i % 2 === 0 ? letter : colors$2.inverse(letter);
10713
+ };
10714
+ };
10715
+ } });
10716
+
10717
+ //#endregion
10718
+ //#region ../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/maps/rainbow.js
10719
+ var require_rainbow = __commonJS({ "../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/maps/rainbow.js"(exports, module) {
10720
+ module["exports"] = function(colors$2) {
10721
+ var rainbowColors = [
10722
+ "red",
10723
+ "yellow",
10724
+ "green",
10725
+ "blue",
10726
+ "magenta"
10727
+ ];
10728
+ return function(letter, i, exploded) {
10729
+ if (letter === " ") return letter;
10730
+ else return colors$2[rainbowColors[i++ % rainbowColors.length]](letter);
10731
+ };
10732
+ };
10733
+ } });
10734
+
10735
+ //#endregion
10736
+ //#region ../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/maps/random.js
10737
+ var require_random = __commonJS({ "../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/maps/random.js"(exports, module) {
10738
+ module["exports"] = function(colors$2) {
10739
+ var available = [
10740
+ "underline",
10741
+ "inverse",
10742
+ "grey",
10743
+ "yellow",
10744
+ "red",
10745
+ "green",
10746
+ "blue",
10747
+ "white",
10748
+ "cyan",
10749
+ "magenta",
10750
+ "brightYellow",
10751
+ "brightRed",
10752
+ "brightGreen",
10753
+ "brightBlue",
10754
+ "brightWhite",
10755
+ "brightCyan",
10756
+ "brightMagenta"
10757
+ ];
10758
+ return function(letter, i, exploded) {
10759
+ return letter === " " ? letter : colors$2[available[Math.round(Math.random() * (available.length - 2))]](letter);
10760
+ };
10761
+ };
10762
+ } });
10763
+
10764
+ //#endregion
10765
+ //#region ../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/colors.js
10766
+ var require_colors = __commonJS({ "../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/lib/colors.js"(exports, module) {
10767
+ var colors$1 = {};
10768
+ module["exports"] = colors$1;
10769
+ colors$1.themes = {};
10770
+ var util = require("util");
10771
+ var ansiStyles = colors$1.styles = require_styles();
10772
+ var defineProps = Object.defineProperties;
10773
+ var newLineRegex = new RegExp(/[\r\n]+/g);
10774
+ colors$1.supportsColor = require_supports_colors().supportsColor;
10775
+ if (typeof colors$1.enabled === "undefined") colors$1.enabled = colors$1.supportsColor() !== false;
10776
+ colors$1.enable = function() {
10777
+ colors$1.enabled = true;
10778
+ };
10779
+ colors$1.disable = function() {
10780
+ colors$1.enabled = false;
10781
+ };
10782
+ colors$1.stripColors = colors$1.strip = function(str) {
10783
+ return ("" + str).replace(/\x1B\[\d+m/g, "");
10784
+ };
10785
+ var stylize = colors$1.stylize = function stylize$1(str, style) {
10786
+ if (!colors$1.enabled) return str + "";
10787
+ var styleMap = ansiStyles[style];
10788
+ if (!styleMap && style in colors$1) return colors$1[style](str);
10789
+ return styleMap.open + str + styleMap.close;
10790
+ };
10791
+ var matchOperatorsRe = /[|\\{}()[\]^$+*?.]/g;
10792
+ var escapeStringRegexp = function(str) {
10793
+ if (typeof str !== "string") throw new TypeError("Expected a string");
10794
+ return str.replace(matchOperatorsRe, "\\$&");
10795
+ };
10796
+ function build(_styles) {
10797
+ var builder = function builder$1() {
10798
+ return applyStyle.apply(builder$1, arguments);
10799
+ };
10800
+ builder._styles = _styles;
10801
+ builder.__proto__ = proto;
10802
+ return builder;
10803
+ }
10804
+ var styles = function() {
10805
+ var ret = {};
10806
+ ansiStyles.grey = ansiStyles.gray;
10807
+ Object.keys(ansiStyles).forEach(function(key) {
10808
+ ansiStyles[key].closeRe = new RegExp(escapeStringRegexp(ansiStyles[key].close), "g");
10809
+ ret[key] = { get: function() {
10810
+ return build(this._styles.concat(key));
10811
+ } };
10812
+ });
10813
+ return ret;
10814
+ }();
10815
+ var proto = defineProps(function colors$2() {}, styles);
10816
+ function applyStyle() {
10817
+ var args = Array.prototype.slice.call(arguments);
10818
+ var str = args.map(function(arg) {
10819
+ if (arg != null && arg.constructor === String) return arg;
10820
+ else return util.inspect(arg);
10821
+ }).join(" ");
10822
+ if (!colors$1.enabled || !str) return str;
10823
+ var newLinesPresent = str.indexOf("\n") != -1;
10824
+ var nestedStyles = this._styles;
10825
+ var i = nestedStyles.length;
10826
+ while (i--) {
10827
+ var code = ansiStyles[nestedStyles[i]];
10828
+ str = code.open + str.replace(code.closeRe, code.open) + code.close;
10829
+ if (newLinesPresent) str = str.replace(newLineRegex, function(match) {
10830
+ return code.close + match + code.open;
10831
+ });
10832
+ }
10833
+ return str;
10834
+ }
10835
+ colors$1.setTheme = function(theme) {
10836
+ if (typeof theme === "string") {
10837
+ console.log("colors.setTheme now only accepts an object, not a string. If you are trying to set a theme from a file, it is now your (the caller's) responsibility to require the file. The old syntax looked like colors.setTheme(__dirname + '/../themes/generic-logging.js'); The new syntax looks like colors.setTheme(require(__dirname + '/../themes/generic-logging.js'));");
10838
+ return;
10839
+ }
10840
+ for (var style in theme) (function(style$1) {
10841
+ colors$1[style$1] = function(str) {
10842
+ if (typeof theme[style$1] === "object") {
10843
+ var out = str;
10844
+ for (var i in theme[style$1]) out = colors$1[theme[style$1][i]](out);
10845
+ return out;
10846
+ }
10847
+ return colors$1[theme[style$1]](str);
10848
+ };
10849
+ })(style);
10850
+ };
10851
+ function init() {
10852
+ var ret = {};
10853
+ Object.keys(styles).forEach(function(name) {
10854
+ ret[name] = { get: function() {
10855
+ return build([name]);
10856
+ } };
10857
+ });
10858
+ return ret;
10859
+ }
10860
+ var sequencer = function sequencer$1(map$1, str) {
10861
+ var exploded = str.split("");
10862
+ exploded = exploded.map(map$1);
10863
+ return exploded.join("");
10864
+ };
10865
+ colors$1.trap = require_trap();
10866
+ colors$1.zalgo = require_zalgo();
10867
+ colors$1.maps = {};
10868
+ colors$1.maps.america = require_america()(colors$1);
10869
+ colors$1.maps.zebra = require_zebra()(colors$1);
10870
+ colors$1.maps.rainbow = require_rainbow()(colors$1);
10871
+ colors$1.maps.random = require_random()(colors$1);
10872
+ for (var map in colors$1.maps) (function(map$1) {
10873
+ colors$1[map$1] = function(str) {
10874
+ return sequencer(colors$1.maps[map$1], str);
10875
+ };
10876
+ })(map);
10877
+ defineProps(colors$1, init());
10878
+ } });
10879
+
10880
+ //#endregion
10881
+ //#region ../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/safe.js
10882
+ var require_safe = __commonJS({ "../../../node_modules/.bun/@colors+colors@1.5.0/node_modules/@colors/colors/safe.js"(exports, module) {
10883
+ var colors = require_colors();
10884
+ module["exports"] = colors;
10885
+ } });
10886
+
10887
+ //#endregion
10888
+ //#region ../../../node_modules/.bun/cli-table3@0.6.5/node_modules/cli-table3/src/cell.js
10889
+ var require_cell = __commonJS({ "../../../node_modules/.bun/cli-table3@0.6.5/node_modules/cli-table3/src/cell.js"(exports, module) {
10890
+ const { info, debug: debug$2 } = require_debug();
10891
+ const utils$1 = require_utils();
10892
+ var Cell$1 = class Cell$1 {
10893
+ /**
10894
+ * A representation of a cell within the table.
10895
+ * Implementations must have `init` and `draw` methods,
10896
+ * as well as `colSpan`, `rowSpan`, `desiredHeight` and `desiredWidth` properties.
10897
+ * @param options
10898
+ * @constructor
10899
+ */
10900
+ constructor(options) {
10901
+ this.setOptions(options);
10902
+ /**
10903
+ * Each cell will have it's `x` and `y` values set by the `layout-manager` prior to
10904
+ * `init` being called;
10905
+ * @type {Number}
10906
+ */
10907
+ this.x = null;
10908
+ this.y = null;
10909
+ }
10910
+ setOptions(options) {
10911
+ if ([
10912
+ "boolean",
10913
+ "number",
10914
+ "bigint",
10915
+ "string"
10916
+ ].indexOf(typeof options) !== -1) options = { content: "" + options };
10917
+ options = options || {};
10918
+ this.options = options;
10919
+ let content = options.content;
10920
+ if ([
10921
+ "boolean",
10922
+ "number",
10923
+ "bigint",
10924
+ "string"
10925
+ ].indexOf(typeof content) !== -1) this.content = String(content);
10926
+ else if (!content) this.content = this.options.href || "";
10927
+ else throw new Error("Content needs to be a primitive, got: " + typeof content);
10928
+ this.colSpan = options.colSpan || 1;
10929
+ this.rowSpan = options.rowSpan || 1;
10930
+ if (this.options.href) Object.defineProperty(this, "href", { get() {
10931
+ return this.options.href;
10932
+ } });
10933
+ }
10934
+ mergeTableOptions(tableOptions, cells) {
10935
+ this.cells = cells;
10936
+ let optionsChars = this.options.chars || {};
10937
+ let tableChars = tableOptions.chars;
10938
+ let chars = this.chars = {};
10939
+ CHAR_NAMES.forEach(function(name) {
10940
+ setOption(optionsChars, tableChars, name, chars);
10941
+ });
10942
+ this.truncate = this.options.truncate || tableOptions.truncate;
10943
+ let style = this.options.style = this.options.style || {};
10944
+ let tableStyle = tableOptions.style;
10945
+ setOption(style, tableStyle, "padding-left", this);
10946
+ setOption(style, tableStyle, "padding-right", this);
10947
+ this.head = style.head || tableStyle.head;
10948
+ this.border = style.border || tableStyle.border;
10949
+ this.fixedWidth = tableOptions.colWidths[this.x];
10950
+ this.lines = this.computeLines(tableOptions);
10951
+ this.desiredWidth = utils$1.strlen(this.content) + this.paddingLeft + this.paddingRight;
10952
+ this.desiredHeight = this.lines.length;
10953
+ }
10954
+ computeLines(tableOptions) {
10955
+ const tableWordWrap = tableOptions.wordWrap || tableOptions.textWrap;
10956
+ const { wordWrap: wordWrap$1 = tableWordWrap } = this.options;
10957
+ if (this.fixedWidth && wordWrap$1) {
10958
+ this.fixedWidth -= this.paddingLeft + this.paddingRight;
10959
+ if (this.colSpan) {
10960
+ let i = 1;
10961
+ while (i < this.colSpan) {
10962
+ this.fixedWidth += tableOptions.colWidths[this.x + i];
10963
+ i++;
10964
+ }
10965
+ }
10966
+ const { wrapOnWordBoundary: tableWrapOnWordBoundary = true } = tableOptions;
10967
+ const { wrapOnWordBoundary = tableWrapOnWordBoundary } = this.options;
10968
+ return this.wrapLines(utils$1.wordWrap(this.fixedWidth, this.content, wrapOnWordBoundary));
10969
+ }
10970
+ return this.wrapLines(this.content.split("\n"));
10971
+ }
10972
+ wrapLines(computedLines) {
10973
+ const lines = utils$1.colorizeLines(computedLines);
10974
+ if (this.href) return lines.map((line) => utils$1.hyperlink(this.href, line));
10975
+ return lines;
10976
+ }
10977
+ /**
10978
+ * Initializes the Cells data structure.
10979
+ *
10980
+ * @param tableOptions - A fully populated set of tableOptions.
10981
+ * In addition to the standard default values, tableOptions must have fully populated the
10982
+ * `colWidths` and `rowWidths` arrays. Those arrays must have lengths equal to the number
10983
+ * of columns or rows (respectively) in this table, and each array item must be a Number.
10984
+ *
10985
+ */
10986
+ init(tableOptions) {
10987
+ let x = this.x;
10988
+ let y = this.y;
10989
+ this.widths = tableOptions.colWidths.slice(x, x + this.colSpan);
10990
+ this.heights = tableOptions.rowHeights.slice(y, y + this.rowSpan);
10991
+ this.width = this.widths.reduce(sumPlusOne, -1);
10992
+ this.height = this.heights.reduce(sumPlusOne, -1);
10993
+ this.hAlign = this.options.hAlign || tableOptions.colAligns[x];
10994
+ this.vAlign = this.options.vAlign || tableOptions.rowAligns[y];
10995
+ this.drawRight = x + this.colSpan == tableOptions.colWidths.length;
10996
+ }
10997
+ /**
10998
+ * Draws the given line of the cell.
10999
+ * This default implementation defers to methods `drawTop`, `drawBottom`, `drawLine` and `drawEmpty`.
11000
+ * @param lineNum - can be `top`, `bottom` or a numerical line number.
11001
+ * @param spanningCell - will be a number if being called from a RowSpanCell, and will represent how
11002
+ * many rows below it's being called from. Otherwise it's undefined.
11003
+ * @returns {String} The representation of this line.
11004
+ */
11005
+ draw(lineNum, spanningCell) {
11006
+ if (lineNum == "top") return this.drawTop(this.drawRight);
11007
+ if (lineNum == "bottom") return this.drawBottom(this.drawRight);
11008
+ let content = utils$1.truncate(this.content, 10, this.truncate);
11009
+ if (!lineNum) info(`${this.y}-${this.x}: ${this.rowSpan - lineNum}x${this.colSpan} Cell ${content}`);
11010
+ let padLen = Math.max(this.height - this.lines.length, 0);
11011
+ let padTop;
11012
+ switch (this.vAlign) {
11013
+ case "center":
11014
+ padTop = Math.ceil(padLen / 2);
11015
+ break;
11016
+ case "bottom":
11017
+ padTop = padLen;
11018
+ break;
11019
+ default: padTop = 0;
11020
+ }
11021
+ if (lineNum < padTop || lineNum >= padTop + this.lines.length) return this.drawEmpty(this.drawRight, spanningCell);
11022
+ let forceTruncation = this.lines.length > this.height && lineNum + 1 >= this.height;
11023
+ return this.drawLine(lineNum - padTop, this.drawRight, forceTruncation, spanningCell);
11024
+ }
11025
+ /**
11026
+ * Renders the top line of the cell.
11027
+ * @param drawRight - true if this method should render the right edge of the cell.
11028
+ * @returns {String}
11029
+ */
11030
+ drawTop(drawRight) {
11031
+ let content = [];
11032
+ if (this.cells) this.widths.forEach(function(width, index$1) {
11033
+ content.push(this._topLeftChar(index$1));
11034
+ content.push(utils$1.repeat(this.chars[this.y == 0 ? "top" : "mid"], width));
11035
+ }, this);
11036
+ else {
11037
+ content.push(this._topLeftChar(0));
11038
+ content.push(utils$1.repeat(this.chars[this.y == 0 ? "top" : "mid"], this.width));
11039
+ }
11040
+ if (drawRight) content.push(this.chars[this.y == 0 ? "topRight" : "rightMid"]);
11041
+ return this.wrapWithStyleColors("border", content.join(""));
11042
+ }
11043
+ _topLeftChar(offset) {
11044
+ let x = this.x + offset;
11045
+ let leftChar;
11046
+ if (this.y == 0) leftChar = x == 0 ? "topLeft" : offset == 0 ? "topMid" : "top";
11047
+ else if (x == 0) leftChar = "leftMid";
11048
+ else {
11049
+ leftChar = offset == 0 ? "midMid" : "bottomMid";
11050
+ if (this.cells) {
11051
+ let spanAbove = this.cells[this.y - 1][x] instanceof Cell$1.ColSpanCell;
11052
+ if (spanAbove) leftChar = offset == 0 ? "topMid" : "mid";
11053
+ if (offset == 0) {
11054
+ let i = 1;
11055
+ while (this.cells[this.y][x - i] instanceof Cell$1.ColSpanCell) i++;
11056
+ if (this.cells[this.y][x - i] instanceof Cell$1.RowSpanCell) leftChar = "leftMid";
11057
+ }
11058
+ }
11059
+ }
11060
+ return this.chars[leftChar];
11061
+ }
11062
+ wrapWithStyleColors(styleProperty, content) {
11063
+ if (this[styleProperty] && this[styleProperty].length) try {
11064
+ let colors$2 = require_safe();
11065
+ for (let i = this[styleProperty].length - 1; i >= 0; i--) colors$2 = colors$2[this[styleProperty][i]];
11066
+ return colors$2(content);
11067
+ } catch (e) {
11068
+ return content;
11069
+ }
11070
+ else return content;
11071
+ }
11072
+ /**
11073
+ * Renders a line of text.
11074
+ * @param lineNum - Which line of text to render. This is not necessarily the line within the cell.
11075
+ * There may be top-padding above the first line of text.
11076
+ * @param drawRight - true if this method should render the right edge of the cell.
11077
+ * @param forceTruncationSymbol - `true` if the rendered text should end with the truncation symbol even
11078
+ * if the text fits. This is used when the cell is vertically truncated. If `false` the text should
11079
+ * only include the truncation symbol if the text will not fit horizontally within the cell width.
11080
+ * @param spanningCell - a number of if being called from a RowSpanCell. (how many rows below). otherwise undefined.
11081
+ * @returns {String}
11082
+ */
11083
+ drawLine(lineNum, drawRight, forceTruncationSymbol, spanningCell) {
11084
+ let left = this.chars[this.x == 0 ? "left" : "middle"];
11085
+ if (this.x && spanningCell && this.cells) {
11086
+ let cellLeft = this.cells[this.y + spanningCell][this.x - 1];
11087
+ while (cellLeft instanceof ColSpanCell$1) cellLeft = this.cells[cellLeft.y][cellLeft.x - 1];
11088
+ if (!(cellLeft instanceof RowSpanCell$1)) left = this.chars["rightMid"];
11089
+ }
11090
+ let leftPadding = utils$1.repeat(" ", this.paddingLeft);
11091
+ let right = drawRight ? this.chars["right"] : "";
11092
+ let rightPadding = utils$1.repeat(" ", this.paddingRight);
11093
+ let line = this.lines[lineNum];
11094
+ let len = this.width - (this.paddingLeft + this.paddingRight);
11095
+ if (forceTruncationSymbol) line += this.truncate || "…";
11096
+ let content = utils$1.truncate(line, len, this.truncate);
11097
+ content = utils$1.pad(content, len, " ", this.hAlign);
11098
+ content = leftPadding + content + rightPadding;
11099
+ return this.stylizeLine(left, content, right);
11100
+ }
11101
+ stylizeLine(left, content, right) {
11102
+ left = this.wrapWithStyleColors("border", left);
11103
+ right = this.wrapWithStyleColors("border", right);
11104
+ if (this.y === 0) content = this.wrapWithStyleColors("head", content);
11105
+ return left + content + right;
11106
+ }
11107
+ /**
11108
+ * Renders the bottom line of the cell.
11109
+ * @param drawRight - true if this method should render the right edge of the cell.
11110
+ * @returns {String}
11111
+ */
11112
+ drawBottom(drawRight) {
11113
+ let left = this.chars[this.x == 0 ? "bottomLeft" : "bottomMid"];
11114
+ let content = utils$1.repeat(this.chars.bottom, this.width);
11115
+ let right = drawRight ? this.chars["bottomRight"] : "";
11116
+ return this.wrapWithStyleColors("border", left + content + right);
11117
+ }
11118
+ /**
11119
+ * Renders a blank line of text within the cell. Used for top and/or bottom padding.
11120
+ * @param drawRight - true if this method should render the right edge of the cell.
11121
+ * @param spanningCell - a number of if being called from a RowSpanCell. (how many rows below). otherwise undefined.
11122
+ * @returns {String}
11123
+ */
11124
+ drawEmpty(drawRight, spanningCell) {
11125
+ let left = this.chars[this.x == 0 ? "left" : "middle"];
11126
+ if (this.x && spanningCell && this.cells) {
11127
+ let cellLeft = this.cells[this.y + spanningCell][this.x - 1];
11128
+ while (cellLeft instanceof ColSpanCell$1) cellLeft = this.cells[cellLeft.y][cellLeft.x - 1];
11129
+ if (!(cellLeft instanceof RowSpanCell$1)) left = this.chars["rightMid"];
11130
+ }
11131
+ let right = drawRight ? this.chars["right"] : "";
11132
+ let content = utils$1.repeat(" ", this.width);
11133
+ return this.stylizeLine(left, content, right);
11134
+ }
11135
+ };
11136
+ var ColSpanCell$1 = class {
11137
+ /**
11138
+ * A Cell that doesn't do anything. It just draws empty lines.
11139
+ * Used as a placeholder in column spanning.
11140
+ * @constructor
11141
+ */
11142
+ constructor() {}
11143
+ draw(lineNum) {
11144
+ if (typeof lineNum === "number") debug$2(`${this.y}-${this.x}: 1x1 ColSpanCell`);
11145
+ return "";
11146
+ }
11147
+ init() {}
11148
+ mergeTableOptions() {}
11149
+ };
11150
+ var RowSpanCell$1 = class {
11151
+ /**
11152
+ * A placeholder Cell for a Cell that spans multiple rows.
11153
+ * It delegates rendering to the original cell, but adds the appropriate offset.
11154
+ * @param originalCell
11155
+ * @constructor
11156
+ */
11157
+ constructor(originalCell) {
11158
+ this.originalCell = originalCell;
11159
+ }
11160
+ init(tableOptions) {
11161
+ let y = this.y;
11162
+ let originalY = this.originalCell.y;
11163
+ this.cellOffset = y - originalY;
11164
+ this.offset = findDimension(tableOptions.rowHeights, originalY, this.cellOffset);
11165
+ }
11166
+ draw(lineNum) {
11167
+ if (lineNum == "top") return this.originalCell.draw(this.offset, this.cellOffset);
11168
+ if (lineNum == "bottom") return this.originalCell.draw("bottom");
11169
+ debug$2(`${this.y}-${this.x}: 1x${this.colSpan} RowSpanCell for ${this.originalCell.content}`);
11170
+ return this.originalCell.draw(this.offset + 1 + lineNum);
11171
+ }
11172
+ mergeTableOptions() {}
11173
+ };
11174
+ function firstDefined(...args) {
11175
+ return args.filter((v) => v !== void 0 && v !== null).shift();
11176
+ }
11177
+ function setOption(objA, objB, nameB, targetObj) {
11178
+ let nameA = nameB.split("-");
11179
+ if (nameA.length > 1) {
11180
+ nameA[1] = nameA[1].charAt(0).toUpperCase() + nameA[1].substr(1);
11181
+ nameA = nameA.join("");
11182
+ targetObj[nameA] = firstDefined(objA[nameA], objA[nameB], objB[nameA], objB[nameB]);
11183
+ } else targetObj[nameB] = firstDefined(objA[nameB], objB[nameB]);
11184
+ }
11185
+ function findDimension(dimensionTable, startingIndex, span) {
11186
+ let ret = dimensionTable[startingIndex];
11187
+ for (let i = 1; i < span; i++) ret += 1 + dimensionTable[startingIndex + i];
11188
+ return ret;
11189
+ }
11190
+ function sumPlusOne(a, b) {
11191
+ return a + b + 1;
11192
+ }
11193
+ let CHAR_NAMES = [
11194
+ "top",
11195
+ "top-mid",
11196
+ "top-left",
11197
+ "top-right",
11198
+ "bottom",
11199
+ "bottom-mid",
11200
+ "bottom-left",
11201
+ "bottom-right",
11202
+ "left",
11203
+ "left-mid",
11204
+ "mid",
11205
+ "mid-mid",
11206
+ "right",
11207
+ "right-mid",
11208
+ "middle"
11209
+ ];
11210
+ module.exports = Cell$1;
11211
+ module.exports.ColSpanCell = ColSpanCell$1;
11212
+ module.exports.RowSpanCell = RowSpanCell$1;
11213
+ } });
11214
+
11215
+ //#endregion
11216
+ //#region ../../../node_modules/.bun/cli-table3@0.6.5/node_modules/cli-table3/src/layout-manager.js
11217
+ var require_layout_manager = __commonJS({ "../../../node_modules/.bun/cli-table3@0.6.5/node_modules/cli-table3/src/layout-manager.js"(exports, module) {
11218
+ const { warn, debug: debug$1 } = require_debug();
11219
+ const Cell = require_cell();
11220
+ const { ColSpanCell, RowSpanCell } = Cell;
11221
+ (function() {
11222
+ function next(alloc, col) {
11223
+ if (alloc[col] > 0) return next(alloc, col + 1);
11224
+ return col;
11225
+ }
11226
+ function layoutTable(table) {
11227
+ let alloc = {};
11228
+ table.forEach(function(row, rowIndex) {
11229
+ let col = 0;
11230
+ row.forEach(function(cell) {
11231
+ cell.y = rowIndex;
11232
+ cell.x = rowIndex ? next(alloc, col) : col;
11233
+ const rowSpan = cell.rowSpan || 1;
11234
+ const colSpan = cell.colSpan || 1;
11235
+ if (rowSpan > 1) for (let cs = 0; cs < colSpan; cs++) alloc[cell.x + cs] = rowSpan;
11236
+ col = cell.x + colSpan;
11237
+ });
11238
+ Object.keys(alloc).forEach((idx) => {
11239
+ alloc[idx]--;
11240
+ if (alloc[idx] < 1) delete alloc[idx];
11241
+ });
11242
+ });
11243
+ }
11244
+ function maxWidth(table) {
11245
+ let mw = 0;
11246
+ table.forEach(function(row) {
11247
+ row.forEach(function(cell) {
11248
+ mw = Math.max(mw, cell.x + (cell.colSpan || 1));
11249
+ });
11250
+ });
11251
+ return mw;
11252
+ }
11253
+ function maxHeight(table) {
11254
+ return table.length;
11255
+ }
11256
+ function cellsConflict(cell1, cell2) {
11257
+ let yMin1 = cell1.y;
11258
+ let yMax1 = cell1.y - 1 + (cell1.rowSpan || 1);
11259
+ let yMin2 = cell2.y;
11260
+ let yMax2 = cell2.y - 1 + (cell2.rowSpan || 1);
11261
+ let yConflict = !(yMin1 > yMax2 || yMin2 > yMax1);
11262
+ let xMin1 = cell1.x;
11263
+ let xMax1 = cell1.x - 1 + (cell1.colSpan || 1);
11264
+ let xMin2 = cell2.x;
11265
+ let xMax2 = cell2.x - 1 + (cell2.colSpan || 1);
11266
+ let xConflict = !(xMin1 > xMax2 || xMin2 > xMax1);
11267
+ return yConflict && xConflict;
11268
+ }
11269
+ function conflictExists(rows, x, y) {
11270
+ let i_max = Math.min(rows.length - 1, y);
11271
+ let cell = {
11272
+ x,
11273
+ y
11274
+ };
11275
+ for (let i = 0; i <= i_max; i++) {
11276
+ let row = rows[i];
11277
+ for (let j = 0; j < row.length; j++) if (cellsConflict(cell, row[j])) return true;
11278
+ }
11279
+ return false;
11280
+ }
11281
+ function allBlank(rows, y, xMin, xMax) {
11282
+ for (let x = xMin; x < xMax; x++) if (conflictExists(rows, x, y)) return false;
11283
+ return true;
11284
+ }
11285
+ function addRowSpanCells(table) {
11286
+ table.forEach(function(row, rowIndex) {
11287
+ row.forEach(function(cell) {
11288
+ for (let i = 1; i < cell.rowSpan; i++) {
11289
+ let rowSpanCell = new RowSpanCell(cell);
11290
+ rowSpanCell.x = cell.x;
11291
+ rowSpanCell.y = cell.y + i;
11292
+ rowSpanCell.colSpan = cell.colSpan;
11293
+ insertCell(rowSpanCell, table[rowIndex + i]);
11294
+ }
11295
+ });
11296
+ });
11297
+ }
11298
+ function addColSpanCells(cellRows) {
11299
+ for (let rowIndex = cellRows.length - 1; rowIndex >= 0; rowIndex--) {
11300
+ let cellColumns = cellRows[rowIndex];
11301
+ for (let columnIndex = 0; columnIndex < cellColumns.length; columnIndex++) {
11302
+ let cell = cellColumns[columnIndex];
11303
+ for (let k = 1; k < cell.colSpan; k++) {
11304
+ let colSpanCell = new ColSpanCell();
11305
+ colSpanCell.x = cell.x + k;
11306
+ colSpanCell.y = cell.y;
11307
+ cellColumns.splice(columnIndex + 1, 0, colSpanCell);
11308
+ }
11309
+ }
11310
+ }
11311
+ }
11312
+ function insertCell(cell, row) {
11313
+ let x = 0;
11314
+ while (x < row.length && row[x].x < cell.x) x++;
11315
+ row.splice(x, 0, cell);
11316
+ }
11317
+ function fillInTable(table) {
11318
+ let h_max = maxHeight(table);
11319
+ let w_max = maxWidth(table);
11320
+ debug$1(`Max rows: ${h_max}; Max cols: ${w_max}`);
11321
+ for (let y = 0; y < h_max; y++) for (let x = 0; x < w_max; x++) if (!conflictExists(table, x, y)) {
11322
+ let opts = {
11323
+ x,
11324
+ y,
11325
+ colSpan: 1,
11326
+ rowSpan: 1
11327
+ };
11328
+ x++;
11329
+ while (x < w_max && !conflictExists(table, x, y)) {
11330
+ opts.colSpan++;
11331
+ x++;
11332
+ }
11333
+ let y2 = y + 1;
11334
+ while (y2 < h_max && allBlank(table, y2, opts.x, opts.x + opts.colSpan)) {
11335
+ opts.rowSpan++;
11336
+ y2++;
11337
+ }
11338
+ let cell = new Cell(opts);
11339
+ cell.x = opts.x;
11340
+ cell.y = opts.y;
11341
+ warn(`Missing cell at ${cell.y}-${cell.x}.`);
11342
+ insertCell(cell, table[y]);
11343
+ }
11344
+ }
11345
+ function generateCells(rows) {
11346
+ return rows.map(function(row) {
11347
+ if (!Array.isArray(row)) {
11348
+ let key = Object.keys(row)[0];
11349
+ row = row[key];
11350
+ if (Array.isArray(row)) {
11351
+ row = row.slice();
11352
+ row.unshift(key);
11353
+ } else row = [key, row];
11354
+ }
11355
+ return row.map(function(cell) {
11356
+ return new Cell(cell);
11357
+ });
11358
+ });
11359
+ }
11360
+ function makeTableLayout(rows) {
11361
+ let cellRows = generateCells(rows);
11362
+ layoutTable(cellRows);
11363
+ fillInTable(cellRows);
11364
+ addRowSpanCells(cellRows);
11365
+ addColSpanCells(cellRows);
11366
+ return cellRows;
11367
+ }
11368
+ module.exports = {
11369
+ makeTableLayout,
11370
+ layoutTable,
11371
+ addRowSpanCells,
11372
+ maxWidth,
11373
+ fillInTable,
11374
+ computeWidths: makeComputeWidths("colSpan", "desiredWidth", "x", 1),
11375
+ computeHeights: makeComputeWidths("rowSpan", "desiredHeight", "y", 1)
11376
+ };
11377
+ })();
11378
+ function makeComputeWidths(colSpan, desiredWidth, x, forcedMin) {
11379
+ return function(vals, table) {
11380
+ let result = [];
11381
+ let spanners = [];
11382
+ let auto = {};
11383
+ table.forEach(function(row) {
11384
+ row.forEach(function(cell) {
11385
+ if ((cell[colSpan] || 1) > 1) spanners.push(cell);
11386
+ else result[cell[x]] = Math.max(result[cell[x]] || 0, cell[desiredWidth] || 0, forcedMin);
11387
+ });
11388
+ });
11389
+ vals.forEach(function(val, index$1) {
11390
+ if (typeof val === "number") result[index$1] = val;
11391
+ });
11392
+ for (let k = spanners.length - 1; k >= 0; k--) {
11393
+ let cell = spanners[k];
11394
+ let span = cell[colSpan];
11395
+ let col = cell[x];
11396
+ let existingWidth = result[col];
11397
+ let editableCols = typeof vals[col] === "number" ? 0 : 1;
11398
+ if (typeof existingWidth === "number") for (let i = 1; i < span; i++) {
11399
+ existingWidth += 1 + result[col + i];
11400
+ if (typeof vals[col + i] !== "number") editableCols++;
11401
+ }
11402
+ else {
11403
+ existingWidth = desiredWidth === "desiredWidth" ? cell.desiredWidth - 1 : 1;
11404
+ if (!auto[col] || auto[col] < existingWidth) auto[col] = existingWidth;
11405
+ }
11406
+ if (cell[desiredWidth] > existingWidth) {
11407
+ let i = 0;
11408
+ while (editableCols > 0 && cell[desiredWidth] > existingWidth) {
11409
+ if (typeof vals[col + i] !== "number") {
11410
+ let dif = Math.round((cell[desiredWidth] - existingWidth) / editableCols);
11411
+ existingWidth += dif;
11412
+ result[col + i] += dif;
11413
+ editableCols--;
11414
+ }
11415
+ i++;
11416
+ }
11417
+ }
11418
+ }
11419
+ Object.assign(vals, result, auto);
11420
+ for (let j = 0; j < vals.length; j++) vals[j] = Math.max(forcedMin, vals[j] || 0);
11421
+ };
11422
+ }
11423
+ } });
11424
+
11425
+ //#endregion
11426
+ //#region ../../../node_modules/.bun/cli-table3@0.6.5/node_modules/cli-table3/src/table.js
11427
+ var require_table = __commonJS({ "../../../node_modules/.bun/cli-table3@0.6.5/node_modules/cli-table3/src/table.js"(exports, module) {
11428
+ const debug = require_debug();
11429
+ const utils = require_utils();
11430
+ const tableLayout = require_layout_manager();
11431
+ var Table$1 = class extends Array {
11432
+ constructor(opts) {
11433
+ super();
11434
+ const options = utils.mergeOptions(opts);
11435
+ Object.defineProperty(this, "options", {
11436
+ value: options,
11437
+ enumerable: options.debug
11438
+ });
11439
+ if (options.debug) {
11440
+ switch (typeof options.debug) {
11441
+ case "boolean":
11442
+ debug.setDebugLevel(debug.WARN);
11443
+ break;
11444
+ case "number":
11445
+ debug.setDebugLevel(options.debug);
11446
+ break;
11447
+ case "string":
11448
+ debug.setDebugLevel(parseInt(options.debug, 10));
11449
+ break;
11450
+ default:
11451
+ debug.setDebugLevel(debug.WARN);
11452
+ debug.warn(`Debug option is expected to be boolean, number, or string. Received a ${typeof options.debug}`);
11453
+ }
11454
+ Object.defineProperty(this, "messages", { get() {
11455
+ return debug.debugMessages();
11456
+ } });
11457
+ }
11458
+ }
11459
+ toString() {
11460
+ let array = this;
11461
+ let headersPresent = this.options.head && this.options.head.length;
11462
+ if (headersPresent) {
11463
+ array = [this.options.head];
11464
+ if (this.length) array.push.apply(array, this);
11465
+ } else this.options.style.head = [];
11466
+ let cells = tableLayout.makeTableLayout(array);
11467
+ cells.forEach(function(row) {
11468
+ row.forEach(function(cell) {
11469
+ cell.mergeTableOptions(this.options, cells);
11470
+ }, this);
11471
+ }, this);
11472
+ tableLayout.computeWidths(this.options.colWidths, cells);
11473
+ tableLayout.computeHeights(this.options.rowHeights, cells);
11474
+ cells.forEach(function(row) {
11475
+ row.forEach(function(cell) {
11476
+ cell.init(this.options);
11477
+ }, this);
11478
+ }, this);
11479
+ let result = [];
11480
+ for (let rowIndex = 0; rowIndex < cells.length; rowIndex++) {
11481
+ let row = cells[rowIndex];
11482
+ let heightOfRow = this.options.rowHeights[rowIndex];
11483
+ if (rowIndex === 0 || !this.options.style.compact || rowIndex == 1 && headersPresent) doDraw(row, "top", result);
11484
+ for (let lineNum = 0; lineNum < heightOfRow; lineNum++) doDraw(row, lineNum, result);
11485
+ if (rowIndex + 1 == cells.length) doDraw(row, "bottom", result);
11486
+ }
11487
+ return result.join("\n");
11488
+ }
11489
+ get width() {
11490
+ let str = this.toString().split("\n");
11491
+ return str[0].length;
11492
+ }
11493
+ };
11494
+ Table$1.reset = () => debug.reset();
11495
+ function doDraw(row, lineNum, result) {
11496
+ let line = [];
11497
+ row.forEach(function(cell) {
11498
+ line.push(cell.draw(lineNum));
11499
+ });
11500
+ let str = line.join("");
11501
+ if (str.length) result.push(str);
11502
+ }
11503
+ module.exports = Table$1;
11504
+ } });
11505
+
11506
+ //#endregion
11507
+ //#region ../../../node_modules/.bun/cli-table3@0.6.5/node_modules/cli-table3/index.js
11508
+ var require_cli_table3 = __commonJS({ "../../../node_modules/.bun/cli-table3@0.6.5/node_modules/cli-table3/index.js"(exports, module) {
11509
+ module.exports = require_table();
11510
+ } });
11511
+
11512
+ //#endregion
11513
+ //#region src/utils/format.ts
11514
+ var import_cli_table3 = __toESM(require_cli_table3(), 1);
11515
+ /**
11516
+ * Validates a port number string (single or comma-separated).
11517
+ * Valid: "3000", "3000,3001", "80,443,8080"
11518
+ * Invalid: "abc", "99999", "0", "-1", "3000,", ",3000"
11519
+ *
11520
+ * @param ports - Port string to validate
11521
+ * @returns Object with valid flag, parsed ports, and error message
11522
+ */
11523
+ function validatePorts(ports) {
11524
+ if (!ports || !ports.trim()) return {
11525
+ valid: false,
11526
+ ports: [],
11527
+ error: "Port string is empty"
11528
+ };
11529
+ const parts = ports.split(",").map((p) => p.trim());
11530
+ const parsed = [];
11531
+ for (const part of parts) {
11532
+ if (!/^\d+$/.test(part)) return {
11533
+ valid: false,
11534
+ ports: [],
11535
+ error: `Invalid port "${part}" — must be a number`
11536
+ };
11537
+ const num = parseInt(part, 10);
11538
+ if (num < 1 || num > 65535) return {
11539
+ valid: false,
11540
+ ports: [],
11541
+ error: `Port ${num} out of range (1-65535)`
11542
+ };
11543
+ parsed.push(num);
11544
+ }
11545
+ const dupes = parsed.filter((p, i) => parsed.indexOf(p) !== i);
11546
+ if (dupes.length > 0) return {
11547
+ valid: false,
11548
+ ports: parsed,
11549
+ error: `Duplicate port: ${dupes[0]}`
11550
+ };
11551
+ return {
11552
+ valid: true,
11553
+ ports: parsed
11554
+ };
11555
+ }
11556
+ /**
11557
+ * Validates a .coolify.json state object (single-app format).
11558
+ * Checks required fields, types, and port validity.
11559
+ *
11560
+ * @param state - The parsed JSON object
11561
+ * @returns Object with valid flag, warnings, and errors
11562
+ */
11563
+ function validateCoolifyState(state) {
11564
+ const errors = [];
11565
+ const warnings = [];
11566
+ const isMultiApp = Array.isArray(state.apps);
11567
+ const isSingleApp = typeof state.appUuid === "string";
11568
+ if (!isMultiApp && !isSingleApp) {
11569
+ errors.push("Invalid format: must have \"appUuid\" (single-app) or \"apps\" array (multi-app)");
11570
+ return {
11571
+ valid: false,
11572
+ errors,
11573
+ warnings
11574
+ };
11575
+ }
11576
+ const commonRequired = [
11577
+ "serverUuid",
11578
+ "projectUuid",
11579
+ "environmentUuid"
11580
+ ];
11581
+ for (const field of commonRequired) if (!state[field] || typeof state[field] !== "string") errors.push(`Missing or invalid required field: ${field}`);
11582
+ if (isSingleApp) {
11583
+ if (state.portsExposes && typeof state.portsExposes === "string") {
11584
+ const portResult = validatePorts(state.portsExposes);
11585
+ if (!portResult.valid) warnings.push(`portsExposes: ${portResult.error}`);
11586
+ }
11587
+ if (state.buildPack && typeof state.buildPack === "string") {
11588
+ const validBuildPacks = [
11589
+ "dockerfile",
11590
+ "nixpacks",
11591
+ "static",
11592
+ "dockercompose"
11593
+ ];
11594
+ if (!validBuildPacks.includes(state.buildPack)) warnings.push(`Unknown buildPack "${state.buildPack}" — expected: ${validBuildPacks.join(", ")}`);
11595
+ }
11596
+ }
11597
+ if (isMultiApp) {
11598
+ const apps = state.apps;
11599
+ if (apps.length === 0) errors.push("Multi-app format requires at least one app");
11600
+ for (let i = 0; i < apps.length; i++) {
11601
+ const app = apps[i];
11602
+ if (!app.uuid || typeof app.uuid !== "string") errors.push(`apps[${i}]: missing or invalid "uuid"`);
11603
+ if (!app.name || typeof app.name !== "string") errors.push(`apps[${i}]: missing or invalid "name"`);
11604
+ if (!app.service || typeof app.service !== "string") errors.push(`apps[${i}]: missing or invalid "service"`);
11605
+ if (app.port !== void 0) {
11606
+ const port = app.port;
11607
+ if (typeof port !== "number" || port < 1 || port > 65535) warnings.push(`apps[${i}] (${app.name}): invalid port ${port}`);
11608
+ }
11609
+ }
11610
+ const uuids = apps.map((a) => a.uuid).filter(Boolean);
11611
+ const dupeUuids = uuids.filter((u, i) => uuids.indexOf(u) !== i);
11612
+ if (dupeUuids.length > 0) errors.push(`Duplicate app UUIDs: ${dupeUuids.join(", ")}`);
11613
+ }
11614
+ return {
11615
+ valid: errors.length === 0,
11616
+ errors,
11617
+ warnings
11618
+ };
11619
+ }
11620
+
11621
+ //#endregion
11622
+ //#region src/cli/coolify-state.ts
11623
+ const STATE_FILE = ".coolify.json";
11624
+ /**
11625
+ * Loads .coolify.json from the current working directory (single-app format).
11626
+ *
11627
+ * Handles both single-app and multi-app formats. For multi-app state with
11628
+ * exactly one app, returns a synthesized single-app state for backward compat.
11629
+ *
11630
+ * @returns The deploy state if found, null otherwise
11631
+ */
11632
+ function loadCoolifyState() {
11633
+ const statePath = (0, node_path.join)(process.cwd(), STATE_FILE);
11634
+ if (!(0, node_fs.existsSync)(statePath)) return null;
11635
+ try {
11636
+ const content = (0, node_fs.readFileSync)(statePath, "utf-8");
11637
+ const state = JSON.parse(content);
11638
+ if (Array.isArray(state.apps)) {
11639
+ if (state.apps.length === 1) {
11640
+ const app = state.apps[0];
11641
+ return {
11642
+ appUuid: app.uuid,
11643
+ appName: app.name,
11644
+ serverUuid: state.serverUuid,
11645
+ serverName: state.serverName,
11646
+ projectUuid: state.projectUuid,
11647
+ projectName: state.projectName,
11648
+ environmentUuid: state.environmentUuid,
11649
+ environmentName: state.environmentName,
11650
+ domain: app.domain,
11651
+ branch: state.branch,
11652
+ gitRepository: state.gitRepository,
11653
+ coolifyUrl: state.coolifyUrl,
11654
+ updatedAt: state.updatedAt
11655
+ };
11656
+ }
11657
+ return null;
11658
+ }
11659
+ if (!state.appUuid) return null;
11660
+ const validation = validateCoolifyState(state);
11661
+ if (!validation.valid) console.error(`Warning: .coolify.json has errors: ${validation.errors.join("; ")}`);
11662
+ if (validation.warnings.length > 0) for (const w of validation.warnings) console.error(`Warning: .coolify.json — ${w}`);
11663
+ return state;
11664
+ } catch {
11665
+ return null;
11666
+ }
11667
+ }
11668
+ /**
11669
+ * Loads .coolify.json in multi-app format.
11670
+ *
11671
+ * If the file is in single-app format, returns null (use loadCoolifyState instead).
11672
+ *
11673
+ * @returns The multi-app state if found, null otherwise
11674
+ */
11675
+ function loadMultiAppState() {
11676
+ const statePath = (0, node_path.join)(process.cwd(), STATE_FILE);
11677
+ if (!(0, node_fs.existsSync)(statePath)) return null;
11678
+ try {
11679
+ const content = (0, node_fs.readFileSync)(statePath, "utf-8");
11680
+ const state = JSON.parse(content);
11681
+ if (!Array.isArray(state.apps)) return null;
11682
+ return state;
11683
+ } catch {
11684
+ return null;
11685
+ }
11686
+ }
11687
+ /**
11688
+ * Resolves a UUID argument — if not provided, tries to read from .coolify.json.
11689
+ *
11690
+ * Supports both single-app and multi-app state formats. For multi-app state
11691
+ * with exactly one app, auto-selects that app. For multiple apps, returns null
11692
+ * (user must specify explicitly).
11693
+ *
11694
+ * @param uuid - UUID from CLI argument (may be undefined)
11695
+ * @param field - Which field to read from .coolify.json (default: appUuid)
11696
+ * @returns The resolved UUID or null if not found
9351
11697
  */
9352
11698
  function resolveUuid(uuid, field = "appUuid") {
9353
- if (uuid) return uuid;
11699
+ if (uuid && /^[a-z0-9]{16,40}$/.test(uuid)) return uuid;
9354
11700
  const state = loadCoolifyState();
9355
- if (!state) return null;
9356
- const value = state[field];
9357
- return typeof value === "string" ? value : null;
11701
+ if (state) {
11702
+ const value = state[field];
11703
+ return typeof value === "string" ? value : null;
11704
+ }
11705
+ const multiState = loadMultiAppState();
11706
+ if (multiState && multiState.apps.length === 1 && field === "appUuid") return multiState.apps[0].uuid;
11707
+ return null;
9358
11708
  }
9359
11709
 
9360
11710
  //#endregion