@kubb/cli 4.29.1 → 4.31.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 (53) hide show
  1. package/dist/{agent-BzD6f3mV.js → agent-CGYnHRU4.js} +2 -2
  2. package/dist/{agent-BzD6f3mV.js.map → agent-CGYnHRU4.js.map} +1 -1
  3. package/dist/{agent-NAhMf2ot.cjs → agent-kU5gLqqn.cjs} +2 -2
  4. package/dist/{agent-NAhMf2ot.cjs.map → agent-kU5gLqqn.cjs.map} +1 -1
  5. package/dist/{generate-CGEE6Etf.js → generate-DvoKuzJW.js} +30 -6
  6. package/dist/{generate-CGEE6Etf.js.map → generate-DvoKuzJW.js.map} +1 -1
  7. package/dist/{generate-b2shdOTg.cjs → generate-G4sRCtYd.cjs} +30 -6
  8. package/dist/generate-G4sRCtYd.cjs.map +1 -0
  9. package/dist/index.cjs +7 -7
  10. package/dist/index.js +7 -7
  11. package/dist/{init-CPrROO67.js → init-Cp7PS6R5.js} +3 -36
  12. package/dist/init-Cp7PS6R5.js.map +1 -0
  13. package/dist/{init-CaoLbJ4R.cjs → init-XsLQVNk3.cjs} +5 -38
  14. package/dist/init-XsLQVNk3.cjs.map +1 -0
  15. package/dist/{mcp-Jboea6xH.js → mcp-CD0ZKRHG.js} +18 -2
  16. package/dist/mcp-CD0ZKRHG.js.map +1 -0
  17. package/dist/{mcp-97TXkJVX.cjs → mcp-DCjAEKzU.cjs} +20 -3
  18. package/dist/mcp-DCjAEKzU.cjs.map +1 -0
  19. package/dist/package-BYVzWUJV.js +6 -0
  20. package/dist/package-BYVzWUJV.js.map +1 -0
  21. package/dist/{package-DPA0iPrU.cjs → package-BqKkzL1A.cjs} +2 -2
  22. package/dist/package-BqKkzL1A.cjs.map +1 -0
  23. package/dist/{start-lrn1-P52.cjs → start-BN1ikd53.cjs} +17 -2
  24. package/dist/start-BN1ikd53.cjs.map +1 -0
  25. package/dist/{start-CYuU23PX.js → start-VN4IxBaM.js} +17 -2
  26. package/dist/{start-CYuU23PX.js.map → start-VN4IxBaM.js.map} +1 -1
  27. package/dist/telemetry-Ccka73zO.js +149 -0
  28. package/dist/telemetry-Ccka73zO.js.map +1 -0
  29. package/dist/telemetry-DxyJ2d4j.cjs +162 -0
  30. package/dist/telemetry-DxyJ2d4j.cjs.map +1 -0
  31. package/dist/{validate-BgYhe_55.cjs → validate-BbVY6zQM.cjs} +16 -1
  32. package/dist/validate-BbVY6zQM.cjs.map +1 -0
  33. package/dist/{validate-DOeZKiGx.js → validate-zO3bvm66.js} +16 -1
  34. package/dist/validate-zO3bvm66.js.map +1 -0
  35. package/package.json +8 -7
  36. package/src/commands/agent/start.ts +6 -1
  37. package/src/commands/init.ts +2 -1
  38. package/src/commands/mcp.ts +7 -1
  39. package/src/commands/validate.ts +5 -0
  40. package/src/runners/generate.ts +28 -2
  41. package/src/utils/packageManager.ts +2 -60
  42. package/src/utils/telemetry.ts +278 -0
  43. package/dist/generate-b2shdOTg.cjs.map +0 -1
  44. package/dist/init-CPrROO67.js.map +0 -1
  45. package/dist/init-CaoLbJ4R.cjs.map +0 -1
  46. package/dist/mcp-97TXkJVX.cjs.map +0 -1
  47. package/dist/mcp-Jboea6xH.js.map +0 -1
  48. package/dist/package-1sFkRYXi.js +0 -6
  49. package/dist/package-1sFkRYXi.js.map +0 -1
  50. package/dist/package-DPA0iPrU.cjs.map +0 -1
  51. package/dist/start-lrn1-P52.cjs.map +0 -1
  52. package/dist/validate-BgYhe_55.cjs.map +0 -1
  53. package/dist/validate-DOeZKiGx.js.map +0 -1
@@ -1,5 +1,9 @@
1
1
  const require_chunk = require('./chunk-CNbaEX1y.cjs');
2
+ const require_package = require('./package-BqKkzL1A.cjs');
3
+ const require_telemetry = require('./telemetry-DxyJ2d4j.cjs');
2
4
  let citty = require("citty");
5
+ let node_process = require("node:process");
6
+ node_process = require_chunk.__toESM(node_process);
3
7
  let node_util = require("node:util");
4
8
  let jiti = require("jiti");
5
9
 
@@ -24,14 +28,27 @@ const command = (0, citty.defineCommand)({
24
28
  mod = await jiti$1.import("@kubb/mcp", { default: true });
25
29
  } catch (_e) {
26
30
  console.error(`Import of '@kubb/mcp' is required to start the MCP server`);
27
- process.exit(1);
31
+ node_process.default.exit(1);
28
32
  }
29
33
  const { run } = mod;
34
+ const hrStart = node_process.default.hrtime();
30
35
  try {
31
36
  console.log("⏳ Starting MCP server...");
32
37
  console.warn((0, node_util.styleText)("yellow", "This feature is still under development — use with caution"));
33
- await run();
38
+ run();
39
+ await require_telemetry.sendTelemetry(require_telemetry.buildTelemetryEvent({
40
+ command: "mcp",
41
+ kubbVersion: require_package.version,
42
+ hrStart,
43
+ status: "success"
44
+ }));
34
45
  } catch (error) {
46
+ await require_telemetry.sendTelemetry(require_telemetry.buildTelemetryEvent({
47
+ command: "mcp",
48
+ kubbVersion: require_package.version,
49
+ hrStart,
50
+ status: "failed"
51
+ }));
35
52
  console.error(error?.message);
36
53
  }
37
54
  }
