@kubb/cli 4.23.0 → 4.24.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 (50) hide show
  1. package/dist/agent-Buz_5Op4.cjs +22 -0
  2. package/dist/agent-Buz_5Op4.cjs.map +1 -0
  3. package/dist/agent-C9MWOHKX.js +22 -0
  4. package/dist/agent-C9MWOHKX.js.map +1 -0
  5. package/dist/{chunk-jHaXqnEa.js → chunk-EyRqdYP6.js} +4 -1
  6. package/dist/{generate-Cv8oibM4.cjs → generate-BYLZgOxz.cjs} +440 -13
  7. package/dist/generate-BYLZgOxz.cjs.map +1 -0
  8. package/dist/{generate-DhFw-owG.js → generate-DoM5hz_l.js} +435 -8
  9. package/dist/generate-DoM5hz_l.js.map +1 -0
  10. package/dist/index.cjs +8 -8
  11. package/dist/index.cjs.map +1 -1
  12. package/dist/index.d.ts +1 -1
  13. package/dist/index.js +10 -10
  14. package/dist/index.js.map +1 -1
  15. package/dist/{init-CiYFzdzt.js → init-CGHonZd1.js} +4 -4
  16. package/dist/{init-CiYFzdzt.js.map → init-CGHonZd1.js.map} +1 -1
  17. package/dist/{init-BKWuXKMO.cjs → init-CIr2otlG.cjs} +3 -3
  18. package/dist/{init-BKWuXKMO.cjs.map → init-CIr2otlG.cjs.map} +1 -1
  19. package/dist/{mcp-BdwwUv36.js → mcp-85caBdzd.js} +2 -2
  20. package/dist/{mcp-BdwwUv36.js.map → mcp-85caBdzd.js.map} +1 -1
  21. package/dist/{mcp-Hy_PYnFp.cjs → mcp-DGyip5BX.cjs} +1 -1
  22. package/dist/{mcp-Hy_PYnFp.cjs.map → mcp-DGyip5BX.cjs.map} +1 -1
  23. package/dist/package-DbleONiT.js +6 -0
  24. package/dist/package-DbleONiT.js.map +1 -0
  25. package/dist/{package-BfNquhL9.cjs → package-JlnkYQn6.cjs} +2 -2
  26. package/dist/package-JlnkYQn6.cjs.map +1 -0
  27. package/dist/start-DdvHHe8S.js +76 -0
  28. package/dist/start-DdvHHe8S.js.map +1 -0
  29. package/dist/start-Vf8kCm8g.cjs +80 -0
  30. package/dist/start-Vf8kCm8g.cjs.map +1 -0
  31. package/dist/{validate-YI4YkVTl.js → validate-DaGKH-63.js} +2 -2
  32. package/dist/{validate-YI4YkVTl.js.map → validate-DaGKH-63.js.map} +1 -1
  33. package/package.json +6 -5
  34. package/src/commands/agent/start.ts +85 -0
  35. package/src/commands/agent.ts +27 -0
  36. package/src/index.ts +2 -2
  37. package/dist/generate-Cv8oibM4.cjs.map +0 -1
  38. package/dist/generate-DhFw-owG.js.map +0 -1
  39. package/dist/getCosmiConfig-Co29x0Wv.cjs +0 -458
  40. package/dist/getCosmiConfig-Co29x0Wv.cjs.map +0 -1
  41. package/dist/getCosmiConfig-y2n_oW_y.js +0 -438
  42. package/dist/getCosmiConfig-y2n_oW_y.js.map +0 -1
  43. package/dist/package-BfNquhL9.cjs.map +0 -1
  44. package/dist/package-_Sd-Chc0.js +0 -6
  45. package/dist/package-_Sd-Chc0.js.map +0 -1
  46. package/dist/start-BtAU-_Gn.cjs +0 -128
  47. package/dist/start-BtAU-_Gn.cjs.map +0 -1
  48. package/dist/start-ugFADwjK.js +0 -125
  49. package/dist/start-ugFADwjK.js.map +0 -1
  50. package/src/commands/start.ts +0 -149
