@kubb/plugin-mcp 5.0.0-alpha.33 → 5.0.0-alpha.35

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -1,10 +1,9 @@
1
1
  import "./chunk--u3MIqq1.js";
2
2
  import path from "node:path";
3
- import { caseParams, createFile, createFunctionParameter, createFunctionParameters, createOperationParams, createParameterGroup, createSource, createText } from "@kubb/ast";
3
+ import { ast, defineGenerator, definePlugin, defineResolver } from "@kubb/core";
4
4
  import { functionPrinter, pluginTsName } from "@kubb/plugin-ts";
5
- import { Const, File, Function as Function$1 } from "@kubb/renderer-jsx";
5
+ import { Const, File, Function as Function$1, jsxRenderer } from "@kubb/renderer-jsx";
6
6
  import { Fragment, jsx, jsxs } from "@kubb/renderer-jsx/jsx-runtime";
7
- import { createPlugin, defineGenerator, definePresets, defineResolver, getPreset, mergeGenerators } from "@kubb/core";
8
7
  import { pluginZodName } from "@kubb/plugin-zod";
9
8
  import { pluginClientName } from "@kubb/plugin-client";
10
9
  import { source } from "@kubb/plugin-client/templates/clients/axios.source";
@@ -270,6 +269,15 @@ function getParamsMapping(params) {
270
269
  function zodExprFromSchemaNode(schema) {
271
270
  let expr;
272
271
  switch (schema.type) {
272
+ case "enum": {
273
+ const rawValues = schema.namedEnumValues?.length ? schema.namedEnumValues.map((v) => v.value) : (schema.enumValues ?? []).filter((v) => v !== null);
274
+ if (rawValues.length > 0 && rawValues.every((v) => typeof v === "string")) expr = `z.enum([${rawValues.map((v) => JSON.stringify(v)).join(", ")}])`;
275
+ else if (rawValues.length > 0) {
276
+ const literals = rawValues.map((v) => `z.literal(${JSON.stringify(v)})`);
277
+ expr = literals.length === 1 ? literals[0] : `z.union([${literals.join(", ")}])`;
278
+ } else expr = "z.string()";
279
+ break;
280
+ }
273
281
  case "integer":
274
282
  expr = "z.coerce.number()";
275
283
  break;
@@ -300,7 +308,7 @@ function McpHandler({ name, node, resolver, baseURL, dataReturnType, paramsCasin
300
308
  const urlPath = new URLPath(node.path);
301
309
  const contentType = node.requestBody?.contentType;
302
310
  const isFormData = contentType === "multipart/form-data";
303
- const casedParams = caseParams(node.parameters, paramsCasing);
311
+ const casedParams = ast.caseParams(node.parameters, paramsCasing);
304
312
  const queryParams = casedParams.filter((p) => p.in === "query");
305
313
  const headerParams = casedParams.filter((p) => p.in === "header");
306
314
  const originalPathParams = node.parameters.filter((p) => p.in === "path");
@@ -314,7 +322,7 @@ function McpHandler({ name, node, resolver, baseURL, dataReturnType, paramsCasin
314
322
  `ResponseErrorConfig<${errorResponses.length > 0 ? errorResponses.join(" | ") : "Error"}>`,
315
323
  requestName || "unknown"
316
324
  ].filter(Boolean);
317
- const paramsNode = createOperationParams(node, {
325
+ const paramsNode = ast.createOperationParams(node, {
318
326
  paramsType: "object",
319
327
  pathParamsType: "inline",
320
328
  resolver,
@@ -408,7 +416,7 @@ function Server({ name, serverName, serverVersion, paramsCasing, operations }) {
408
416
  `
409
417
  }),
410
418
  operations.map(({ tool, mcp, zod, node }) => {
411
- const pathParams = caseParams(node.parameters, paramsCasing).filter((p) => p.in === "path");
419
+ const pathParams = ast.caseParams(node.parameters, paramsCasing).filter((p) => p.in === "path");
412
420
  const pathEntries = [];
413
421
  const otherEntries = [];
414
422
  for (const p of pathParams) {
@@ -432,7 +440,7 @@ function Server({ name, serverName, serverVersion, paramsCasing, operations }) {
432
440
  });
433
441
  otherEntries.sort((a, b) => a.key.localeCompare(b.key));
434
442
  const entries = [...pathEntries, ...otherEntries];
435
- const paramsNode = entries.length ? createFunctionParameters({ params: [createParameterGroup({ properties: entries.map((e) => createFunctionParameter({
443
+ const paramsNode = entries.length ? ast.createFunctionParameters({ params: [ast.createParameterGroup({ properties: entries.map((e) => ast.createFunctionParameter({
436
444
  name: e.key,
437
445
  optional: false
438
446
  })) })] }) : void 0;
@@ -480,12 +488,13 @@ server.registerTool(${JSON.stringify(tool.name)}, {
480
488
  //#region src/generators/mcpGenerator.tsx
481
489
  const mcpGenerator = defineGenerator({
482
490
  name: "mcp",
483
- operation(node, options) {
484
- const { resolver, driver, root } = this;
485
- const { output, client, paramsCasing, group } = options;
491
+ renderer: jsxRenderer,
492
+ operation(node, ctx) {
493
+ const { resolver, driver, root } = ctx;
494
+ const { output, client, paramsCasing, group } = ctx.options;
486
495
  const pluginTs = driver.getPlugin(pluginTsName);
487
496
  if (!pluginTs?.resolver) return null;
488
- const casedParams = caseParams(node.parameters, paramsCasing);
497
+ const casedParams = ast.caseParams(node.parameters, paramsCasing);
489
498
  const pathParams = casedParams.filter((p) => p.in === "path");
490
499
  const queryParams = casedParams.filter((p) => p.in === "query");
491
500
  const headerParams = casedParams.filter((p) => p.in === "header");
@@ -606,9 +615,10 @@ const mcpGenerator = defineGenerator({
606
615
  */
607
616
  const serverGenerator = defineGenerator({
608
617
  name: "operations",
609
- operations(nodes, options) {
610
- const { adapter, config, resolver, plugin, driver, root } = this;
611
- const { output, paramsCasing, group } = options;
618
+ renderer: jsxRenderer,
619
+ operations(nodes, ctx) {
620
+ const { adapter, config, resolver, plugin, driver, root } = ctx;
621
+ const { output, paramsCasing, group } = ctx.options;
612
622
  const pluginZod = driver.getPlugin(pluginZodName);
613
623
  if (!pluginZod?.resolver) return;
614
624
  const name = "server";
@@ -623,7 +633,7 @@ const serverGenerator = defineGenerator({
623
633
  meta: { pluginName: plugin.name }
624
634
  };
625
635
  const operationsMapped = nodes.map((node) => {
626
- const casedParams = caseParams(node.parameters, paramsCasing);
636
+ const casedParams = ast.caseParams(node.parameters, paramsCasing);
627
637
  const pathParams = casedParams.filter((p) => p.in === "path");
628
638
  const queryParams = casedParams.filter((p) => p.in === "query");
629
639
  const headerParams = casedParams.filter((p) => p.in === "header");
@@ -760,9 +770,10 @@ const serverGenerator = defineGenerator({
760
770
  */
761
771
  const serverGeneratorLegacy = defineGenerator({
762
772
  name: "operations",
763
- operations(nodes, options) {
764
- const { adapter, config, resolver, plugin, driver, root } = this;
765
- const { output, paramsCasing, group } = options;
773
+ renderer: jsxRenderer,
774
+ operations(nodes, ctx) {
775
+ const { adapter, config, resolver, plugin, driver, root } = ctx;
776
+ const { output, paramsCasing, group } = ctx.options;
766
777
  const pluginZod = driver.getPlugin(pluginZodName);
767
778
  if (!pluginZod?.resolver) return;
768
779
  const name = "server";
@@ -777,7 +788,7 @@ const serverGeneratorLegacy = defineGenerator({
777
788
  meta: { pluginName: plugin.name }
778
789
  };
779
790
  const operationsMapped = nodes.map((node) => {
780
- const casedParams = caseParams(node.parameters, paramsCasing);
791
+ const casedParams = ast.caseParams(node.parameters, paramsCasing);
781
792
  const queryParams = casedParams.filter((p) => p.in === "query");
782
793
  const headerParams = casedParams.filter((p) => p.in === "header");
783
794
  const mcpFile = resolver.resolveFile({
@@ -898,9 +909,6 @@ const serverGeneratorLegacy = defineGenerator({
898
909
  }
899
910
  });
900
911
  //#endregion
901
- //#region package.json
902
- var version = "5.0.0-alpha.33";
903
- //#endregion
904
912
  //#region src/resolvers/resolverMcp.ts
905
913
  /**
906
914
  * Resolver for `@kubb/plugin-mcp` that provides the default naming
@@ -926,65 +934,38 @@ const resolverMcp = defineResolver(() => ({
926
934
  }
927
935
  }));
928
936
  //#endregion
929
- //#region src/presets.ts
930
- /**
931
- * Built-in preset registry for `@kubb/plugin-mcp`.
932
- *
933
- * - `default` — v5 naming with individual zod schemas and per-status responses.
934
- * - `kubbV4` — legacy naming with grouped zod schemas and combined responses.
935
- */
936
- const presets = definePresets({
937
- default: {
938
- name: "default",
939
- resolver: resolverMcp,
940
- generators: [mcpGenerator, serverGenerator]
941
- },
942
- kubbV4: {
943
- name: "kubbV4",
944
- resolver: resolverMcp,
945
- generators: [mcpGenerator, serverGeneratorLegacy]
946
- }
947
- });
948
- //#endregion
949
937
  //#region src/plugin.ts
950
938
  const pluginMcpName = "plugin-mcp";
951
- const pluginMcp = createPlugin((options) => {
939
+ const pluginMcp = definePlugin((options) => {
952
940
  const { output = {
953
941
  path: "mcp",
954
942
  barrelType: "named"
955
- }, group, exclude = [], include, override = [], paramsCasing, client, compatibilityPreset = "default", resolver: userResolver, transformer: userTransformer, generators: userGenerators = [] } = options;
943
+ }, group, exclude = [], include, override = [], paramsCasing, client, resolver: userResolver, transformer: userTransformer, generators: userGenerators = [], compatibilityPreset = "default" } = options;
944
+ const defaultServerGenerator = compatibilityPreset === "kubbV4" ? serverGeneratorLegacy : serverGenerator;
956
945
  const clientName = client?.client ?? "axios";
957
946
  const clientImportPath = client?.importPath ?? (!client?.bundle ? `@kubb/plugin-client/clients/${clientName}` : void 0);
958
- const preset = getPreset({
959
- preset: compatibilityPreset,
960
- presets,
961
- resolver: userResolver,
962
- transformer: userTransformer,
963
- generators: userGenerators
964
- });
965
- const mergedGenerator = mergeGenerators(preset.generators ?? []);
947
+ const groupConfig = group ? {
948
+ ...group,
949
+ name: group.name ? group.name : (ctx) => {
950
+ if (group.type === "path") return `${ctx.group.split("/")[1]}`;
951
+ return `${camelCase(ctx.group)}Requests`;
952
+ }
953
+ } : void 0;
966
954
  return {
967
955
  name: pluginMcpName,
968
- version,
969
- get resolver() {
970
- return preset.resolver;
971
- },
972
- get transformer() {
973
- return preset.transformer;
974
- },
975
- get options() {
976
- return {
956
+ options,
957
+ dependencies: [pluginTsName, pluginZodName],
958
+ hooks: { "kubb:plugin:setup"(ctx) {
959
+ const resolver = userResolver ? {
960
+ ...resolverMcp,
961
+ ...userResolver
962
+ } : resolverMcp;
963
+ ctx.setOptions({
977
964
  output,
978
965
  exclude,
979
966
  include,
980
967
  override,
981
- group: group ? {
982
- ...group,
983
- name: group.name ? group.name : (ctx) => {
984
- if (group.type === "path") return `${ctx.group.split("/")[1]}`;
985
- return `${camelCase(ctx.group)}Requests`;
986
- }
987
- } : void 0,
968
+ group: groupConfig,
988
969
  paramsCasing,
989
970
  client: {
990
971
  client: clientName,
@@ -995,51 +976,36 @@ const pluginMcp = createPlugin((options) => {
995
976
  baseURL: client?.baseURL,
996
977
  paramsCasing: client?.paramsCasing
997
978
  },
998
- resolver: preset.resolver
999
- };
1000
- },
1001
- pre: [pluginTsName, pluginZodName].filter(Boolean),
1002
- async schema(node, options) {
1003
- return mergedGenerator.schema?.call(this, node, options);
1004
- },
1005
- async operation(node, options) {
1006
- return mergedGenerator.operation?.call(this, node, options);
1007
- },
1008
- async operations(nodes, options) {
1009
- return mergedGenerator.operations?.call(this, nodes, options);
1010
- },
1011
- async buildStart() {
1012
- const { adapter, driver } = this;
1013
- const root = this.root;
1014
- const baseURL = adapter?.inputNode?.meta?.baseURL;
1015
- if (baseURL) this.plugin.options.client.baseURL = this.plugin.options.client.baseURL || baseURL;
1016
- const hasClientPlugin = !!driver.getPlugin(pluginClientName);
1017
- if (this.plugin.options.client.bundle && !hasClientPlugin && !this.plugin.options.client.importPath) await this.addFile(createFile({
979
+ resolver
980
+ });
981
+ ctx.setResolver(resolver);
982
+ if (userTransformer) ctx.setTransformer(userTransformer);
983
+ ctx.addGenerator(mcpGenerator);
984
+ ctx.addGenerator(defaultServerGenerator);
985
+ for (const gen of userGenerators) ctx.addGenerator(gen);
986
+ const root = path.resolve(ctx.config.root, ctx.config.output.path);
987
+ const hasClientPlugin = ctx.config.plugins?.some((p) => p.name === pluginClientName);
988
+ if (client?.bundle && !hasClientPlugin && !clientImportPath) ctx.injectFile({
1018
989
  baseName: "fetch.ts",
1019
990
  path: path.resolve(root, ".kubb/fetch.ts"),
1020
- sources: [createSource({
991
+ sources: [ast.createSource({
1021
992
  name: "fetch",
1022
- nodes: [createText(this.plugin.options.client.client === "fetch" ? source$1 : source)],
993
+ nodes: [ast.createText(clientName === "fetch" ? source$1 : source)],
1023
994
  isExportable: true,
1024
995
  isIndexable: true
1025
- })],
1026
- imports: [],
1027
- exports: []
1028
- }));
1029
- if (!hasClientPlugin) await this.addFile(createFile({
996
+ })]
997
+ });
998
+ if (!hasClientPlugin) ctx.injectFile({
1030
999
  baseName: "config.ts",
1031
1000
  path: path.resolve(root, ".kubb/config.ts"),
1032
- sources: [createSource({
1001
+ sources: [ast.createSource({
1033
1002
  name: "config",
1034
- nodes: [createText(source$2)],
1003
+ nodes: [ast.createText(source$2)],
1035
1004
  isExportable: false,
1036
1005
  isIndexable: false
1037
- })],
1038
- imports: [],
1039
- exports: []
1040
- }));
1041
- await this.openInStudio({ ast: true });
1042
- }
1006
+ })]
1007
+ });
1008
+ } }
1043
1009
  };
1044
1010
  });
1045
1011
  //#endregion