@kubb/plugin-mcp 5.0.0-beta.15 → 5.0.0-beta.25
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.cjs +100 -66
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +69 -21
- package/dist/index.js +100 -66
- package/dist/index.js.map +1 -1
- package/extension.yaml +600 -147
- package/package.json +7 -7
- package/src/components/McpHandler.tsx +8 -8
- package/src/components/Server.tsx +6 -6
- package/src/generators/mcpGenerator.tsx +11 -2
- package/src/generators/serverGenerator.tsx +15 -12
- package/src/plugin.ts +33 -1
- package/src/resolvers/resolverMcp.ts +8 -4
- package/src/types.ts +18 -12
- package/src/utils.ts +14 -30
package/dist/index.cjs
CHANGED
|
@@ -247,12 +247,12 @@ var URLPath = class {
|
|
|
247
247
|
get object() {
|
|
248
248
|
return this.toObject();
|
|
249
249
|
}
|
|
250
|
-
/** Returns a map of path parameter names, or `
|
|
250
|
+
/** Returns a map of path parameter names, or `null` when the path has no parameters.
|
|
251
251
|
*
|
|
252
252
|
* @example
|
|
253
253
|
* ```ts
|
|
254
254
|
* new URLPath('/pet/{petId}').params // { petId: 'petId' }
|
|
255
|
-
* new URLPath('/pet').params //
|
|
255
|
+
* new URLPath('/pet').params // null
|
|
256
256
|
* ```
|
|
257
257
|
*/
|
|
258
258
|
get params() {
|
|
@@ -290,12 +290,13 @@ var URLPath = class {
|
|
|
290
290
|
* @example
|
|
291
291
|
* new URLPath('/pet/{petId}').toTemplateString() // '`/pet/${petId}`'
|
|
292
292
|
*/
|
|
293
|
-
toTemplateString({ prefix
|
|
294
|
-
|
|
293
|
+
toTemplateString({ prefix, replacer } = {}) {
|
|
294
|
+
const result = this.path.split(/\{([^}]+)\}/).map((part, i) => {
|
|
295
295
|
if (i % 2 === 0) return part;
|
|
296
296
|
const param = this.#transformParam(part);
|
|
297
297
|
return `\${${replacer ? replacer(param) : param}}`;
|
|
298
|
-
}).join("")
|
|
298
|
+
}).join("");
|
|
299
|
+
return `\`${prefix ?? ""}${result}\``;
|
|
299
300
|
}
|
|
300
301
|
/**
|
|
301
302
|
* Extracts all `{param}` segments from the path and returns them as a key-value map.
|
|
@@ -314,7 +315,7 @@ var URLPath = class {
|
|
|
314
315
|
const key = replacer ? replacer(param) : param;
|
|
315
316
|
params[key] = key;
|
|
316
317
|
});
|
|
317
|
-
return Object.keys(params).length > 0 ? params :
|
|
318
|
+
return Object.keys(params).length > 0 ? params : null;
|
|
318
319
|
}
|
|
319
320
|
/** Converts the OpenAPI path to Express-style colon syntax.
|
|
320
321
|
*
|
|
@@ -330,9 +331,9 @@ var URLPath = class {
|
|
|
330
331
|
//#endregion
|
|
331
332
|
//#region ../../internals/shared/src/operation.ts
|
|
332
333
|
function getOperationLink(node, link) {
|
|
333
|
-
if (!link) return;
|
|
334
|
-
if (typeof link === "function") return link(node);
|
|
335
|
-
if (link === "urlPath") return node.path ? `{@link ${new URLPath(node.path).URL}}` :
|
|
334
|
+
if (!link) return null;
|
|
335
|
+
if (typeof link === "function") return link(node) ?? null;
|
|
336
|
+
if (link === "urlPath") return node.path ? `{@link ${new URLPath(node.path).URL}}` : null;
|
|
336
337
|
return `{@link ${node.path.replaceAll("{", ":").replaceAll("}", "")}}`;
|
|
337
338
|
}
|
|
338
339
|
function buildOperationComments(node, options = {}) {
|
|
@@ -363,15 +364,15 @@ function getOperationParameters(node, options = {}) {
|
|
|
363
364
|
}
|
|
364
365
|
function getStatusCodeNumber(statusCode) {
|
|
365
366
|
const code = Number(statusCode);
|
|
366
|
-
return Number.isNaN(code) ?
|
|
367
|
+
return Number.isNaN(code) ? null : code;
|
|
367
368
|
}
|
|
368
369
|
function isSuccessStatusCode(statusCode) {
|
|
369
370
|
const code = getStatusCodeNumber(statusCode);
|
|
370
|
-
return code !==
|
|
371
|
+
return code !== null && code >= 200 && code < 300;
|
|
371
372
|
}
|
|
372
373
|
function isErrorStatusCode(statusCode) {
|
|
373
374
|
const code = getStatusCodeNumber(statusCode);
|
|
374
|
-
return code !==
|
|
375
|
+
return code !== null && code >= 400;
|
|
375
376
|
}
|
|
376
377
|
function resolveErrorNames(node, resolver) {
|
|
377
378
|
return node.responses.filter((response) => isErrorStatusCode(response.statusCode)).map((response) => resolver.resolveResponseStatusName(node, response.statusCode));
|
|
@@ -398,7 +399,7 @@ function resolveOperationTypeNames(node, resolver, options = {}) {
|
|
|
398
399
|
...query.map((param) => resolver.resolveQueryParamsName(node, param)),
|
|
399
400
|
...header.map((param) => resolver.resolveHeaderParamsName(node, param))
|
|
400
401
|
];
|
|
401
|
-
const bodyAndResponseNames = [node.requestBody?.content?.[0]?.schema ? resolver.resolveDataName(node) :
|
|
402
|
+
const bodyAndResponseNames = [node.requestBody?.content?.[0]?.schema ? resolver.resolveDataName(node) : null, resolver.resolveResponseName(node)];
|
|
402
403
|
const result = (options.order === "body-response-first" ? [
|
|
403
404
|
...bodyAndResponseNames,
|
|
404
405
|
...paramNames,
|
|
@@ -413,6 +414,7 @@ function resolveOperationTypeNames(node, resolver, options = {}) {
|
|
|
413
414
|
}
|
|
414
415
|
function findSuccessStatusCode(responses) {
|
|
415
416
|
for (const response of responses) if (isSuccessStatusCode(response.statusCode)) return response.statusCode;
|
|
417
|
+
return null;
|
|
416
418
|
}
|
|
417
419
|
//#endregion
|
|
418
420
|
//#region ../../internals/shared/src/params.ts
|
|
@@ -424,10 +426,10 @@ function buildParamsMapping(originalParams, mappedParams) {
|
|
|
424
426
|
mapping[param.name] = mappedName;
|
|
425
427
|
if (param.name !== mappedName) hasChanged = true;
|
|
426
428
|
});
|
|
427
|
-
return hasChanged ? mapping :
|
|
429
|
+
return hasChanged ? mapping : null;
|
|
428
430
|
}
|
|
429
431
|
function buildTransformedParamsMapping(params, transformName) {
|
|
430
|
-
if (!params.length) return;
|
|
432
|
+
if (!params.length) return null;
|
|
431
433
|
return buildParamsMapping(params, params.map((param) => ({
|
|
432
434
|
...param,
|
|
433
435
|
name: transformName(param.name)
|
|
@@ -448,7 +450,7 @@ function McpHandler({ name, node, resolver, baseURL, dataReturnType, paramsCasin
|
|
|
448
450
|
const isFormData = contentType === "multipart/form-data";
|
|
449
451
|
const { query: queryParams, header: headerParams } = getOperationParameters(node, { paramsCasing });
|
|
450
452
|
const { path: originalPathParams, query: originalQueryParams, header: originalHeaderParams } = getOperationParameters(node);
|
|
451
|
-
const requestName = node.requestBody?.content?.[0]?.schema ? resolver.resolveDataName(node) :
|
|
453
|
+
const requestName = node.requestBody?.content?.[0]?.schema ? resolver.resolveDataName(node) : null;
|
|
452
454
|
const responseName = resolver.resolveResponseName(node);
|
|
453
455
|
const errorResponses = node.responses.filter((r) => Number(r.statusCode) >= 400).map((r) => resolver.resolveResponseStatusName(node, r.statusCode));
|
|
454
456
|
const generics = [
|
|
@@ -464,11 +466,11 @@ function McpHandler({ name, node, resolver, baseURL, dataReturnType, paramsCasin
|
|
|
464
466
|
});
|
|
465
467
|
const baseParamsSignature = declarationPrinter.print(paramsNode) ?? "";
|
|
466
468
|
const paramsSignature = baseParamsSignature ? `${baseParamsSignature}, request: RequestHandlerExtra<ServerRequest, ServerNotification>` : "request: RequestHandlerExtra<ServerRequest, ServerNotification>";
|
|
467
|
-
const pathParamsMapping = paramsCasing ? buildTransformedParamsMapping(originalPathParams, camelCase) :
|
|
468
|
-
const queryParamsMapping = paramsCasing ? buildTransformedParamsMapping(originalQueryParams, camelCase) :
|
|
469
|
-
const headerParamsMapping = paramsCasing ? buildTransformedParamsMapping(originalHeaderParams, camelCase) :
|
|
470
|
-
const contentTypeHeader = contentType && contentType !== "application/json" && contentType !== "multipart/form-data" ? `'Content-Type': '${contentType}'` :
|
|
471
|
-
const headers = [headerParams.length ? headerParamsMapping ? "...mappedHeaders" : "...headers" :
|
|
469
|
+
const pathParamsMapping = paramsCasing ? buildTransformedParamsMapping(originalPathParams, camelCase) : null;
|
|
470
|
+
const queryParamsMapping = paramsCasing ? buildTransformedParamsMapping(originalQueryParams, camelCase) : null;
|
|
471
|
+
const headerParamsMapping = paramsCasing ? buildTransformedParamsMapping(originalHeaderParams, camelCase) : null;
|
|
472
|
+
const contentTypeHeader = contentType && contentType !== "application/json" && contentType !== "multipart/form-data" ? `'Content-Type': '${contentType}'` : null;
|
|
473
|
+
const headers = [headerParams.length ? headerParamsMapping ? "...mappedHeaders" : "...headers" : null, contentTypeHeader].filter(Boolean);
|
|
472
474
|
const fetchConfig = [];
|
|
473
475
|
fetchConfig.push(`method: ${JSON.stringify(node.method.toUpperCase())}`);
|
|
474
476
|
fetchConfig.push(`url: ${urlPath.template}`);
|
|
@@ -546,33 +548,23 @@ function zodGroupExpr(entry) {
|
|
|
546
548
|
* Used as fallback when no named zod schema is available for a path parameter.
|
|
547
549
|
*/
|
|
548
550
|
function zodExprFromSchemaNode(schema) {
|
|
549
|
-
|
|
550
|
-
|
|
551
|
-
case "enum": {
|
|
551
|
+
const baseExpr = (() => {
|
|
552
|
+
if (schema.type === "enum") {
|
|
552
553
|
const rawValues = schema.namedEnumValues?.length ? schema.namedEnumValues.map((v) => v.value) : (schema.enumValues ?? []).filter((v) => v !== null);
|
|
553
|
-
if (rawValues.length > 0 && rawValues.every((v) => typeof v === "string"))
|
|
554
|
-
|
|
554
|
+
if (rawValues.length > 0 && rawValues.every((v) => typeof v === "string")) return `z.enum([${rawValues.map((v) => JSON.stringify(v)).join(", ")}])`;
|
|
555
|
+
if (rawValues.length > 0) {
|
|
555
556
|
const literals = rawValues.map((v) => `z.literal(${JSON.stringify(v)})`);
|
|
556
|
-
|
|
557
|
-
}
|
|
558
|
-
|
|
557
|
+
return literals.length === 1 ? literals[0] : `z.union([${literals.join(", ")}])`;
|
|
558
|
+
}
|
|
559
|
+
return "z.string()";
|
|
559
560
|
}
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
expr = "z.boolean()";
|
|
568
|
-
break;
|
|
569
|
-
case "array":
|
|
570
|
-
expr = "z.array(z.unknown())";
|
|
571
|
-
break;
|
|
572
|
-
default: expr = "z.string()";
|
|
573
|
-
}
|
|
574
|
-
if (schema.nullable) expr = `${expr}.nullable()`;
|
|
575
|
-
return expr;
|
|
561
|
+
if (schema.type === "integer") return "z.coerce.number()";
|
|
562
|
+
if (schema.type === "number") return "z.number()";
|
|
563
|
+
if (schema.type === "boolean") return "z.boolean()";
|
|
564
|
+
if (schema.type === "array") return "z.array(z.unknown())";
|
|
565
|
+
return "z.string()";
|
|
566
|
+
})();
|
|
567
|
+
return schema.nullable ? `${baseExpr}.nullable()` : baseExpr;
|
|
576
568
|
}
|
|
577
569
|
//#endregion
|
|
578
570
|
//#region src/components/Server.tsx
|
|
@@ -621,9 +613,9 @@ function Server({ name, serverName, serverVersion, paramsCasing, operations }) {
|
|
|
621
613
|
const paramsNode = entries.length ? _kubb_core.ast.createFunctionParameters({ params: [_kubb_core.ast.createParameterGroup({ properties: entries.map((e) => _kubb_core.ast.createFunctionParameter({
|
|
622
614
|
name: e.key,
|
|
623
615
|
optional: false
|
|
624
|
-
})) })] }) :
|
|
616
|
+
})) })] }) : null;
|
|
625
617
|
const destructured = paramsNode ? keysPrinter.print(paramsNode) ?? "" : "";
|
|
626
|
-
const inputSchema = entries.length ? `{ ${entries.map((e) => `${e.key}: ${e.value}`).join(", ")} }` :
|
|
618
|
+
const inputSchema = entries.length ? `{ ${entries.map((e) => `${e.key}: ${e.value}`).join(", ")} }` : null;
|
|
627
619
|
const outputSchema = zod.responseName;
|
|
628
620
|
const config = [
|
|
629
621
|
tool.title ? `title: ${JSON.stringify(tool.title)}` : null,
|
|
@@ -664,6 +656,12 @@ server.registerTool(${JSON.stringify(tool.name)}, {
|
|
|
664
656
|
}
|
|
665
657
|
//#endregion
|
|
666
658
|
//#region src/generators/mcpGenerator.tsx
|
|
659
|
+
/**
|
|
660
|
+
* Built-in operation generator for `@kubb/plugin-mcp`. Emits one MCP tool
|
|
661
|
+
* handler per OpenAPI operation, wiring the input Zod schema, the HTTP call,
|
|
662
|
+
* and the response shape into a single function that an MCP server can
|
|
663
|
+
* register as a callable tool.
|
|
664
|
+
*/
|
|
667
665
|
const mcpGenerator = (0, _kubb_core.defineGenerator)({
|
|
668
666
|
name: "mcp",
|
|
669
667
|
renderer: _kubb_renderer_jsx.jsxRendererSync,
|
|
@@ -687,7 +685,7 @@ const mcpGenerator = (0, _kubb_core.defineGenerator)({
|
|
|
687
685
|
}, {
|
|
688
686
|
root,
|
|
689
687
|
output,
|
|
690
|
-
group
|
|
688
|
+
group: group ?? void 0
|
|
691
689
|
}),
|
|
692
690
|
fileTs: tsResolver.resolveFile({
|
|
693
691
|
name: node.operationId,
|
|
@@ -697,7 +695,7 @@ const mcpGenerator = (0, _kubb_core.defineGenerator)({
|
|
|
697
695
|
}, {
|
|
698
696
|
root,
|
|
699
697
|
output: pluginTs.options?.output ?? output,
|
|
700
|
-
group: pluginTs.options?.group
|
|
698
|
+
group: pluginTs.options?.group ?? void 0
|
|
701
699
|
})
|
|
702
700
|
};
|
|
703
701
|
return /* @__PURE__ */ (0, _kubb_renderer_jsx_jsx_runtime.jsxs)(_kubb_renderer_jsx.File, {
|
|
@@ -797,7 +795,7 @@ const serverGenerator = (0, _kubb_core.defineGenerator)({
|
|
|
797
795
|
name: "operations",
|
|
798
796
|
renderer: _kubb_renderer_jsx.jsxRendererSync,
|
|
799
797
|
operations(nodes, ctx) {
|
|
800
|
-
const { config, resolver, plugin, driver, root
|
|
798
|
+
const { config, resolver, plugin, driver, root } = ctx;
|
|
801
799
|
const { output, paramsCasing, group } = ctx.options;
|
|
802
800
|
const pluginZod = driver.getPlugin(_kubb_plugin_zod.pluginZodName);
|
|
803
801
|
if (!pluginZod) return;
|
|
@@ -823,7 +821,7 @@ const serverGenerator = (0, _kubb_core.defineGenerator)({
|
|
|
823
821
|
}, {
|
|
824
822
|
root,
|
|
825
823
|
output,
|
|
826
|
-
group
|
|
824
|
+
group: group ?? void 0
|
|
827
825
|
});
|
|
828
826
|
const zodFile = zodResolver.resolveFile({
|
|
829
827
|
name: node.operationId,
|
|
@@ -833,11 +831,11 @@ const serverGenerator = (0, _kubb_core.defineGenerator)({
|
|
|
833
831
|
}, {
|
|
834
832
|
root,
|
|
835
833
|
output: pluginZod.options?.output ?? output,
|
|
836
|
-
group: pluginZod.options?.group
|
|
834
|
+
group: pluginZod.options?.group ?? void 0
|
|
837
835
|
});
|
|
838
|
-
const requestName = node.requestBody?.content?.[0]?.schema ? zodResolver.resolveDataName(node) :
|
|
836
|
+
const requestName = node.requestBody?.content?.[0]?.schema ? zodResolver.resolveDataName(node) : null;
|
|
839
837
|
const successStatus = findSuccessStatusCode(node.responses);
|
|
840
|
-
const responseName = successStatus ? zodResolver.resolveResponseStatusName(node, successStatus) :
|
|
838
|
+
const responseName = successStatus ? zodResolver.resolveResponseStatusName(node, successStatus) : null;
|
|
841
839
|
const resolveParams = (params) => params.map((p) => ({
|
|
842
840
|
name: p.name,
|
|
843
841
|
schemaName: zodResolver.resolveParamName(node, p)
|
|
@@ -854,8 +852,8 @@ const serverGenerator = (0, _kubb_core.defineGenerator)({
|
|
|
854
852
|
},
|
|
855
853
|
zod: {
|
|
856
854
|
pathParams: resolveParams(pathParams),
|
|
857
|
-
queryParams: queryParams.length ? resolveParams(queryParams) :
|
|
858
|
-
headerParams: headerParams.length ? resolveParams(headerParams) :
|
|
855
|
+
queryParams: queryParams.length ? resolveParams(queryParams) : null,
|
|
856
|
+
headerParams: headerParams.length ? resolveParams(headerParams) : null,
|
|
859
857
|
requestName,
|
|
860
858
|
responseName,
|
|
861
859
|
file: zodFile
|
|
@@ -886,11 +884,11 @@ const serverGenerator = (0, _kubb_core.defineGenerator)({
|
|
|
886
884
|
baseName: serverFile.baseName,
|
|
887
885
|
path: serverFile.path,
|
|
888
886
|
meta: serverFile.meta,
|
|
889
|
-
banner: resolver.resolveBanner(
|
|
887
|
+
banner: resolver.resolveBanner(ctx.meta, {
|
|
890
888
|
output,
|
|
891
889
|
config
|
|
892
890
|
}),
|
|
893
|
-
footer: resolver.resolveFooter(
|
|
891
|
+
footer: resolver.resolveFooter(ctx.meta, {
|
|
894
892
|
output,
|
|
895
893
|
config
|
|
896
894
|
}),
|
|
@@ -910,8 +908,8 @@ const serverGenerator = (0, _kubb_core.defineGenerator)({
|
|
|
910
908
|
imports,
|
|
911
909
|
/* @__PURE__ */ (0, _kubb_renderer_jsx_jsx_runtime.jsx)(Server, {
|
|
912
910
|
name,
|
|
913
|
-
serverName:
|
|
914
|
-
serverVersion:
|
|
911
|
+
serverName: ctx.meta.title ?? "server",
|
|
912
|
+
serverVersion: ctx.meta.version ?? "0.0.0",
|
|
915
913
|
paramsCasing,
|
|
916
914
|
operations: operationsMapped
|
|
917
915
|
})
|
|
@@ -925,7 +923,7 @@ const serverGenerator = (0, _kubb_core.defineGenerator)({
|
|
|
925
923
|
children: `
|
|
926
924
|
{
|
|
927
925
|
"mcpServers": {
|
|
928
|
-
"${
|
|
926
|
+
"${ctx.meta.title || "server"}": {
|
|
929
927
|
"type": "stdio",
|
|
930
928
|
"command": "npx",
|
|
931
929
|
"args": ["tsx", "${node_path.default.relative(node_path.default.dirname(jsonFile.path), serverFile.path)}"]
|
|
@@ -940,12 +938,16 @@ const serverGenerator = (0, _kubb_core.defineGenerator)({
|
|
|
940
938
|
//#endregion
|
|
941
939
|
//#region src/resolvers/resolverMcp.ts
|
|
942
940
|
/**
|
|
943
|
-
*
|
|
941
|
+
* Default resolver used by `@kubb/plugin-mcp`. Decides the names and file
|
|
942
|
+
* paths for every generated MCP tool handler. Function names get a `Handler`
|
|
943
|
+
* suffix so an operation `addPet` becomes `addPetHandler`.
|
|
944
944
|
*
|
|
945
|
-
*
|
|
945
|
+
* @example Resolve a handler name
|
|
946
|
+
* ```ts
|
|
947
|
+
* import { resolverMcp } from '@kubb/plugin-mcp'
|
|
946
948
|
*
|
|
947
|
-
*
|
|
948
|
-
*
|
|
949
|
+
* resolverMcp.default('addPet', 'function') // 'addPetHandler'
|
|
950
|
+
* ```
|
|
949
951
|
*/
|
|
950
952
|
const resolverMcp = (0, _kubb_core.defineResolver)(() => ({
|
|
951
953
|
name: "default",
|
|
@@ -966,7 +968,39 @@ const resolverMcp = (0, _kubb_core.defineResolver)(() => ({
|
|
|
966
968
|
}));
|
|
967
969
|
//#endregion
|
|
968
970
|
//#region src/plugin.ts
|
|
971
|
+
/**
|
|
972
|
+
* Canonical plugin name for `@kubb/plugin-mcp`. Used for driver lookups and
|
|
973
|
+
* cross-plugin dependency references.
|
|
974
|
+
*/
|
|
969
975
|
const pluginMcpName = "plugin-mcp";
|
|
976
|
+
/**
|
|
977
|
+
* Generates a Model Context Protocol (MCP) server from an OpenAPI spec. Every
|
|
978
|
+
* operation becomes a typed MCP tool that AI assistants (Claude Desktop, Claude
|
|
979
|
+
* Code, MCP-compatible clients) can call directly.
|
|
980
|
+
*
|
|
981
|
+
* @example
|
|
982
|
+
* ```ts
|
|
983
|
+
* import { defineConfig } from 'kubb'
|
|
984
|
+
* import { pluginTs } from '@kubb/plugin-ts'
|
|
985
|
+
* import { pluginClient } from '@kubb/plugin-client'
|
|
986
|
+
* import { pluginZod } from '@kubb/plugin-zod'
|
|
987
|
+
* import { pluginMcp } from '@kubb/plugin-mcp'
|
|
988
|
+
*
|
|
989
|
+
* export default defineConfig({
|
|
990
|
+
* input: { path: './petStore.yaml' },
|
|
991
|
+
* output: { path: './src/gen' },
|
|
992
|
+
* plugins: [
|
|
993
|
+
* pluginTs(),
|
|
994
|
+
* pluginClient(),
|
|
995
|
+
* pluginZod(),
|
|
996
|
+
* pluginMcp({
|
|
997
|
+
* output: { path: './mcp' },
|
|
998
|
+
* client: { baseURL: 'https://petstore.swagger.io/v2' },
|
|
999
|
+
* }),
|
|
1000
|
+
* ],
|
|
1001
|
+
* })
|
|
1002
|
+
* ```
|
|
1003
|
+
*/
|
|
970
1004
|
const pluginMcp = (0, _kubb_core.definePlugin)((options) => {
|
|
971
1005
|
const { output = {
|
|
972
1006
|
path: "mcp",
|
|
@@ -980,7 +1014,7 @@ const pluginMcp = (0, _kubb_core.definePlugin)((options) => {
|
|
|
980
1014
|
if (group.type === "path") return `${ctx.group.split("/")[1]}`;
|
|
981
1015
|
return `${camelCase(ctx.group)}Requests`;
|
|
982
1016
|
}
|
|
983
|
-
} :
|
|
1017
|
+
} : null;
|
|
984
1018
|
return {
|
|
985
1019
|
name: pluginMcpName,
|
|
986
1020
|
options,
|