@@ -1,21 +1,24 @@
1
- import { t as __name } from "./chunk-jHaXqnEa.js";
2
- import { t as version } from "./package-_Sd-Chc0.js";
3
- import { n as getConfigs, r as generate, t as getCosmiConfig } from "./getCosmiConfig-y2n_oW_y.js";
1
+ import { t as __name } from "./chunk-EyRqdYP6.js";
2
+ import { t as version } from "./package-DbleONiT.js";
4
3
  import { defineCommand, showUsage } from "citty";
5
4
  import path, { relative, resolve } from "node:path";
6
5
  import * as process$2 from "node:process";
7
6
  import process$1 from "node:process";
8
7
  import * as clack from "@clack/prompts";
9
- import { LogLevel, PromiseManager, defineLogger, isInputPath } from "@kubb/core";
10
- import { AsyncEventEmitter, executeIfOnline, formatHrtime, formatMs } from "@kubb/core/utils";
11
- import getLatestVersion from "latest-version";
8
+ import { execa, execaCommand } from "execa";
12
9
  import pc from "picocolors";
10
+ import { LogLevel, PromiseManager, defineLogger, isInputPath, safeBuild, setup } from "@kubb/core";
11
+ import { AsyncEventEmitter, executeIfOnline, formatHrtime, formatMs, isPromise } from "@kubb/core/utils";
12
+ import getLatestVersion from "latest-version";
13
13
  import { lt } from "semver";
14
- import { execa } from "execa";
15
14
  import gradientString from "gradient-string";
16
15
  import seedrandom from "seedrandom";
17
16
  import { Writable } from "node:stream";
18
17
  import { write } from "@kubb/core/fs";
18
+ import { createHash } from "node:crypto";
19
+ import { parseArgsStringToArgv } from "string-argv";
20
+ import { cosmiconfig } from "cosmiconfig";
21
+ import { createJiti } from "jiti";
19
22
 
20
23
  //#region src/utils/formatMsWithColor.ts
