@smithery/sdk 1.5.6 → 1.5.8
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/server/stateful.js +0 -1
- package/dist/server/stateless.js +0 -1
- package/dist/shared/config.d.ts +3 -13
- package/dist/shared/config.js +68 -52
- package/package.json +1 -1
package/dist/server/stateful.js
CHANGED
|
@@ -102,7 +102,6 @@ export function createStatefulServer(createMcpServer, options) {
|
|
|
102
102
|
$id: `${req.protocol}://${req.get("host")}/.well-known/mcp-config`,
|
|
103
103
|
title: "MCP Session Configuration",
|
|
104
104
|
description: "Schema for the /mcp endpoint configuration",
|
|
105
|
-
"x-mcp-version": "1.0",
|
|
106
105
|
"x-query-style": "dot+bracket",
|
|
107
106
|
...baseSchema,
|
|
108
107
|
};
|
package/dist/server/stateless.js
CHANGED
|
@@ -98,7 +98,6 @@ export function createStatelessServer(createMcpServer, options) {
|
|
|
98
98
|
$id: `${req.protocol}://${req.get("host")}/.well-known/mcp-config`,
|
|
99
99
|
title: "MCP Session Configuration",
|
|
100
100
|
description: "Schema for the /mcp endpoint configuration",
|
|
101
|
-
"x-mcp-version": "1.0",
|
|
102
101
|
"x-query-style": "dot+bracket",
|
|
103
102
|
...baseSchema,
|
|
104
103
|
};
|
package/dist/shared/config.d.ts
CHANGED
|
@@ -9,28 +9,17 @@ export interface SmitheryUrlOptions {
|
|
|
9
9
|
* Creates a URL to connect to the Smithery MCP server.
|
|
10
10
|
* @param baseUrl The base URL of the Smithery server
|
|
11
11
|
* @param options Optional configuration object
|
|
12
|
-
* @returns A URL
|
|
12
|
+
* @returns A URL with config encoded using dot-notation query params (e.g. model.name=gpt-4&debug=true)
|
|
13
13
|
*/
|
|
14
14
|
export declare function createSmitheryUrl(baseUrl: string, options?: SmitheryUrlOptions): URL;
|
|
15
|
-
/**
|
|
16
|
-
* Parses the config from an express request by checking the query parameter "config".
|
|
17
|
-
* @param req The express request
|
|
18
|
-
* @returns The config
|
|
19
|
-
*/
|
|
20
|
-
export declare function parseExpressRequestConfig(req: ExpressRequest): Record<string, unknown>;
|
|
21
15
|
/**
|
|
22
16
|
* Parses and validates config from an Express request with optional Zod schema validation
|
|
23
|
-
* Supports
|
|
17
|
+
* Supports dot-notation config parameters (e.g., foo=bar, a.b=c)
|
|
24
18
|
* @param req The express request
|
|
25
19
|
* @param schema Optional Zod schema for validation
|
|
26
20
|
* @returns Result with either parsed data or error response
|
|
27
21
|
*/
|
|
28
22
|
export declare function parseAndValidateConfig<T = Record<string, unknown>>(req: ExpressRequest, schema?: z.ZodSchema<T>): import("okay-error").Err<{
|
|
29
|
-
title: string;
|
|
30
|
-
status: number;
|
|
31
|
-
detail: string;
|
|
32
|
-
instance: string;
|
|
33
|
-
}> | import("okay-error").Err<{
|
|
34
23
|
readonly title: "Invalid configuration parameters";
|
|
35
24
|
readonly status: 422;
|
|
36
25
|
readonly detail: "One or more config parameters are invalid.";
|
|
@@ -48,3 +37,4 @@ export declare function parseAndValidateConfig<T = Record<string, unknown>>(req:
|
|
|
48
37
|
received: unknown;
|
|
49
38
|
}[];
|
|
50
39
|
}> | import("okay-error").Ok<T>;
|
|
40
|
+
export declare function parseConfigFromQuery(query: Iterable<[string, unknown]>): Record<string, unknown>;
|
package/dist/shared/config.js
CHANGED
|
@@ -1,19 +1,54 @@
|
|
|
1
1
|
import _ from "lodash";
|
|
2
2
|
import { err, ok } from "okay-error";
|
|
3
3
|
import { zodToJsonSchema } from "zod-to-json-schema";
|
|
4
|
+
function isPlainObject(value) {
|
|
5
|
+
return value !== null && typeof value === "object" && !Array.isArray(value);
|
|
6
|
+
}
|
|
7
|
+
function appendConfigAsDotParams(url, config) {
|
|
8
|
+
function add(pathParts, value) {
|
|
9
|
+
if (Array.isArray(value)) {
|
|
10
|
+
for (let index = 0; index < value.length; index++) {
|
|
11
|
+
add([...pathParts, String(index)], value[index]);
|
|
12
|
+
}
|
|
13
|
+
return;
|
|
14
|
+
}
|
|
15
|
+
if (isPlainObject(value)) {
|
|
16
|
+
for (const [key, nested] of Object.entries(value)) {
|
|
17
|
+
add([...pathParts, key], nested);
|
|
18
|
+
}
|
|
19
|
+
return;
|
|
20
|
+
}
|
|
21
|
+
const key = pathParts.join(".");
|
|
22
|
+
let stringValue;
|
|
23
|
+
switch (typeof value) {
|
|
24
|
+
case "string":
|
|
25
|
+
stringValue = value;
|
|
26
|
+
break;
|
|
27
|
+
case "number":
|
|
28
|
+
case "boolean":
|
|
29
|
+
stringValue = String(value);
|
|
30
|
+
break;
|
|
31
|
+
default:
|
|
32
|
+
stringValue = JSON.stringify(value);
|
|
33
|
+
}
|
|
34
|
+
url.searchParams.set(key, stringValue);
|
|
35
|
+
}
|
|
36
|
+
if (isPlainObject(config)) {
|
|
37
|
+
for (const [key, value] of Object.entries(config)) {
|
|
38
|
+
add([key], value);
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
}
|
|
4
42
|
/**
|
|
5
43
|
* Creates a URL to connect to the Smithery MCP server.
|
|
6
44
|
* @param baseUrl The base URL of the Smithery server
|
|
7
45
|
* @param options Optional configuration object
|
|
8
|
-
* @returns A URL
|
|
46
|
+
* @returns A URL with config encoded using dot-notation query params (e.g. model.name=gpt-4&debug=true)
|
|
9
47
|
*/
|
|
10
48
|
export function createSmitheryUrl(baseUrl, options) {
|
|
11
49
|
const url = new URL(`${baseUrl}/mcp`);
|
|
12
50
|
if (options?.config) {
|
|
13
|
-
|
|
14
|
-
? btoa(JSON.stringify(options.config))
|
|
15
|
-
: Buffer.from(JSON.stringify(options.config)).toString("base64");
|
|
16
|
-
url.searchParams.set("config", param);
|
|
51
|
+
appendConfigAsDotParams(url, options.config);
|
|
17
52
|
}
|
|
18
53
|
if (options?.apiKey) {
|
|
19
54
|
url.searchParams.set("api_key", options.apiKey);
|
|
@@ -23,60 +58,15 @@ export function createSmitheryUrl(baseUrl, options) {
|
|
|
23
58
|
}
|
|
24
59
|
return url;
|
|
25
60
|
}
|
|
26
|
-
/**
|
|
27
|
-
* Parses the config from an express request by checking the query parameter "config".
|
|
28
|
-
* @param req The express request
|
|
29
|
-
* @returns The config
|
|
30
|
-
*/
|
|
31
|
-
export function parseExpressRequestConfig(req) {
|
|
32
|
-
return JSON.parse(Buffer.from(req.query.config, "base64").toString());
|
|
33
|
-
}
|
|
34
61
|
/**
|
|
35
62
|
* Parses and validates config from an Express request with optional Zod schema validation
|
|
36
|
-
* Supports
|
|
63
|
+
* Supports dot-notation config parameters (e.g., foo=bar, a.b=c)
|
|
37
64
|
* @param req The express request
|
|
38
65
|
* @param schema Optional Zod schema for validation
|
|
39
66
|
* @returns Result with either parsed data or error response
|
|
40
67
|
*/
|
|
41
68
|
export function parseAndValidateConfig(req, schema) {
|
|
42
|
-
|
|
43
|
-
let config = {};
|
|
44
|
-
// 1. Process base64-encoded config parameter if present
|
|
45
|
-
if (req.query.config) {
|
|
46
|
-
try {
|
|
47
|
-
config = parseExpressRequestConfig(req);
|
|
48
|
-
}
|
|
49
|
-
catch (configError) {
|
|
50
|
-
return err({
|
|
51
|
-
title: "Invalid config parameter",
|
|
52
|
-
status: 400,
|
|
53
|
-
detail: "Failed to parse config parameter",
|
|
54
|
-
instance: req.originalUrl,
|
|
55
|
-
});
|
|
56
|
-
}
|
|
57
|
-
}
|
|
58
|
-
// 2. Process dot-notation config parameters (foo=bar, a.b=c)
|
|
59
|
-
// This allows URL params like ?server.host=localhost&server.port=8080&debug=true
|
|
60
|
-
for (const [key, value] of Object.entries(req.query)) {
|
|
61
|
-
// Skip reserved parameters
|
|
62
|
-
if (key === "config" || key === "api_key" || key === "profile")
|
|
63
|
-
continue;
|
|
64
|
-
const pathParts = key.split(".");
|
|
65
|
-
// Handle array values from Express query parsing
|
|
66
|
-
const rawValue = Array.isArray(value) ? value[0] : value;
|
|
67
|
-
if (typeof rawValue !== "string")
|
|
68
|
-
continue;
|
|
69
|
-
// Try to parse value as JSON (for booleans, numbers, objects)
|
|
70
|
-
let parsedValue = rawValue;
|
|
71
|
-
try {
|
|
72
|
-
parsedValue = JSON.parse(rawValue);
|
|
73
|
-
}
|
|
74
|
-
catch {
|
|
75
|
-
// If parsing fails, use the raw string value
|
|
76
|
-
}
|
|
77
|
-
// Use lodash's set method to handle nested paths
|
|
78
|
-
_.set(config, pathParts, parsedValue);
|
|
79
|
-
}
|
|
69
|
+
const config = parseConfigFromQuery(Object.entries(req.query));
|
|
80
70
|
// Validate config against schema if provided
|
|
81
71
|
if (schema) {
|
|
82
72
|
const result = schema.safeParse(config);
|
|
@@ -114,3 +104,29 @@ export function parseAndValidateConfig(req, schema) {
|
|
|
114
104
|
}
|
|
115
105
|
return ok(config);
|
|
116
106
|
}
|
|
107
|
+
// Process dot-notation config parameters from query parameters (foo=bar, a.b=c)
|
|
108
|
+
// This allows URL params like ?server.host=localhost&server.port=8080&debug=true
|
|
109
|
+
export function parseConfigFromQuery(query) {
|
|
110
|
+
const config = {};
|
|
111
|
+
for (const [key, value] of query) {
|
|
112
|
+
// Skip reserved parameters
|
|
113
|
+
if (key === "api_key" || key === "profile")
|
|
114
|
+
continue;
|
|
115
|
+
const pathParts = key.split(".");
|
|
116
|
+
// Handle array values from Express query parsing
|
|
117
|
+
const rawValue = Array.isArray(value) ? value[0] : value;
|
|
118
|
+
if (typeof rawValue !== "string")
|
|
119
|
+
continue;
|
|
120
|
+
// Try to parse value as JSON (for booleans, numbers, objects)
|
|
121
|
+
let parsedValue = rawValue;
|
|
122
|
+
try {
|
|
123
|
+
parsedValue = JSON.parse(rawValue);
|
|
124
|
+
}
|
|
125
|
+
catch {
|
|
126
|
+
// If parsing fails, use the raw string value
|
|
127
|
+
}
|
|
128
|
+
// Use lodash's set method to handle nested paths
|
|
129
|
+
_.set(config, pathParts, parsedValue);
|
|
130
|
+
}
|
|
131
|
+
return config;
|
|
132
|
+
}
|