@@ -39,4 +56,4 @@ const command = (0, citty.defineCommand)({
39
56
 
40
57
  //#endregion
41
58
  exports.default = command;
42
- //# sourceMappingURL=mcp-97TXkJVX.cjs.map
59
+ //# sourceMappingURL=mcp-DCjAEKzU.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"mcp-DCjAEKzU.cjs","names":["jiti","process","sendTelemetry","buildTelemetryEvent","version"],"sources":["../src/commands/mcp.ts"],"sourcesContent":["import process from 'node:process'\nimport { styleText } from 'node:util'\nimport type { ArgsDef } from 'citty'\nimport { defineCommand, showUsage } from 'citty'\nimport { createJiti } from 'jiti'\nimport { version } from '../../package.json'\nimport { buildTelemetryEvent, sendTelemetry } from '../utils/telemetry.ts'\n\nconst jiti = createJiti(import.meta.url, {\n sourceMaps: true,\n})\n\nconst args = {\n help: {\n type: 'boolean',\n description: 'Show help',\n alias: 'h',\n default: false,\n },\n} as const satisfies ArgsDef\n\nconst command = defineCommand({\n meta: {\n name: 'mcp',\n description: 'Start the server to enable the MCP client to interact with the LLM.',\n },\n args,\n async run(commandContext) {\n const { args } = commandContext\n\n if (args.help) {\n return showUsage(command)\n }\n\n let mod: any\n try {\n mod = await jiti.import('@kubb/mcp', { default: true })\n } catch (_e) {\n console.error(`Import of '@kubb/mcp' is required to start the MCP server`)\n process.exit(1)\n }\n\n const { run } = mod\n const hrStart = process.hrtime()\n try {\n console.log('⏳ Starting MCP server...')\n console.warn(styleText('yellow', 'This feature is still under development — use with caution'))\n run()\n await sendTelemetry(buildTelemetryEvent({ command: 'mcp', kubbVersion: version, hrStart, status: 'success' }))\n } catch (error) {\n await sendTelemetry(buildTelemetryEvent({ command: 'mcp', kubbVersion: version, hrStart, status: 'failed' }))\n console.error((error as Error)?.message)\n }\n },\n})\n\nexport default command\n"],"mappings":";;;;;;;;;;AAQA,MAAMA,6EAAmC,EACvC,YAAY,MACb,CAAC;AAWF,MAAM,mCAAwB;CAC5B,MAAM;EACJ,MAAM;EACN,aAAa;EACd;CACD,MAdW,EACX,MAAM;EACJ,MAAM;EACN,aAAa;EACb,OAAO;EACP,SAAS;EACV,EACF;CAQC,MAAM,IAAI,gBAAgB;EACxB,MAAM,EAAE,SAAS;AAEjB,MAAI,KAAK,KACP,6BAAiB,QAAQ;EAG3B,IAAI;AACJ,MAAI;AACF,SAAM,MAAMA,OAAK,OAAO,aAAa,EAAE,SAAS,MAAM,CAAC;WAChD,IAAI;AACX,WAAQ,MAAM,4DAA4D;AAC1E,wBAAQ,KAAK,EAAE;;EAGjB,MAAM,EAAE,QAAQ;EAChB,MAAM,UAAUC,qBAAQ,QAAQ;AAChC,MAAI;AACF,WAAQ,IAAI,2BAA2B;AACvC,WAAQ,8BAAe,UAAU,6DAA6D,CAAC;AAC/F,QAAK;AACL,SAAMC,gCAAcC,sCAAoB;IAAE,SAAS;IAAO,aAAaC;IAAS;IAAS,QAAQ;IAAW,CAAC,CAAC;WACvG,OAAO;AACd,SAAMF,gCAAcC,sCAAoB;IAAE,SAAS;IAAO,aAAaC;IAAS;IAAS,QAAQ;IAAU,CAAC,CAAC;AAC7G,WAAQ,MAAO,OAAiB,QAAQ;;;CAG7C,CAAC"}
@@ -0,0 +1,6 @@
1
+ //#region package.json
2
+ var version = "4.31.0";
3
+
4
+ //#endregion
5
+ export { version as t };
6
+ //# sourceMappingURL=package-BYVzWUJV.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"package-BYVzWUJV.js","names":[],"sources":["../package.json"],"sourcesContent":[""],"mappings":""}
@@ -1,6 +1,6 @@
1
1
 
2
2
  //#region package.json
3
- var version = "4.29.1";
3
+ var version = "4.31.0";
4
4
 
5
5
  //#endregion
6
6
  Object.defineProperty(exports, 'version', {
@@ -9,4 +9,4 @@ Object.defineProperty(exports, 'version', {
9
9
  return version;
10
10
  }
11
11
  });
12
- //# sourceMappingURL=package-DPA0iPrU.cjs.map
12
+ //# sourceMappingURL=package-BqKkzL1A.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"package-BqKkzL1A.cjs","names":[],"sources":["../package.json"],"sourcesContent":[""],"mappings":""}
@@ -1,4 +1,6 @@
1
1
  const require_chunk = require('./chunk-CNbaEX1y.cjs');
2
+ const require_package = require('./package-BqKkzL1A.cjs');
3
+ const require_telemetry = require('./telemetry-DxyJ2d4j.cjs');
2
4
  let citty = require("citty");
3
5
  let node_child_process = require("node:child_process");
4
6
  let node_path = require("node:path");
@@ -97,6 +99,7 @@ const command = (0, citty.defineCommand)({
97
99
  args,
98
100
  async run(commandContext) {
99
101
  const { args } = commandContext;
102
+ const hrStart = node_process.hrtime();
100
103
  try {
101
104
  const configPath = node_path.default.resolve(node_process.cwd(), args.config || "kubb.config.ts");
102
105
  const port = args.port ? Number.parseInt(args.port, 10) : 0;
@@ -104,7 +107,7 @@ const command = (0, citty.defineCommand)({
104
107
  const noCache = args["no-cache"];
105
108
  const allowWrite = args["allow-write"];
106
109
  const allowAll = args["allow-all"];
107
- await startServer({
110
+ startServer({
108
111
  port,
109
112
  host,
110
113
  configPath,
@@ -112,7 +115,19 @@ const command = (0, citty.defineCommand)({
112
115
  allowWrite,
113
116
  allowAll
114
117
  });
118
+ await require_telemetry.sendTelemetry(require_telemetry.buildTelemetryEvent({
119
+ command: "agent",
120
+ kubbVersion: require_package.version,
121
+ hrStart,
122
+ status: "success"
123
+ }));
115
124
  } catch (error) {
125
+ await require_telemetry.sendTelemetry(require_telemetry.buildTelemetryEvent({
126
+ command: "agent",
127
+ kubbVersion: require_package.version,
128
+ hrStart,
129
+ status: "failed"
130
+ }));
116
131
  _clack_prompts.log.error((0, node_util.styleText)("red", "Failed to start agent server"));
117
132
  console.error(error);
118
133
  node_process.exit(1);
@@ -122,4 +137,4 @@ const command = (0, citty.defineCommand)({
122
137
 
123
138
  //#endregion
124
139
  exports.default = command;
125
- //# sourceMappingURL=start-lrn1-P52.cjs.map
140
+ //# sourceMappingURL=start-BN1ikd53.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"start-BN1ikd53.cjs","names":["path","process","sendTelemetry","buildTelemetryEvent","version"],"sources":["../src/commands/agent/start.ts"],"sourcesContent":["import { spawn } from 'node:child_process'\nimport path from 'node:path'\nimport * as process from 'node:process'\nimport { fileURLToPath } from 'node:url'\nimport { styleText } from 'node:util'\nimport * as clack from '@clack/prompts'\nimport type { ArgsDef } from 'citty'\nimport { defineCommand } from 'citty'\nimport { version } from '../../../package.json'\nimport { buildTelemetryEvent, sendTelemetry } from '../../utils/telemetry.ts'\n\nconst args = {\n config: {\n type: 'string',\n description: 'Path to the Kubb config',\n alias: 'c',\n },\n port: {\n type: 'string',\n description: 'Port for the server. If not specified, an available port is automatically selected.',\n alias: 'p',\n },\n host: {\n type: 'string',\n description: 'Host for the server',\n default: 'localhost',\n },\n 'no-cache': {\n type: 'boolean',\n description: 'Disable session caching',\n default: false,\n },\n 'allow-write': {\n type: 'boolean',\n description: 'Allow writing generated files to the filesystem. When not set, no files are written and the config patch is not persisted.',\n default: false,\n },\n 'allow-all': {\n type: 'boolean',\n description: 'Grant all permissions (implies --allow-write).',\n default: false,\n },\n} as const satisfies ArgsDef\n\ntype StartServerProps = {\n port: number\n host: string\n configPath: string\n noCache: boolean\n allowWrite: boolean\n allowAll: boolean\n}\n\nasync function startServer({ port, host, configPath, noCache, allowWrite, allowAll }: StartServerProps): Promise<void> {\n try {\n // Load .env file into process.env using Node.js built-in (v20.12.0+)\n try {\n process.loadEnvFile()\n } catch {\n // .env file may not exist; ignore\n }\n\n // Resolve the @kubb/agent package path\n const agentPkgUrl = import.meta.resolve('@kubb/agent/package.json')\n const agentPkgPath = fileURLToPath(agentPkgUrl)\n const agentDir = path.dirname(agentPkgPath)\n const serverPath = path.join(agentDir, '.output', 'server', 'index.mjs')\n\n // nitro env\n const PORT = process.env.PORT || (port === 0 ? '3000' : String(port))\n const HOST = process.env.HOST || host || '0.0.0.0'\n\n // kubb env\n const KUBB_AGENT_ROOT = process.env.KUBB_AGENT_ROOT || process.cwd()\n const KUBB_AGENT_CONFIG = process.env.KUBB_AGENT_CONFIG || configPath || 'kubb.config.ts'\n const KUBB_AGENT_NO_CACHE = noCache ? 'true' : 'false'\n const KUBB_AGENT_ALLOW_WRITE = allowAll || allowWrite ? 'true' : (process.env.KUBB_AGENT_ALLOW_WRITE ?? 'false')\n const KUBB_AGENT_ALLOW_ALL = allowAll ? 'true' : (process.env.KUBB_AGENT_ALLOW_ALL ?? 'false')\n const KUBB_AGENT_TOKEN = process.env.KUBB_AGENT_TOKEN\n const KUBB_AGENT_RETRY_TIMEOUT = process.env.KUBB_AGENT_RETRY_TIMEOUT || '30000'\n const KUBB_STUDIO_URL = process.env.KUBB_STUDIO_URL || 'https://studio.kubb.dev'\n\n // Set environment variables\n const env = {\n PORT,\n HOST,\n KUBB_AGENT_ROOT,\n KUBB_AGENT_CONFIG,\n KUBB_AGENT_NO_CACHE,\n KUBB_AGENT_ALLOW_WRITE,\n KUBB_AGENT_ALLOW_ALL,\n KUBB_AGENT_TOKEN,\n KUBB_AGENT_RETRY_TIMEOUT,\n KUBB_STUDIO_URL,\n }\n\n clack.log.step(styleText('cyan', 'Starting agent server...'))\n clack.log.info(styleText('dim', `Config: ${KUBB_AGENT_CONFIG}`))\n clack.log.info(styleText('dim', `Host: ${HOST}`))\n clack.log.info(styleText('dim', `Port: ${PORT}`))\n if (noCache) {\n clack.log.info(styleText('dim', 'Session caching: disabled'))\n }\n if (!KUBB_AGENT_ALLOW_WRITE && !KUBB_AGENT_ALLOW_ALL) {\n clack.log.warn(styleText('yellow', 'Filesystem writes disabled. Use --allow-write or --allow-all to enable.'))\n }\n\n spawn('node', [serverPath], {\n env: { ...process.env, ...env },\n stdio: 'inherit',\n cwd: process.cwd(),\n })\n } catch (error) {\n console.error('Failed to start agent server:', error)\n process.exit(1)\n }\n}\n\nconst command = defineCommand({\n meta: {\n name: 'start',\n description: 'Start the Agent server',\n },\n args,\n async run(commandContext) {\n const { args } = commandContext\n const hrStart = process.hrtime()\n\n try {\n const configPath = path.resolve(process.cwd(), args.config || 'kubb.config.ts')\n const port = args.port ? Number.parseInt(args.port, 10) : 0\n const host = args.host\n const noCache = args['no-cache']\n const allowWrite = args['allow-write']\n const allowAll = args['allow-all']\n\n startServer({ port, host, configPath, noCache, allowWrite, allowAll })\n await sendTelemetry(buildTelemetryEvent({ command: 'agent', kubbVersion: version, hrStart, status: 'success' }))\n } catch (error) {\n await sendTelemetry(buildTelemetryEvent({ command: 'agent', kubbVersion: version, hrStart, status: 'failed' }))\n clack.log.error(styleText('red', 'Failed to start agent server'))\n console.error(error)\n process.exit(1)\n }\n },\n})\n\nexport default command\n"],"mappings":"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"}
@@ -1,4 +1,6 @@
1
1
  import { t as __name } from "./chunk-DKWOrOAv.js";
2
+ import { t as version } from "./package-BYVzWUJV.js";
3
+ import { n as sendTelemetry, t as buildTelemetryEvent } from "./telemetry-Ccka73zO.js";
2
4
  import { defineCommand } from "citty";
3
5
  import { spawn } from "node:child_process";
4
6
  import path from "node:path";
@@ -94,6 +96,7 @@ const command = defineCommand({
94
96
  args,
95
97
  async run(commandContext) {
96
98
  const { args } = commandContext;
99
+ const hrStart = process$1.hrtime();
97
100
  try {
98
101
  const configPath = path.resolve(process$1.cwd(), args.config || "kubb.config.ts");
99
102
  const port = args.port ? Number.parseInt(args.port, 10) : 0;
@@ -101,7 +104,7 @@ const command = defineCommand({
101
104
  const noCache = args["no-cache"];
102
105
  const allowWrite = args["allow-write"];
103
106
  const allowAll = args["allow-all"];
104
- await startServer({
107
+ startServer({
105
108
  port,
106
109
  host,
107
110
  configPath,
@@ -109,7 +112,19 @@ const command = defineCommand({
109
112
  allowWrite,
110
113
  allowAll
111
114
  });
115
+ await sendTelemetry(buildTelemetryEvent({
116
+ command: "agent",
117
+ kubbVersion: version,
118
+ hrStart,
119
+ status: "success"
120
+ }));
112
121
  } catch (error) {
122
+ await sendTelemetry(buildTelemetryEvent({
123
+ command: "agent",
124
+ kubbVersion: version,
125
+ hrStart,
126
+ status: "failed"
127
+ }));
113
128
  clack.log.error(styleText("red", "Failed to start agent server"));
114
129
  console.error(error);
115
130
  process$1.exit(1);
@@ -119,4 +134,4 @@ const command = defineCommand({
119
134
 
120
135
  //#endregion
121
136
  export { command as default };
122
- //# sourceMappingURL=start-CYuU23PX.js.map
137
+ //# sourceMappingURL=start-VN4IxBaM.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"start-CYuU23PX.js","names":["process"],"sources":["../src/commands/agent/start.ts"],"sourcesContent":["import { spawn } from 'node:child_process'\nimport path from 'node:path'\nimport * as process from 'node:process'\nimport { fileURLToPath } from 'node:url'\nimport { styleText } from 'node:util'\nimport * as clack from '@clack/prompts'\nimport type { ArgsDef } from 'citty'\nimport { defineCommand } from 'citty'\n\nconst args = {\n config: {\n type: 'string',\n description: 'Path to the Kubb config',\n alias: 'c',\n },\n port: {\n type: 'string',\n description: 'Port for the server. If not specified, an available port is automatically selected.',\n alias: 'p',\n },\n host: {\n type: 'string',\n description: 'Host for the server',\n default: 'localhost',\n },\n 'no-cache': {\n type: 'boolean',\n description: 'Disable session caching',\n default: false,\n },\n 'allow-write': {\n type: 'boolean',\n description: 'Allow writing generated files to the filesystem. When not set, no files are written and the config patch is not persisted.',\n default: false,\n },\n 'allow-all': {\n type: 'boolean',\n description: 'Grant all permissions (implies --allow-write).',\n default: false,\n },\n} as const satisfies ArgsDef\n\ntype StartServerProps = {\n port: number\n host: string\n configPath: string\n noCache: boolean\n allowWrite: boolean\n allowAll: boolean\n}\n\nasync function startServer({ port, host, configPath, noCache, allowWrite, allowAll }: StartServerProps): Promise<void> {\n try {\n // Load .env file into process.env using Node.js built-in (v20.12.0+)\n try {\n process.loadEnvFile()\n } catch {\n // .env file may not exist; ignore\n }\n\n // Resolve the @kubb/agent package path\n const agentPkgUrl = import.meta.resolve('@kubb/agent/package.json')\n const agentPkgPath = fileURLToPath(agentPkgUrl)\n const agentDir = path.dirname(agentPkgPath)\n const serverPath = path.join(agentDir, '.output', 'server', 'index.mjs')\n\n // nitro env\n const PORT = process.env.PORT || (port === 0 ? '3000' : String(port))\n const HOST = process.env.HOST || host || '0.0.0.0'\n\n // kubb env\n const KUBB_AGENT_ROOT = process.env.KUBB_AGENT_ROOT || process.cwd()\n const KUBB_AGENT_CONFIG = process.env.KUBB_AGENT_CONFIG || configPath || 'kubb.config.ts'\n const KUBB_AGENT_NO_CACHE = noCache ? 'true' : 'false'\n const KUBB_AGENT_ALLOW_WRITE = allowAll || allowWrite ? 'true' : (process.env.KUBB_AGENT_ALLOW_WRITE ?? 'false')\n const KUBB_AGENT_ALLOW_ALL = allowAll ? 'true' : (process.env.KUBB_AGENT_ALLOW_ALL ?? 'false')\n const KUBB_AGENT_TOKEN = process.env.KUBB_AGENT_TOKEN\n const KUBB_AGENT_RETRY_TIMEOUT = process.env.KUBB_AGENT_RETRY_TIMEOUT || '30000'\n const KUBB_STUDIO_URL = process.env.KUBB_STUDIO_URL || 'https://studio.kubb.dev'\n\n // Set environment variables\n const env = {\n PORT,\n HOST,\n KUBB_AGENT_ROOT,\n KUBB_AGENT_CONFIG,\n KUBB_AGENT_NO_CACHE,\n KUBB_AGENT_ALLOW_WRITE,\n KUBB_AGENT_ALLOW_ALL,\n KUBB_AGENT_TOKEN,\n KUBB_AGENT_RETRY_TIMEOUT,\n KUBB_STUDIO_URL,\n }\n\n clack.log.step(styleText('cyan', 'Starting agent server...'))\n clack.log.info(styleText('dim', `Config: ${KUBB_AGENT_CONFIG}`))\n clack.log.info(styleText('dim', `Host: ${HOST}`))\n clack.log.info(styleText('dim', `Port: ${PORT}`))\n if (noCache) {\n clack.log.info(styleText('dim', 'Session caching: disabled'))\n }\n if (!KUBB_AGENT_ALLOW_WRITE && !KUBB_AGENT_ALLOW_ALL) {\n clack.log.warn(styleText('yellow', 'Filesystem writes disabled. Use --allow-write or --allow-all to enable.'))\n }\n\n spawn('node', [serverPath], {\n env: { ...process.env, ...env },\n stdio: 'inherit',\n cwd: process.cwd(),\n })\n } catch (error) {\n console.error('Failed to start agent server:', error)\n process.exit(1)\n }\n}\n\nconst command = defineCommand({\n meta: {\n name: 'start',\n description: 'Start the Agent server',\n },\n args,\n async run(commandContext) {\n const { args } = commandContext\n\n try {\n const configPath = path.resolve(process.cwd(), args.config || 'kubb.config.ts')\n const port = args.port ? Number.parseInt(args.port, 10) : 0\n const host = args.host\n const noCache = args['no-cache']\n const allowWrite = args['allow-write']\n const allowAll = args['allow-all']\n\n await startServer({ port, host, configPath, noCache, allowWrite, allowAll })\n } catch (error) {\n clack.log.error(styleText('red', 'Failed to start agent server'))\n console.error(error)\n process.exit(1)\n }\n },\n})\n\nexport default command\n"],"mappings":";;;;;;;;;;AASA,MAAM,OAAO;CACX,QAAQ;EACN,MAAM;EACN,aAAa;EACb,OAAO;EACR;CACD,MAAM;EACJ,MAAM;EACN,aAAa;EACb,OAAO;EACR;CACD,MAAM;EACJ,MAAM;EACN,aAAa;EACb,SAAS;EACV;CACD,YAAY;EACV,MAAM;EACN,aAAa;EACb,SAAS;EACV;CACD,eAAe;EACb,MAAM;EACN,aAAa;EACb,SAAS;EACV;CACD,aAAa;EACX,MAAM;EACN,aAAa;EACb,SAAS;EACV;CACF;AAWD,eAAe,YAAY,EAAE,MAAM,MAAM,YAAY,SAAS,YAAY,YAA6C;AACrH,KAAI;AAEF,MAAI;AACF,aAAQ,aAAa;UACf;EAMR,MAAM,eAAe,cADD,OAAO,KAAK,QAAQ,2BAA2B,CACpB;EAC/C,MAAM,WAAW,KAAK,QAAQ,aAAa;EAC3C,MAAM,aAAa,KAAK,KAAK,UAAU,WAAW,UAAU,YAAY;EAGxE,MAAM,OAAOA,UAAQ,IAAI,SAAS,SAAS,IAAI,SAAS,OAAO,KAAK;EACpE,MAAM,OAAOA,UAAQ,IAAI,QAAQ,QAAQ;EAGzC,MAAM,kBAAkBA,UAAQ,IAAI,mBAAmBA,UAAQ,KAAK;EACpE,MAAM,oBAAoBA,UAAQ,IAAI,qBAAqB,cAAc;EACzE,MAAM,sBAAsB,UAAU,SAAS;EAC/C,MAAM,yBAAyB,YAAY,aAAa,SAAUA,UAAQ,IAAI,0BAA0B;EACxG,MAAM,uBAAuB,WAAW,SAAUA,UAAQ,IAAI,wBAAwB;EAMtF,MAAM,MAAM;GACV;GACA;GACA;GACA;GACA;GACA;GACA;GACA,kBAbuBA,UAAQ,IAAI;GAcnC,0BAb+BA,UAAQ,IAAI,4BAA4B;GAcvE,iBAbsBA,UAAQ,IAAI,mBAAmB;GActD;AAED,QAAM,IAAI,KAAK,UAAU,QAAQ,2BAA2B,CAAC;AAC7D,QAAM,IAAI,KAAK,UAAU,OAAO,WAAW,oBAAoB,CAAC;AAChE,QAAM,IAAI,KAAK,UAAU,OAAO,SAAS,OAAO,CAAC;AACjD,QAAM,IAAI,KAAK,UAAU,OAAO,SAAS,OAAO,CAAC;AACjD,MAAI,QACF,OAAM,IAAI,KAAK,UAAU,OAAO,4BAA4B,CAAC;AAE/D,MAAI,CAAC,0BAA0B,CAAC,qBAC9B,OAAM,IAAI,KAAK,UAAU,UAAU,0EAA0E,CAAC;AAGhH,QAAM,QAAQ,CAAC,WAAW,EAAE;GAC1B,KAAK;IAAE,GAAGA,UAAQ;IAAK,GAAG;IAAK;GAC/B,OAAO;GACP,KAAKA,UAAQ,KAAK;GACnB,CAAC;UACK,OAAO;AACd,UAAQ,MAAM,iCAAiC,MAAM;AACrD,YAAQ,KAAK,EAAE;;;AAInB,MAAM,UAAU,cAAc;CAC5B,MAAM;EACJ,MAAM;EACN,aAAa;EACd;CACD;CACA,MAAM,IAAI,gBAAgB;EACxB,MAAM,EAAE,SAAS;AAEjB,MAAI;GACF,MAAM,aAAa,KAAK,QAAQA,UAAQ,KAAK,EAAE,KAAK,UAAU,iBAAiB;GAC/E,MAAM,OAAO,KAAK,OAAO,OAAO,SAAS,KAAK,MAAM,GAAG,GAAG;GAC1D,MAAM,OAAO,KAAK;GAClB,MAAM,UAAU,KAAK;GACrB,MAAM,aAAa,KAAK;GACxB,MAAM,WAAW,KAAK;AAEtB,SAAM,YAAY;IAAE;IAAM;IAAM;IAAY;IAAS;IAAY;IAAU,CAAC;WACrE,OAAO;AACd,SAAM,IAAI,MAAM,UAAU,OAAO,+BAA+B,CAAC;AACjE,WAAQ,MAAM,MAAM;AACpB,aAAQ,KAAK,EAAE;;;CAGpB,CAAC"}
1
+ {"version":3,"file":"start-VN4IxBaM.js","names":["process"],"sources":["../src/commands/agent/start.ts"],"sourcesContent":["import { spawn } from 'node:child_process'\nimport path from 'node:path'\nimport * as process from 'node:process'\nimport { fileURLToPath } from 'node:url'\nimport { styleText } from 'node:util'\nimport * as clack from '@clack/prompts'\nimport type { ArgsDef } from 'citty'\nimport { defineCommand } from 'citty'\nimport { version } from '../../../package.json'\nimport { buildTelemetryEvent, sendTelemetry } from '../../utils/telemetry.ts'\n\nconst args = {\n config: {\n type: 'string',\n description: 'Path to the Kubb config',\n alias: 'c',\n },\n port: {\n type: 'string',\n description: 'Port for the server. If not specified, an available port is automatically selected.',\n alias: 'p',\n },\n host: {\n type: 'string',\n description: 'Host for the server',\n default: 'localhost',\n },\n 'no-cache': {\n type: 'boolean',\n description: 'Disable session caching',\n default: false,\n },\n 'allow-write': {\n type: 'boolean',\n description: 'Allow writing generated files to the filesystem. When not set, no files are written and the config patch is not persisted.',\n default: false,\n },\n 'allow-all': {\n type: 'boolean',\n description: 'Grant all permissions (implies --allow-write).',\n default: false,\n },\n} as const satisfies ArgsDef\n\ntype StartServerProps = {\n port: number\n host: string\n configPath: string\n noCache: boolean\n allowWrite: boolean\n allowAll: boolean\n}\n\nasync function startServer({ port, host, configPath, noCache, allowWrite, allowAll }: StartServerProps): Promise<void> {\n try {\n // Load .env file into process.env using Node.js built-in (v20.12.0+)\n try {\n process.loadEnvFile()\n } catch {\n // .env file may not exist; ignore\n }\n\n // Resolve the @kubb/agent package path\n const agentPkgUrl = import.meta.resolve('@kubb/agent/package.json')\n const agentPkgPath = fileURLToPath(agentPkgUrl)\n const agentDir = path.dirname(agentPkgPath)\n const serverPath = path.join(agentDir, '.output', 'server', 'index.mjs')\n\n // nitro env\n const PORT = process.env.PORT || (port === 0 ? '3000' : String(port))\n const HOST = process.env.HOST || host || '0.0.0.0'\n\n // kubb env\n const KUBB_AGENT_ROOT = process.env.KUBB_AGENT_ROOT || process.cwd()\n const KUBB_AGENT_CONFIG = process.env.KUBB_AGENT_CONFIG || configPath || 'kubb.config.ts'\n const KUBB_AGENT_NO_CACHE = noCache ? 'true' : 'false'\n const KUBB_AGENT_ALLOW_WRITE = allowAll || allowWrite ? 'true' : (process.env.KUBB_AGENT_ALLOW_WRITE ?? 'false')\n const KUBB_AGENT_ALLOW_ALL = allowAll ? 'true' : (process.env.KUBB_AGENT_ALLOW_ALL ?? 'false')\n const KUBB_AGENT_TOKEN = process.env.KUBB_AGENT_TOKEN\n const KUBB_AGENT_RETRY_TIMEOUT = process.env.KUBB_AGENT_RETRY_TIMEOUT || '30000'\n const KUBB_STUDIO_URL = process.env.KUBB_STUDIO_URL || 'https://studio.kubb.dev'\n\n // Set environment variables\n const env = {\n PORT,\n HOST,\n KUBB_AGENT_ROOT,\n KUBB_AGENT_CONFIG,\n KUBB_AGENT_NO_CACHE,\n KUBB_AGENT_ALLOW_WRITE,\n KUBB_AGENT_ALLOW_ALL,\n KUBB_AGENT_TOKEN,\n KUBB_AGENT_RETRY_TIMEOUT,\n KUBB_STUDIO_URL,\n }\n\n clack.log.step(styleText('cyan', 'Starting agent server...'))\n clack.log.info(styleText('dim', `Config: ${KUBB_AGENT_CONFIG}`))\n clack.log.info(styleText('dim', `Host: ${HOST}`))\n clack.log.info(styleText('dim', `Port: ${PORT}`))\n if (noCache) {\n clack.log.info(styleText('dim', 'Session caching: disabled'))\n }\n if (!KUBB_AGENT_ALLOW_WRITE && !KUBB_AGENT_ALLOW_ALL) {\n clack.log.warn(styleText('yellow', 'Filesystem writes disabled. Use --allow-write or --allow-all to enable.'))\n }\n\n spawn('node', [serverPath], {\n env: { ...process.env, ...env },\n stdio: 'inherit',\n cwd: process.cwd(),\n })\n } catch (error) {\n console.error('Failed to start agent server:', error)\n process.exit(1)\n }\n}\n\nconst command = defineCommand({\n meta: {\n name: 'start',\n description: 'Start the Agent server',\n },\n args,\n async run(commandContext) {\n const { args } = commandContext\n const hrStart = process.hrtime()\n\n try {\n const configPath = path.resolve(process.cwd(), args.config || 'kubb.config.ts')\n const port = args.port ? Number.parseInt(args.port, 10) : 0\n const host = args.host\n const noCache = args['no-cache']\n const allowWrite = args['allow-write']\n const allowAll = args['allow-all']\n\n startServer({ port, host, configPath, noCache, allowWrite, allowAll })\n await sendTelemetry(buildTelemetryEvent({ command: 'agent', kubbVersion: version, hrStart, status: 'success' }))\n } catch (error) {\n await sendTelemetry(buildTelemetryEvent({ command: 'agent', kubbVersion: version, hrStart, status: 'failed' }))\n clack.log.error(styleText('red', 'Failed to start agent server'))\n console.error(error)\n process.exit(1)\n }\n },\n})\n\nexport default command\n"],"mappings":"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"}
@@ -0,0 +1,149 @@
1
+ import { t as __name } from "./chunk-DKWOrOAv.js";
2
+ import process from "node:process";
3
+ import { randomBytes } from "node:crypto";
4
+ import os from "node:os";
5
+ import { executeIfOnline } from "@kubb/core/utils";
6
+
7
+ //#region src/utils/telemetry.ts
8
+ const OTLP_ENDPOINT = "https://otlp.kubb.dev";
9
+ /**
10
+ * Detect whether the current process is running inside a CI environment by
11
+ * checking the well-known environment variables set by all major CI systems.
12
+ */
13
+ function isCi() {
14
+ return !!(process.env["CI"] || process.env["GITHUB_ACTIONS"] || process.env["GITLAB_CI"] || process.env["BITBUCKET_BUILD_NUMBER"] || process.env["JENKINS_URL"] || process.env["CIRCLECI"] || process.env["TRAVIS"] || process.env["TEAMCITY_VERSION"] || process.env["BUILDKITE"] || process.env["TF_BUILD"]);
15
+ }
16
+ /**
17
+ * Check if telemetry is disabled via DO_NOT_TRACK or KUBB_DISABLE_TELEMETRY.
18
+ * Respects the standard DO_NOT_TRACK convention used across development tools.
19
+ */
20
+ function isTelemetryDisabled() {
21
+ return process.env["DO_NOT_TRACK"] === "1" || process.env["DO_NOT_TRACK"] === "true" || process.env["KUBB_DISABLE_TELEMETRY"] === "1" || process.env["KUBB_DISABLE_TELEMETRY"] === "true";
22
+ }
23
+ /**
24
+ * Convert a TelemetryEvent into an OTLP-compatible JSON trace payload.
25
+ * See https://opentelemetry.io/docs/languages/sdk-configuration/otlp-exporter/
26
+ */
27
+ function buildOtlpPayload(event) {
28
+ const traceId = randomBytes(16).toString("hex");
29
+ const spanId = randomBytes(8).toString("hex");
30
+ const endTimeNs = BigInt(Date.now()) * 1000000n;
31
+ const startTimeNs = endTimeNs - BigInt(event.duration) * 1000000n;
32
+ const attributes = [
33
+ {
34
+ key: "kubb.command",
35
+ value: { stringValue: event.command }
36
+ },
37
+ {
38
+ key: "kubb.version",
39
+ value: { stringValue: event.kubbVersion }
40
+ },
41
+ {
42
+ key: "kubb.node_version",
43
+ value: { stringValue: event.nodeVersion }
44
+ },
45
+ {
46
+ key: "kubb.platform",
47
+ value: { stringValue: event.platform }
48
+ },
49
+ {
50
+ key: "kubb.ci",
51
+ value: { boolValue: event.ci }
52
+ },
53
+ {
54
+ key: "kubb.files_created",
55
+ value: { intValue: event.filesCreated }
56
+ },
57
+ {
58
+ key: "kubb.status",
59
+ value: { stringValue: event.status }
60
+ },
61
+ {
62
+ key: "kubb.plugins",
63
+ value: { arrayValue: { values: event.plugins.map((p) => ({ kvlistValue: { values: [{
64
+ key: "name",
65
+ value: { stringValue: p.name }
66
+ }, {
67
+ key: "options",
68
+ value: { stringValue: JSON.stringify(p.options) }
69
+ }] } })) } }
70
+ }
71
+ ];
72
+ return { resourceSpans: [{
73
+ resource: { attributes: [
74
+ {
75
+ key: "service.name",
76
+ value: { stringValue: "kubb-cli" }
77
+ },
78
+ {
79
+ key: "service.version",
80
+ value: { stringValue: event.kubbVersion }
81
+ },
82
+ {
83
+ key: "telemetry.sdk.language",
84
+ value: { stringValue: "nodejs" }
85
+ }
86
+ ] },
87
+ scopeSpans: [{
88
+ scope: {
89
+ name: "kubb-cli",
90
+ version: event.kubbVersion
91
+ },
92
+ spans: [{
93
+ traceId,
94
+ spanId,
95
+ name: event.command,
96
+ kind: 1,
97
+ startTimeUnixNano: String(startTimeNs),
98
+ endTimeUnixNano: String(endTimeNs),
99
+ attributes,
100
+ status: { code: event.status === "success" ? 1 : 2 }
101
+ }]
102
+ }]
103
+ }] };
104
+ }
105
+ /**
106
+ * Send an anonymous telemetry event to the Kubb OTLP endpoint.
107
+ * Respects DO_NOT_TRACK and KUBB_DISABLE_TELEMETRY environment variables.
108
+ * Fails silently to never interrupt the generation process.
109
+ */
110
+ async function sendTelemetry(event) {
111
+ if (isTelemetryDisabled()) return;
112
+ await executeIfOnline(async () => {
113
+ try {
114
+ await fetch(`${OTLP_ENDPOINT}/v1/traces`, {
115
+ method: "POST",
116
+ headers: {
117
+ "Content-Type": "application/json",
118
+ "Kubb-Telemetry-Version": "1",
119
+ "Kubb-Telemetry-Source": "kubb-cli"
120
+ },
121
+ body: JSON.stringify(buildOtlpPayload(event)),
122
+ signal: AbortSignal.timeout(5e3)
123
+ });
124
+ } catch (_e) {}
125
+ });
126
+ }
127
+ /**
128
+ * Build an anonymous telemetry payload from a completed generation run.
129
+ * No file paths, OpenAPI specs, or secrets are included.
130
+ */
131
+ function buildTelemetryEvent(options) {
132
+ const [seconds, nanoseconds] = process.hrtime(options.hrStart);
133
+ const duration = Math.round(seconds * 1e3 + nanoseconds / 1e6);
134
+ return {
135
+ command: options.command,
136
+ kubbVersion: options.kubbVersion,
137
+ nodeVersion: process.versions.node.split(".")[0] ?? "unknown",
138
+ platform: os.platform(),
139
+ ci: isCi(),
140
+ plugins: options.plugins ?? [],
141
+ duration,
142
+ filesCreated: options.filesCreated ?? 0,
143
+ status: options.status
144
+ };
145
+ }
146
+
147
+ //#endregion
148
+ export { sendTelemetry as n, buildTelemetryEvent as t };
149
+ //# sourceMappingURL=telemetry-Ccka73zO.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"telemetry-Ccka73zO.js","names":[],"sources":["../src/utils/telemetry.ts"],"sourcesContent":["import { randomBytes } from 'node:crypto'\nimport os from 'node:os'\nimport process from 'node:process'\nimport { executeIfOnline } from '@kubb/core/utils'\n\nconst OTLP_ENDPOINT = 'https://otlp.kubb.dev'\n\n// ---------------------------------------------------------------------------\n// OpenTelemetry OTLP JSON types\n// https://github.com/open-telemetry/opentelemetry-proto/blob/main/opentelemetry/proto/trace/v1/trace.proto\n// https://github.com/open-telemetry/opentelemetry-proto/blob/main/opentelemetry/proto/common/v1/common.proto\n// ---------------------------------------------------------------------------\n\ntype OtlpStringValue = { stringValue: string }\ntype OtlpBoolValue = { boolValue: boolean }\ntype OtlpIntValue = { intValue: number }\ntype OtlpDoubleValue = { doubleValue: number }\ntype OtlpBytesValue = { bytesValue: string }\ntype OtlpArrayValue = { arrayValue: { values: OtlpAnyValue[] } }\ntype OtlpKvListValue = { kvlistValue: { values: OtlpKeyValue[] } }\n\ntype OtlpAnyValue = OtlpStringValue | OtlpBoolValue | OtlpIntValue | OtlpDoubleValue | OtlpBytesValue | OtlpArrayValue | OtlpKvListValue\n\ntype OtlpKeyValue = {\n key: string\n value: OtlpAnyValue\n}\n\ntype OtlpResource = {\n attributes: OtlpKeyValue[]\n droppedAttributesCount?: number\n}\n\ntype OtlpInstrumentationScope = {\n name: string\n version?: string\n attributes?: OtlpKeyValue[]\n droppedAttributesCount?: number\n}\n\n/** https://github.com/open-telemetry/opentelemetry-proto/blob/main/opentelemetry/proto/trace/v1/trace.proto#L103 */\ntype OtlpSpanKind = 0 | 1 | 2 | 3 | 4 | 5\n\n/** 0 = STATUS_CODE_UNSET, 1 = STATUS_CODE_OK, 2 = STATUS_CODE_ERROR */\ntype OtlpStatusCode = 0 | 1 | 2\n\ntype OtlpStatus = {\n code: OtlpStatusCode\n message?: string\n}\n\ntype OtlpSpan = {\n traceId: string\n spanId: string\n traceState?: string\n parentSpanId?: string\n name: string\n kind: OtlpSpanKind\n startTimeUnixNano: string\n endTimeUnixNano: string\n attributes?: OtlpKeyValue[]\n droppedAttributesCount?: number\n events?: OtlpSpanEvent[]\n droppedEventsCount?: number\n links?: OtlpSpanLink[]\n droppedLinksCount?: number\n status?: OtlpStatus\n}\n\ntype OtlpSpanEvent = {\n timeUnixNano: string\n name: string\n attributes?: OtlpKeyValue[]\n droppedAttributesCount?: number\n}\n\ntype OtlpSpanLink = {\n traceId: string\n spanId: string\n traceState?: string\n attributes?: OtlpKeyValue[]\n droppedAttributesCount?: number\n}\n\ntype OtlpScopeSpans = {\n scope: OtlpInstrumentationScope\n spans: OtlpSpan[]\n schemaUrl?: string\n}\n\ntype OtlpResourceSpans = {\n resource: OtlpResource\n scopeSpans: OtlpScopeSpans[]\n schemaUrl?: string\n}\n\n/** Root payload sent to POST /v1/traces */\nexport type OtlpExportTraceServiceRequest = {\n resourceSpans: OtlpResourceSpans[]\n}\n\n// ---------------------------------------------------------------------------\n\nexport type TelemetryPlugin = {\n name: string\n options: Record<string, unknown>\n}\n\nexport type TelemetryEvent = {\n command: string\n kubbVersion: string\n nodeVersion: string\n platform: string\n ci: boolean\n plugins: TelemetryPlugin[]\n duration: number\n filesCreated: number\n status: 'success' | 'failed'\n}\n\n/**\n * Detect whether the current process is running inside a CI environment by\n * checking the well-known environment variables set by all major CI systems.\n */\nexport function isCi(): boolean {\n return !!(\n (\n process.env['CI'] || // Generic (GitHub Actions, GitLab CI, CircleCI, Travis CI, etc.)\n process.env['GITHUB_ACTIONS'] || // GitHub Actions\n process.env['GITLAB_CI'] || // GitLab CI\n process.env['BITBUCKET_BUILD_NUMBER'] || // Bitbucket Pipelines\n process.env['JENKINS_URL'] || // Jenkins\n process.env['CIRCLECI'] || // CircleCI\n process.env['TRAVIS'] || // Travis CI\n process.env['TEAMCITY_VERSION'] || // TeamCity\n process.env['BUILDKITE'] || // Buildkite\n process.env['TF_BUILD']\n ) // Azure Pipelines\n )\n}\n\n/**\n * Check if telemetry is disabled via DO_NOT_TRACK or KUBB_DISABLE_TELEMETRY.\n * Respects the standard DO_NOT_TRACK convention used across development tools.\n */\nexport function isTelemetryDisabled(): boolean {\n return (\n process.env['DO_NOT_TRACK'] === '1' ||\n process.env['DO_NOT_TRACK'] === 'true' ||\n process.env['KUBB_DISABLE_TELEMETRY'] === '1' ||\n process.env['KUBB_DISABLE_TELEMETRY'] === 'true'\n )\n}\n\n/**\n * Convert a TelemetryEvent into an OTLP-compatible JSON trace payload.\n * See https://opentelemetry.io/docs/languages/sdk-configuration/otlp-exporter/\n */\nexport function buildOtlpPayload(event: TelemetryEvent): OtlpExportTraceServiceRequest {\n const traceId = randomBytes(16).toString('hex')\n const spanId = randomBytes(8).toString('hex')\n const endTimeNs = BigInt(Date.now()) * 1_000_000n\n const startTimeNs = endTimeNs - BigInt(event.duration) * 1_000_000n\n\n const attributes: OtlpKeyValue[] = [\n { key: 'kubb.command', value: { stringValue: event.command } },\n { key: 'kubb.version', value: { stringValue: event.kubbVersion } },\n { key: 'kubb.node_version', value: { stringValue: event.nodeVersion } },\n { key: 'kubb.platform', value: { stringValue: event.platform } },\n { key: 'kubb.ci', value: { boolValue: event.ci } },\n { key: 'kubb.files_created', value: { intValue: event.filesCreated } },\n { key: 'kubb.status', value: { stringValue: event.status } },\n {\n key: 'kubb.plugins',\n value: {\n arrayValue: {\n values: event.plugins.map(\n (p): OtlpKvListValue => ({\n kvlistValue: {\n values: [\n { key: 'name', value: { stringValue: p.name } },\n { key: 'options', value: { stringValue: JSON.stringify(p.options) } },\n ],\n },\n }),\n ),\n },\n },\n },\n ]\n\n return {\n resourceSpans: [\n {\n resource: {\n attributes: [\n { key: 'service.name', value: { stringValue: 'kubb-cli' } },\n { key: 'service.version', value: { stringValue: event.kubbVersion } },\n { key: 'telemetry.sdk.language', value: { stringValue: 'nodejs' } },\n ],\n },\n scopeSpans: [\n {\n scope: { name: 'kubb-cli', version: event.kubbVersion },\n spans: [\n {\n traceId,\n spanId,\n name: event.command,\n kind: 1 satisfies OtlpSpanKind,\n startTimeUnixNano: String(startTimeNs),\n endTimeUnixNano: String(endTimeNs),\n attributes,\n status: { code: (event.status === 'success' ? 1 : 2) satisfies OtlpStatusCode },\n },\n ],\n },\n ],\n },\n ],\n }\n}\n\n/**\n * Send an anonymous telemetry event to the Kubb OTLP endpoint.\n * Respects DO_NOT_TRACK and KUBB_DISABLE_TELEMETRY environment variables.\n * Fails silently to never interrupt the generation process.\n */\nexport async function sendTelemetry(event: TelemetryEvent): Promise<void> {\n if (isTelemetryDisabled()) {\n return\n }\n\n await executeIfOnline(async () => {\n try {\n await fetch(`${OTLP_ENDPOINT}/v1/traces`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'Kubb-Telemetry-Version': '1',\n 'Kubb-Telemetry-Source': 'kubb-cli',\n },\n body: JSON.stringify(buildOtlpPayload(event)),\n signal: AbortSignal.timeout(5_000),\n })\n } catch (_e) {\n // Fail silently – telemetry must never break the CLI\n }\n })\n}\n\n/**\n * Build an anonymous telemetry payload from a completed generation run.\n * No file paths, OpenAPI specs, or secrets are included.\n */\nexport function buildTelemetryEvent(options: {\n command: 'generate' | 'mcp' | 'validate' | 'agent'\n kubbVersion: string\n plugins?: TelemetryPlugin[]\n hrStart: [number, number]\n filesCreated?: number\n status: 'success' | 'failed'\n}): TelemetryEvent {\n const [seconds, nanoseconds] = process.hrtime(options.hrStart)\n const duration = Math.round(seconds * 1000 + nanoseconds / 1e6)\n\n return {\n command: options.command,\n kubbVersion: options.kubbVersion,\n nodeVersion: process.versions.node.split('.')[0] ?? 'unknown',\n platform: os.platform(),\n ci: isCi(),\n plugins: options.plugins ?? [],\n duration,\n filesCreated: options.filesCreated ?? 0,\n status: options.status,\n }\n}\n"],"mappings":"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"}
@@ -0,0 +1,162 @@
1
+ const require_chunk = require('./chunk-CNbaEX1y.cjs');
2
+ let node_process = require("node:process");
3
+ node_process = require_chunk.__toESM(node_process);
4
+ let node_crypto = require("node:crypto");
5
+ let node_os = require("node:os");
6
+ node_os = require_chunk.__toESM(node_os);
7
+ let _kubb_core_utils = require("@kubb/core/utils");
8
+
9
+ //#region src/utils/telemetry.ts
10
+ const OTLP_ENDPOINT = "https://otlp.kubb.dev";
11
+ /**
12
+ * Detect whether the current process is running inside a CI environment by
13
+ * checking the well-known environment variables set by all major CI systems.
14
+ */
15
+ function isCi() {
16
+ return !!(node_process.default.env["CI"] || node_process.default.env["GITHUB_ACTIONS"] || node_process.default.env["GITLAB_CI"] || node_process.default.env["BITBUCKET_BUILD_NUMBER"] || node_process.default.env["JENKINS_URL"] || node_process.default.env["CIRCLECI"] || node_process.default.env["TRAVIS"] || node_process.default.env["TEAMCITY_VERSION"] || node_process.default.env["BUILDKITE"] || node_process.default.env["TF_BUILD"]);
17
+ }
18
+ /**
19
+ * Check if telemetry is disabled via DO_NOT_TRACK or KUBB_DISABLE_TELEMETRY.
20
+ * Respects the standard DO_NOT_TRACK convention used across development tools.
21
+ */
22
+ function isTelemetryDisabled() {
23
+ return node_process.default.env["DO_NOT_TRACK"] === "1" || node_process.default.env["DO_NOT_TRACK"] === "true" || node_process.default.env["KUBB_DISABLE_TELEMETRY"] === "1" || node_process.default.env["KUBB_DISABLE_TELEMETRY"] === "true";
24
+ }
25
+ /**
26
+ * Convert a TelemetryEvent into an OTLP-compatible JSON trace payload.
27
+ * See https://opentelemetry.io/docs/languages/sdk-configuration/otlp-exporter/
28
+ */
29
+ function buildOtlpPayload(event) {
30
+ const traceId = (0, node_crypto.randomBytes)(16).toString("hex");
31
+ const spanId = (0, node_crypto.randomBytes)(8).toString("hex");
32
+ const endTimeNs = BigInt(Date.now()) * 1000000n;
33
+ const startTimeNs = endTimeNs - BigInt(event.duration) * 1000000n;
34
+ const attributes = [
35
+ {
36
+ key: "kubb.command",
37
+ value: { stringValue: event.command }
38
+ },
39
+ {
40
+ key: "kubb.version",
41
+ value: { stringValue: event.kubbVersion }
42
+ },
43
+ {
44
+ key: "kubb.node_version",
45
+ value: { stringValue: event.nodeVersion }
46
+ },
47
+ {
48
+ key: "kubb.platform",
49
+ value: { stringValue: event.platform }
50
+ },
51
+ {
52
+ key: "kubb.ci",
53
+ value: { boolValue: event.ci }
54
+ },
55
+ {
56
+ key: "kubb.files_created",
57
+ value: { intValue: event.filesCreated }
58
+ },
59
+ {
60
+ key: "kubb.status",
61
+ value: { stringValue: event.status }
62
+ },
63
+ {
64
+ key: "kubb.plugins",
65
+ value: { arrayValue: { values: event.plugins.map((p) => ({ kvlistValue: { values: [{
66
+ key: "name",
67
+ value: { stringValue: p.name }
68
+ }, {
69
+ key: "options",
70
+ value: { stringValue: JSON.stringify(p.options) }
71
+ }] } })) } }
72
+ }
73
+ ];
74
+ return { resourceSpans: [{
75
+ resource: { attributes: [
76
+ {
77
+ key: "service.name",
78
+ value: { stringValue: "kubb-cli" }
79
+ },
80
+ {
81
+ key: "service.version",
82
+ value: { stringValue: event.kubbVersion }
83
+ },
84
+ {
85
+ key: "telemetry.sdk.language",
86
+ value: { stringValue: "nodejs" }
87
+ }
88
+ ] },
89
+ scopeSpans: [{
90
+ scope: {
91
+ name: "kubb-cli",
92
+ version: event.kubbVersion
93
+ },
94
+ spans: [{
95
+ traceId,
96
+ spanId,
97
+ name: event.command,
98
+ kind: 1,
99
+ startTimeUnixNano: String(startTimeNs),
100
+ endTimeUnixNano: String(endTimeNs),
101
+ attributes,
102
+ status: { code: event.status === "success" ? 1 : 2 }
103
+ }]
104
+ }]
105
+ }] };
106
+ }
107
+ /**
108
+ * Send an anonymous telemetry event to the Kubb OTLP endpoint.
109
+ * Respects DO_NOT_TRACK and KUBB_DISABLE_TELEMETRY environment variables.
110
+ * Fails silently to never interrupt the generation process.
111
+ */
112
+ async function sendTelemetry(event) {
113
+ if (isTelemetryDisabled()) return;
114
+ await (0, _kubb_core_utils.executeIfOnline)(async () => {
115
+ try {
116
+ await fetch(`${OTLP_ENDPOINT}/v1/traces`, {
117
+ method: "POST",
118
+ headers: {
119
+ "Content-Type": "application/json",
120
+ "Kubb-Telemetry-Version": "1",
121
+ "Kubb-Telemetry-Source": "kubb-cli"
122
+ },
123
+ body: JSON.stringify(buildOtlpPayload(event)),
124
+ signal: AbortSignal.timeout(5e3)
125
+ });
126
+ } catch (_e) {}
127
+ });
128
+ }
129
+ /**
130
+ * Build an anonymous telemetry payload from a completed generation run.
131
+ * No file paths, OpenAPI specs, or secrets are included.
132
+ */
133
+ function buildTelemetryEvent(options) {
134
+ const [seconds, nanoseconds] = node_process.default.hrtime(options.hrStart);
135
+ const duration = Math.round(seconds * 1e3 + nanoseconds / 1e6);
136
+ return {
137
+ command: options.command,
138
+ kubbVersion: options.kubbVersion,
139
+ nodeVersion: node_process.default.versions.node.split(".")[0] ?? "unknown",
140
+ platform: node_os.default.platform(),
141
+ ci: isCi(),
142
+ plugins: options.plugins ?? [],
143
+ duration,
144
+ filesCreated: options.filesCreated ?? 0,
145
+ status: options.status
146
+ };
147
+ }
148
+
149
+ //#endregion
150
+ Object.defineProperty(exports, 'buildTelemetryEvent', {
151
+ enumerable: true,
152
+ get: function () {
153
+ return buildTelemetryEvent;
154
+ }
155
+ });
156
+ Object.defineProperty(exports, 'sendTelemetry', {
157
+ enumerable: true,
158
+ get: function () {
159
+ return sendTelemetry;
160
+ }
161
+ });
162
+ //# sourceMappingURL=telemetry-DxyJ2d4j.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"telemetry-DxyJ2d4j.cjs","names":["process","os"],"sources":["../src/utils/telemetry.ts"],"sourcesContent":["import { randomBytes } from 'node:crypto'\nimport os from 'node:os'\nimport process from 'node:process'\nimport { executeIfOnline } from '@kubb/core/utils'\n\nconst OTLP_ENDPOINT = 'https://otlp.kubb.dev'\n\n// ---------------------------------------------------------------------------\n// OpenTelemetry OTLP JSON types\n// https://github.com/open-telemetry/opentelemetry-proto/blob/main/opentelemetry/proto/trace/v1/trace.proto\n// https://github.com/open-telemetry/opentelemetry-proto/blob/main/opentelemetry/proto/common/v1/common.proto\n// ---------------------------------------------------------------------------\n\ntype OtlpStringValue = { stringValue: string }\ntype OtlpBoolValue = { boolValue: boolean }\ntype OtlpIntValue = { intValue: number }\ntype OtlpDoubleValue = { doubleValue: number }\ntype OtlpBytesValue = { bytesValue: string }\ntype OtlpArrayValue = { arrayValue: { values: OtlpAnyValue[] } }\ntype OtlpKvListValue = { kvlistValue: { values: OtlpKeyValue[] } }\n\ntype OtlpAnyValue = OtlpStringValue | OtlpBoolValue | OtlpIntValue | OtlpDoubleValue | OtlpBytesValue | OtlpArrayValue | OtlpKvListValue\n\ntype OtlpKeyValue = {\n key: string\n value: OtlpAnyValue\n}\n\ntype OtlpResource = {\n attributes: OtlpKeyValue[]\n droppedAttributesCount?: number\n}\n\ntype OtlpInstrumentationScope = {\n name: string\n version?: string\n attributes?: OtlpKeyValue[]\n droppedAttributesCount?: number\n}\n\n/** https://github.com/open-telemetry/opentelemetry-proto/blob/main/opentelemetry/proto/trace/v1/trace.proto#L103 */\ntype OtlpSpanKind = 0 | 1 | 2 | 3 | 4 | 5\n\n/** 0 = STATUS_CODE_UNSET, 1 = STATUS_CODE_OK, 2 = STATUS_CODE_ERROR */\ntype OtlpStatusCode = 0 | 1 | 2\n\ntype OtlpStatus = {\n code: OtlpStatusCode\n message?: string\n}\n\ntype OtlpSpan = {\n traceId: string\n spanId: string\n traceState?: string\n parentSpanId?: string\n name: string\n kind: OtlpSpanKind\n startTimeUnixNano: string\n endTimeUnixNano: string\n attributes?: OtlpKeyValue[]\n droppedAttributesCount?: number\n events?: OtlpSpanEvent[]\n droppedEventsCount?: number\n links?: OtlpSpanLink[]\n droppedLinksCount?: number\n status?: OtlpStatus\n}\n\ntype OtlpSpanEvent = {\n timeUnixNano: string\n name: string\n attributes?: OtlpKeyValue[]\n droppedAttributesCount?: number\n}\n\ntype OtlpSpanLink = {\n traceId: string\n spanId: string\n traceState?: string\n attributes?: OtlpKeyValue[]\n droppedAttributesCount?: number\n}\n\ntype OtlpScopeSpans = {\n scope: OtlpInstrumentationScope\n spans: OtlpSpan[]\n schemaUrl?: string\n}\n\ntype OtlpResourceSpans = {\n resource: OtlpResource\n scopeSpans: OtlpScopeSpans[]\n schemaUrl?: string\n}\n\n/** Root payload sent to POST /v1/traces */\nexport type OtlpExportTraceServiceRequest = {\n resourceSpans: OtlpResourceSpans[]\n}\n\n// ---------------------------------------------------------------------------\n\nexport type TelemetryPlugin = {\n name: string\n options: Record<string, unknown>\n}\n\nexport type TelemetryEvent = {\n command: string\n kubbVersion: string\n nodeVersion: string\n platform: string\n ci: boolean\n plugins: TelemetryPlugin[]\n duration: number\n filesCreated: number\n status: 'success' | 'failed'\n}\n\n/**\n * Detect whether the current process is running inside a CI environment by\n * checking the well-known environment variables set by all major CI systems.\n */\nexport function isCi(): boolean {\n return !!(\n (\n process.env['CI'] || // Generic (GitHub Actions, GitLab CI, CircleCI, Travis CI, etc.)\n process.env['GITHUB_ACTIONS'] || // GitHub Actions\n process.env['GITLAB_CI'] || // GitLab CI\n process.env['BITBUCKET_BUILD_NUMBER'] || // Bitbucket Pipelines\n process.env['JENKINS_URL'] || // Jenkins\n process.env['CIRCLECI'] || // CircleCI\n process.env['TRAVIS'] || // Travis CI\n process.env['TEAMCITY_VERSION'] || // TeamCity\n process.env['BUILDKITE'] || // Buildkite\n process.env['TF_BUILD']\n ) // Azure Pipelines\n )\n}\n\n/**\n * Check if telemetry is disabled via DO_NOT_TRACK or KUBB_DISABLE_TELEMETRY.\n * Respects the standard DO_NOT_TRACK convention used across development tools.\n */\nexport function isTelemetryDisabled(): boolean {\n return (\n process.env['DO_NOT_TRACK'] === '1' ||\n process.env['DO_NOT_TRACK'] === 'true' ||\n process.env['KUBB_DISABLE_TELEMETRY'] === '1' ||\n process.env['KUBB_DISABLE_TELEMETRY'] === 'true'\n )\n}\n\n/**\n * Convert a TelemetryEvent into an OTLP-compatible JSON trace payload.\n * See https://opentelemetry.io/docs/languages/sdk-configuration/otlp-exporter/\n */\nexport function buildOtlpPayload(event: TelemetryEvent): OtlpExportTraceServiceRequest {\n const traceId = randomBytes(16).toString('hex')\n const spanId = randomBytes(8).toString('hex')\n const endTimeNs = BigInt(Date.now()) * 1_000_000n\n const startTimeNs = endTimeNs - BigInt(event.duration) * 1_000_000n\n\n const attributes: OtlpKeyValue[] = [\n { key: 'kubb.command', value: { stringValue: event.command } },\n { key: 'kubb.version', value: { stringValue: event.kubbVersion } },\n { key: 'kubb.node_version', value: { stringValue: event.nodeVersion } },\n { key: 'kubb.platform', value: { stringValue: event.platform } },\n { key: 'kubb.ci', value: { boolValue: event.ci } },\n { key: 'kubb.files_created', value: { intValue: event.filesCreated } },\n { key: 'kubb.status', value: { stringValue: event.status } },\n {\n key: 'kubb.plugins',\n value: {\n arrayValue: {\n values: event.plugins.map(\n (p): OtlpKvListValue => ({\n kvlistValue: {\n values: [\n { key: 'name', value: { stringValue: p.name } },\n { key: 'options', value: { stringValue: JSON.stringify(p.options) } },\n ],\n },\n }),\n ),\n },\n },\n },\n ]\n\n return {\n resourceSpans: [\n {\n resource: {\n attributes: [\n { key: 'service.name', value: { stringValue: 'kubb-cli' } },\n { key: 'service.version', value: { stringValue: event.kubbVersion } },\n { key: 'telemetry.sdk.language', value: { stringValue: 'nodejs' } },\n ],\n },\n scopeSpans: [\n {\n scope: { name: 'kubb-cli', version: event.kubbVersion },\n spans: [\n {\n traceId,\n spanId,\n name: event.command,\n kind: 1 satisfies OtlpSpanKind,\n startTimeUnixNano: String(startTimeNs),\n endTimeUnixNano: String(endTimeNs),\n attributes,\n status: { code: (event.status === 'success' ? 1 : 2) satisfies OtlpStatusCode },\n },\n ],\n },\n ],\n },\n ],\n }\n}\n\n/**\n * Send an anonymous telemetry event to the Kubb OTLP endpoint.\n * Respects DO_NOT_TRACK and KUBB_DISABLE_TELEMETRY environment variables.\n * Fails silently to never interrupt the generation process.\n */\nexport async function sendTelemetry(event: TelemetryEvent): Promise<void> {\n if (isTelemetryDisabled()) {\n return\n }\n\n await executeIfOnline(async () => {\n try {\n await fetch(`${OTLP_ENDPOINT}/v1/traces`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'Kubb-Telemetry-Version': '1',\n 'Kubb-Telemetry-Source': 'kubb-cli',\n },\n body: JSON.stringify(buildOtlpPayload(event)),\n signal: AbortSignal.timeout(5_000),\n })\n } catch (_e) {\n // Fail silently – telemetry must never break the CLI\n }\n })\n}\n\n/**\n * Build an anonymous telemetry payload from a completed generation run.\n * No file paths, OpenAPI specs, or secrets are included.\n */\nexport function buildTelemetryEvent(options: {\n command: 'generate' | 'mcp' | 'validate' | 'agent'\n kubbVersion: string\n plugins?: TelemetryPlugin[]\n hrStart: [number, number]\n filesCreated?: number\n status: 'success' | 'failed'\n}): TelemetryEvent {\n const [seconds, nanoseconds] = process.hrtime(options.hrStart)\n const duration = Math.round(seconds * 1000 + nanoseconds / 1e6)\n\n return {\n command: options.command,\n kubbVersion: options.kubbVersion,\n nodeVersion: process.versions.node.split('.')[0] ?? 'unknown',\n platform: os.platform(),\n ci: isCi(),\n plugins: options.plugins ?? [],\n duration,\n filesCreated: options.filesCreated ?? 0,\n status: options.status,\n }\n}\n"],"mappings":"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"}
@@ -1,4 +1,6 @@
1
1
  const require_chunk = require('./chunk-CNbaEX1y.cjs');
2
+ const require_package = require('./package-BqKkzL1A.cjs');
3
+ const require_telemetry = require('./telemetry-DxyJ2d4j.cjs');
2
4
  let citty = require("citty");
3
5
  let node_process = require("node:process");
4
6
  node_process = require_chunk.__toESM(node_process);
@@ -36,10 +38,23 @@ const command = (0, citty.defineCommand)({
36
38
  node_process.default.exit(1);
37
39
  }
38
40
  const { parse } = mod;
41
+ const hrStart = node_process.default.hrtime();
39
42
  try {
40
43
  await (await parse(args.input)).validate();
44
+ await require_telemetry.sendTelemetry(require_telemetry.buildTelemetryEvent({
45
+ command: "validate",
46
+ kubbVersion: require_package.version,
47
+ hrStart,
48
+ status: "success"
49
+ }));
41
50
  console.log("✅ Validation success");
42
51
  } catch (error) {
52
+ await require_telemetry.sendTelemetry(require_telemetry.buildTelemetryEvent({
53
+ command: "validate",
54
+ kubbVersion: require_package.version,
55
+ hrStart,
56
+ status: "failed"
57
+ }));
43
58
  console.error("❌ Validation failed");
44
59
  console.log(error?.message);
45
60
  node_process.default.exit(1);
@@ -50,4 +65,4 @@ const command = (0, citty.defineCommand)({
50
65
 
51
66
  //#endregion
52
67
  exports.default = command;
53
- //# sourceMappingURL=validate-BgYhe_55.cjs.map
68
+ //# sourceMappingURL=validate-BbVY6zQM.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"validate-BbVY6zQM.cjs","names":["jiti","process","sendTelemetry","buildTelemetryEvent","version"],"sources":["../src/commands/validate.ts"],"sourcesContent":["import process from 'node:process'\nimport type { ArgsDef } from 'citty'\nimport { defineCommand, showUsage } from 'citty'\nimport { createJiti } from 'jiti'\nimport { version } from '../../package.json'\nimport { buildTelemetryEvent, sendTelemetry } from '../utils/telemetry.ts'\n\nconst jiti = createJiti(import.meta.url, {\n sourceMaps: true,\n})\n\nconst args = {\n input: {\n type: 'string',\n description: 'Path to Swagger/OpenAPI file',\n alias: 'i',\n },\n help: {\n type: 'boolean',\n description: 'Show help',\n alias: 'h',\n default: false,\n },\n} as const satisfies ArgsDef\n\nconst command = defineCommand({\n meta: {\n name: 'validate',\n description: 'Validate a Swagger/OpenAPI file',\n },\n args,\n async run(commandContext) {\n const { args } = commandContext\n\n if (args.help) {\n return showUsage(command)\n }\n\n if (args.input) {\n let mod: any\n try {\n mod = await jiti.import('@kubb/oas', { default: true })\n } catch (_e) {\n console.error(`Import of '@kubb/oas' is required to do validation`)\n process.exit(1)\n }\n\n const { parse } = mod\n const hrStart = process.hrtime()\n try {\n const oas = await parse(args.input)\n await oas.validate()\n\n await sendTelemetry(buildTelemetryEvent({ command: 'validate', kubbVersion: version, hrStart, status: 'success' }))\n console.log('✅ Validation success')\n } catch (error) {\n await sendTelemetry(buildTelemetryEvent({ command: 'validate', kubbVersion: version, hrStart, status: 'failed' }))\n console.error('❌ Validation failed')\n console.log((error as Error)?.message)\n process.exit(1)\n }\n }\n },\n})\n\nexport default command\n"],"mappings":";;;;;;;;;AAOA,MAAMA,6EAAmC,EACvC,YAAY,MACb,CAAC;AAgBF,MAAM,mCAAwB;CAC5B,MAAM;EACJ,MAAM;EACN,aAAa;EACd;CACD,MAnBW;EACX,OAAO;GACL,MAAM;GACN,aAAa;GACb,OAAO;GACR;EACD,MAAM;GACJ,MAAM;GACN,aAAa;GACb,OAAO;GACP,SAAS;GACV;EACF;CAQC,MAAM,IAAI,gBAAgB;EACxB,MAAM,EAAE,SAAS;AAEjB,MAAI,KAAK,KACP,6BAAiB,QAAQ;AAG3B,MAAI,KAAK,OAAO;GACd,IAAI;AACJ,OAAI;AACF,UAAM,MAAMA,OAAK,OAAO,aAAa,EAAE,SAAS,MAAM,CAAC;YAChD,IAAI;AACX,YAAQ,MAAM,qDAAqD;AACnE,yBAAQ,KAAK,EAAE;;GAGjB,MAAM,EAAE,UAAU;GAClB,MAAM,UAAUC,qBAAQ,QAAQ;AAChC,OAAI;AAEF,WADY,MAAM,MAAM,KAAK,MAAM,EACzB,UAAU;AAEpB,UAAMC,gCAAcC,sCAAoB;KAAE,SAAS;KAAY,aAAaC;KAAS;KAAS,QAAQ;KAAW,CAAC,CAAC;AACnH,YAAQ,IAAI,uBAAuB;YAC5B,OAAO;AACd,UAAMF,gCAAcC,sCAAoB;KAAE,SAAS;KAAY,aAAaC;KAAS;KAAS,QAAQ;KAAU,CAAC,CAAC;AAClH,YAAQ,MAAM,sBAAsB;AACpC,YAAQ,IAAK,OAAiB,QAAQ;AACtC,yBAAQ,KAAK,EAAE;;;;CAItB,CAAC"}