21
24
  /**
@@ -1142,6 +1145,430 @@ async function setupLogger(context, { logLevel }) {
1142
1145
  return cleanup;
1143
1146
  }
1144
1147
 
1148
+ //#endregion
1149
+ //#region src/utils/detectFormatter.ts
1150
+ /**
1151
+ * Check if a formatter command is available in the system.
1152
+ *
1153
+ * @param formatter - The formatter to check ('biome', 'prettier', or 'oxfmt')
1154
+ * @returns Promise that resolves to true if the formatter is available, false otherwise
1155
+ *
1156
+ * @remarks
1157
+ * This function checks availability by running `<formatter> --version` command.
1158
+ * All supported formatters (biome, prettier, oxfmt) implement the --version flag.
1159
+ */
1160
+ async function isFormatterAvailable(formatter) {
1161
+ try {
1162
+ await execaCommand(`${formatter} --version`, { stdio: "ignore" });
1163
+ return true;
1164
+ } catch {
1165
+ return false;
1166
+ }
1167
+ }
1168
+ /**
1169
+ * Detect which formatter is available in the system.
1170
+ *
1171
+ * @returns Promise that resolves to the first available formatter or undefined if none are found
1172
+ *
1173
+ * @remarks
1174
+ * Checks in order of preference: biome, oxfmt, prettier.
1175
+ * Uses the `--version` flag to detect if each formatter command is available.
1176
+ * This is a reliable method as all supported formatters implement this flag.
1177
+ *
1178
+ * @example
1179
+ * ```typescript
1180
+ * const formatter = await detectFormatter()
1181
+ * if (formatter) {
1182
+ * console.log(`Using ${formatter} for formatting`)
1183
+ * } else {
1184
+ * console.log('No formatter found')
1185
+ * }
1186
+ * ```
1187
+ */
1188
+ async function detectFormatter() {
1189
+ for (const formatter of [
1190
+ "biome",
1191
+ "oxfmt",
1192
+ "prettier"
1193
+ ]) if (await isFormatterAvailable(formatter)) return formatter;
1194
+ }
1195
+
1196
+ //#endregion
1197
+ //#region src/utils/detectLinter.ts
1198
+ /**
1199
+ * Check if a linter command is available in the system.
1200
+ *
1201
+ * @param linter - The linter to check ('biome', 'oxlint', or 'eslint')
1202
+ * @returns Promise that resolves to true if the linter is available, false otherwise
1203
+ *
1204
+ * @remarks
1205
+ * This function checks availability by running `<linter> --version` command.
1206
+ * All supported linters (biome, oxlint, eslint) implement the --version flag.
1207
+ */
1208
+ async function isLinterAvailable(linter) {
1209
+ try {
1210
+ await execaCommand(`${linter} --version`, { stdio: "ignore" });
1211
+ return true;
1212
+ } catch {
1213
+ return false;
1214
+ }
1215
+ }
1216
+ /**
1217
+ * Detect which linter is available in the system.
1218
+ *
1219
+ * @returns Promise that resolves to the first available linter or undefined if none are found
1220
+ *
1221
+ * @remarks
1222
+ * Checks in order of preference: biome, oxlint, eslint.
1223
+ * Uses the `--version` flag to detect if each linter command is available.
1224
+ * This is a reliable method as all supported linters implement this flag.
1225
+ *
1226
+ * @example
1227
+ * ```typescript
1228
+ * const linter = await detectLinter()
1229
+ * if (linter) {
1230
+ * console.log(`Using ${linter} for linting`)
1231
+ * } else {
1232
+ * console.log('No linter found')
1233
+ * }
1234
+ * ```
1235
+ */
1236
+ async function detectLinter() {
1237
+ for (const linter of [
1238
+ "biome",
1239
+ "oxlint",
1240
+ "eslint"
1241
+ ]) if (await isLinterAvailable(linter)) return linter;
1242
+ }
1243
+
1244
+ //#endregion
1245
+ //#region src/utils/executeHooks.ts
1246
+ async function executeHooks({ hooks, events }) {
1247
+ const commands = Array.isArray(hooks.done) ? hooks.done : [hooks.done].filter(Boolean);
1248
+ for (const command$1 of commands) {
1249
+ const [cmd, ...args] = [...parseArgsStringToArgv(command$1)];
1250
+ if (!cmd) continue;
1251
+ const hookId = createHash("sha256").update(command$1).digest("hex");
1252
+ await events.emit("hook:start", {
1253
+ id: hookId,
1254
+ command: cmd,
1255
+ args
1256
+ });
1257
+ await events.onOnce("hook:end", async ({ success, error }) => {
1258
+ if (!success) throw error;
1259
+ await events.emit("success", `${pc.dim(command$1)} successfully executed`);
1260
+ });
1261
+ }
1262
+ }
1263
+
1264
+ //#endregion
1265
+ //#region src/utils/formatters.ts
1266
+ const formatters = {
1267
+ prettier: {
1268
+ command: "prettier",
1269
+ args: (outputPath) => [
1270
+ "--ignore-unknown",
1271
+ "--write",
1272
+ outputPath
1273
+ ],
1274
+ errorMessage: "Prettier not found"
1275
+ },
1276
+ biome: {
1277
+ command: "biome",
1278
+ args: (outputPath) => [
1279
+ "format",
1280
+ "--write",
1281
+ outputPath
1282
+ ],
1283
+ errorMessage: "Biome not found"
1284
+ },
1285
+ oxfmt: {
1286
+ command: "oxfmt",
1287
+ args: (outputPath) => [outputPath],
1288
+ errorMessage: "Oxfmt not found"
1289
+ }
1290
+ };
1291
+
1292
+ //#endregion
1293
+ //#region src/runners/generate.ts
1294
+ async function generate({ input, config: userConfig, events, logLevel }) {
1295
+ const inputPath = input ?? ("path" in userConfig.input ? userConfig.input.path : void 0);
1296
+ const hrStart = process$1.hrtime();
1297
+ const config = {
1298
+ ...userConfig,
1299
+ root: userConfig.root || process$1.cwd(),
1300
+ input: inputPath ? {
1301
+ ...userConfig.input,
1302
+ path: inputPath
1303
+ } : userConfig.input,
1304
+ output: {
1305
+ write: true,
1306
+ barrelType: "named",
1307
+ extension: { ".ts": ".ts" },
1308
+ format: "prettier",
1309
+ ...userConfig.output
1310
+ }
1311
+ };
1312
+ await events.emit("generation:start", config);
1313
+ await events.emit("info", config.name ? `Setup generation ${pc.bold(config.name)}` : "Setup generation", inputPath);
1314
+ const { sources, fabric, pluginManager } = await setup({
1315
+ config,
1316
+ events
1317
+ });
1318
+ await events.emit("info", config.name ? `Build generation ${pc.bold(config.name)}` : "Build generation", inputPath);
1319
+ const { files, failedPlugins, pluginTimings, error } = await safeBuild({
1320
+ config,
1321
+ events
1322
+ }, {
1323
+ pluginManager,
1324
+ fabric,
1325
+ events,
1326
+ sources
1327
+ });
1328
+ await events.emit("info", "Load summary");
1329
+ if (failedPlugins.size > 0 || error) {
1330
+ [error, ...Array.from(failedPlugins).filter((it) => it.error).map((it) => it.error)].filter(Boolean).forEach((err) => {
1331
+ events.emit("error", err);
1332
+ });
1333
+ await events.emit("generation:end", config, files, sources);
1334
+ await events.emit("generation:summary", config, {
1335
+ failedPlugins,
1336
+ filesCreated: files.length,
1337
+ status: failedPlugins.size > 0 || error ? "failed" : "success",
1338
+ hrStart,
1339
+ pluginTimings: logLevel >= LogLevel.verbose ? pluginTimings : void 0
1340
+ });
1341
+ process$1.exit(1);
1342
+ }
1343
+ await events.emit("success", "Generation successfully", inputPath);
1344
+ await events.emit("generation:end", config, files, sources);
1345
+ if (config.output.format) {
1346
+ await events.emit("format:start");
1347
+ let formatter = config.output.format;
1348
+ if (formatter === "auto") {
1349
+ const detectedFormatter = await detectFormatter();
1350
+ if (!detectedFormatter) await events.emit("warn", "No formatter found (biome, prettier, or oxfmt). Skipping formatting.");
1351
+ else {
1352
+ formatter = detectedFormatter;
1353
+ await events.emit("info", `Auto-detected formatter: ${pc.dim(formatter)}`);
1354
+ }
1355
+ }
1356
+ if (formatter && formatter !== "auto" && formatter in formatters) {
1357
+ const formatterConfig = formatters[formatter];
1358
+ const outputPath = path.resolve(config.root, config.output.path);
1359
+ try {
1360
+ const hookId = createHash("sha256").update([config.name, formatter].filter(Boolean).join("-")).digest("hex");
1361
+ await events.emit("hook:start", {
1362
+ id: hookId,
1363
+ command: formatterConfig.command,
1364
+ args: formatterConfig.args(outputPath)
1365
+ });
1366
+ await events.onOnce("hook:end", async ({ success, error: error$1 }) => {
1367
+ if (!success) throw error$1;
1368
+ await events.emit("success", [
1369
+ `Formatting with ${pc.dim(formatter)}`,
1370
+ logLevel >= LogLevel.info ? `on ${pc.dim(outputPath)}` : void 0,
1371
+ "successfully"
1372
+ ].filter(Boolean).join(" "));
1373
+ });
1374
+ } catch (caughtError) {
1375
+ const error$1 = new Error(formatterConfig.errorMessage);
1376
+ error$1.cause = caughtError;
1377
+ await events.emit("error", error$1);
1378
+ }
1379
+ }
1380
+ await events.emit("format:end");
1381
+ }
1382
+ if (config.output.lint) {
1383
+ await events.emit("lint:start");
1384
+ let linter = config.output.lint;
1385
+ if (linter === "auto") {
1386
+ const detectedLinter = await detectLinter();
1387
+ if (!detectedLinter) await events.emit("warn", "No linter found (biome, oxlint, or eslint). Skipping linting.");
1388
+ else {
1389
+ linter = detectedLinter;
1390
+ await events.emit("info", `Auto-detected linter: ${pc.dim(linter)}`);
1391
+ }
1392
+ }
1393
+ if (linter && linter !== "auto") {
1394
+ await events.emit("info", [`Linting with ${pc.dim(linter)}`, logLevel >= LogLevel.info ? `on ${pc.dim(path.resolve(config.root, config.output.path))}` : void 0].filter(Boolean).join(" "));
1395
+ if (linter === "eslint") try {
1396
+ const hookId = createHash("sha256").update([config.name, linter].filter(Boolean).join("-")).digest("hex");
1397
+ await events.emit("hook:start", {
1398
+ id: hookId,
1399
+ command: "eslint",
1400
+ args: [path.resolve(config.root, config.output.path), "--fix"]
1401
+ });
1402
+ await events.onOnce("hook:end", async ({ success, error: error$1 }) => {
1403
+ if (!success) throw error$1;
1404
+ await events.emit("success", [
1405
+ `Linted with ${pc.dim(linter)}`,
1406
+ logLevel >= LogLevel.info ? `on ${pc.dim(path.resolve(config.root, config.output.path))}` : void 0,
1407
+ "successfully"
1408
+ ].filter(Boolean).join(" "));
1409
+ });
1410
+ } catch (caughtError) {
1411
+ const error$1 = /* @__PURE__ */ new Error("Eslint not found");
1412
+ error$1.cause = caughtError;
1413
+ await events.emit("error", error$1);
1414
+ }
1415
+ if (linter === "biome") try {
1416
+ const hookId = createHash("sha256").update([config.name, linter].filter(Boolean).join("-")).digest("hex");
1417
+ await events.emit("hook:start", {
1418
+ id: hookId,
1419
+ command: "biome",
1420
+ args: [
1421
+ "lint",
1422
+ "--fix",
1423
+ path.resolve(config.root, config.output.path)
1424
+ ]
1425
+ });
1426
+ await events.onOnce("hook:end", async ({ success, error: error$1 }) => {
1427
+ if (!success) throw error$1;
1428
+ await events.emit("success", [
1429
+ `Linted with ${pc.dim(linter)}`,
1430
+ logLevel >= LogLevel.info ? `on ${pc.dim(path.resolve(config.root, config.output.path))}` : void 0,
1431
+ "successfully"
1432
+ ].filter(Boolean).join(" "));
1433
+ });
1434
+ } catch (caughtError) {
1435
+ const error$1 = /* @__PURE__ */ new Error("Biome not found");
1436
+ error$1.cause = caughtError;
1437
+ await events.emit("error", error$1);
1438
+ }
1439
+ if (linter === "oxlint") try {
1440
+ const hookId = createHash("sha256").update([config.name, linter].filter(Boolean).join("-")).digest("hex");
1441
+ await events.emit("hook:start", {
1442
+ id: hookId,
1443
+ command: "oxlint",
1444
+ args: ["--fix", path.resolve(config.root, config.output.path)]
1445
+ });
1446
+ await events.onOnce("hook:end", async ({ success, error: error$1 }) => {
1447
+ if (!success) throw error$1;
1448
+ await events.emit("success", [
1449
+ `Linted with ${pc.dim(linter)}`,
1450
+ logLevel >= LogLevel.info ? `on ${pc.dim(path.resolve(config.root, config.output.path))}` : void 0,
1451
+ "successfully"
1452
+ ].filter(Boolean).join(" "));
1453
+ });
1454
+ } catch (caughtError) {
1455
+ const error$1 = /* @__PURE__ */ new Error("Oxlint not found");
1456
+ error$1.cause = caughtError;
1457
+ await events.emit("error", error$1);
1458
+ }
1459
+ }
1460
+ await events.emit("lint:end");
1461
+ }
1462
+ if (config.hooks) {
1463
+ await events.emit("hooks:start");
1464
+ await executeHooks({
1465
+ hooks: config.hooks,
1466
+ events
1467
+ });
1468
+ await events.emit("hooks:end");
1469
+ }
1470
+ await events.emit("generation:summary", config, {
1471
+ failedPlugins,
1472
+ filesCreated: files.length,
1473
+ status: failedPlugins.size > 0 || error ? "failed" : "success",
1474
+ hrStart,
1475
+ pluginTimings
1476
+ });
1477
+ }
1478
+
1479
+ //#endregion
1480
+ //#region src/utils/getPlugins.ts
1481
+ function isJSONPlugins(plugins) {
1482
+ return !!plugins?.some((plugin) => {
1483
+ return Array.isArray(plugin) && typeof plugin?.at(0) === "string";
1484
+ });
1485
+ }
1486
+ function isObjectPlugins(plugins) {
1487
+ return plugins instanceof Object && !Array.isArray(plugins);
1488
+ }
1489
+ function getPlugins(plugins) {
1490
+ if (isObjectPlugins(plugins)) throw new Error("Object plugins are not supported anymore, best to use http://kubb.dev/getting-started/configure#json");
1491
+ if (isJSONPlugins(plugins)) throw new Error("JSON plugins are not supported anymore, best to use http://kubb.dev/getting-started/configure#json");
1492
+ return Promise.resolve(plugins);
1493
+ }
1494
+
1495
+ //#endregion
1496
+ //#region src/utils/getConfigs.ts
1497
+ /**
1498
+ * Converting UserConfig to Config Array without a change in the object beside the JSON convert.
1499
+ */
1500
+ async function getConfigs(result, args) {
1501
+ const config = result?.config;
1502
+ let kubbUserConfig = Promise.resolve(config);
1503
+ if (typeof config === "function") {
1504
+ const possiblePromise = config(args);
1505
+ if (isPromise(possiblePromise)) kubbUserConfig = possiblePromise;
1506
+ kubbUserConfig = Promise.resolve(possiblePromise);
1507
+ }
1508
+ let JSONConfig = await kubbUserConfig;
1509
+ if (!Array.isArray(JSONConfig)) JSONConfig = [JSONConfig];
1510
+ const results = [];
1511
+ for (const item of JSONConfig) {
1512
+ const plugins = item.plugins ? await getPlugins(item.plugins) : void 0;
1513
+ results.push({
1514
+ ...item,
1515
+ plugins
1516
+ });
1517
+ }
1518
+ return results;
1519
+ }
1520
+
1521
+ //#endregion
1522
+ //#region src/utils/getCosmiConfig.ts
1523
+ const tsLoader = async (configFile) => {
1524
+ return await createJiti(configFile, {
1525
+ jsx: {
1526
+ runtime: "automatic",
1527
+ importSource: "@kubb/react-fabric"
1528
+ },
1529
+ sourceMaps: true,
1530
+ interopDefault: true
1531
+ }).import(configFile, { default: true });
1532
+ };
1533
+ async function getCosmiConfig(moduleName, config) {
1534
+ let result;
1535
+ const searchPlaces = [
1536
+ "package.json",
1537
+ `.${moduleName}rc`,
1538
+ `.${moduleName}rc.json`,
1539
+ `.${moduleName}rc.yaml`,
1540
+ `.${moduleName}rc.yml`,
1541
+ `.${moduleName}rc.ts`,
1542
+ `.${moduleName}rc.js`,
1543
+ `.${moduleName}rc.mjs`,
1544
+ `.${moduleName}rc.cjs`,
1545
+ `${moduleName}.config.ts`,
1546
+ `${moduleName}.config.js`,
1547
+ `${moduleName}.config.mjs`,
1548
+ `${moduleName}.config.cjs`
1549
+ ];
1550
+ const explorer = cosmiconfig(moduleName, {
1551
+ cache: false,
1552
+ searchPlaces: [
1553
+ ...searchPlaces.map((searchPlace) => {
1554
+ return `.config/${searchPlace}`;
1555
+ }),
1556
+ ...searchPlaces.map((searchPlace) => {
1557
+ return `configs/${searchPlace}`;
1558
+ }),
1559
+ ...searchPlaces
1560
+ ],
1561
+ loaders: { ".ts": tsLoader }
1562
+ });
1563
+ try {
1564
+ result = config ? await explorer.load(config) : await explorer.search();
1565
+ } catch (error) {
1566
+ throw new Error("Config failed loading", { cause: error });
1567
+ }
1568
+ if (result?.isEmpty || !result || !result.config) throw new Error("Config not defined, create a kubb.config.js or pass through your config with the option --config");
1569
+ return result;
1570
+ }
1571
+
1145
1572
  //#endregion
1146
1573
  //#region src/utils/watcher.ts
1147
1574
  async function startWatcher(path$1, cb) {
@@ -1267,4 +1694,4 @@ var generate_default = command;
1267
1694
 
1268
1695
  //#endregion
1269
1696
  export { generate_default as default };
1270
- //# sourceMappingURL=generate-DhFw-owG.js.map
1697
+ //# sourceMappingURL=generate-DoM5hz_l.js.map