@tigerdata/mcp-boilerplate 0.1.5 → 0.1.7
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/StatusError.d.ts +4 -0
- package/dist/cliEntrypoint.d.ts +1 -0
- package/dist/http/api.d.ts +5 -0
- package/dist/http/mcp.d.ts +8 -0
- package/dist/http/mcp.js +31 -5
- package/dist/httpServer.d.ts +21 -0
- package/dist/httpServer.js +2 -1
- package/dist/instrumentation.d.ts +3 -0
- package/dist/logger.d.ts +9 -0
- package/dist/mcpServer.d.ts +16 -0
- package/dist/mcpServer.js +2 -0
- package/dist/registerExitHandlers.d.ts +1 -0
- package/dist/stdio.d.ts +12 -0
- package/dist/tracing.d.ts +4 -0
- package/dist/types.d.ts +33 -0
- package/package.json +1 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare function cliEntrypoint(stdioEntrypoint: string, httpEntrypoint: string, instrumentation?: string): Promise<void>;
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* REST API alternative to MCP for direct use of the same tools.
|
|
3
|
+
*/
|
|
4
|
+
import { ApiFactory, RouterFactoryResult } from '../types.js';
|
|
5
|
+
export declare const apiRouterFactory: <Context extends Record<string, unknown>>(context: Context, apiFactories: readonly ApiFactory<Context, any, any>[]) => RouterFactoryResult;
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
|
|
2
|
+
import { RouterFactoryResult } from '../types.js';
|
|
3
|
+
export declare const mcpRouterFactory: <Context extends Record<string, unknown>>(context: Context, createServer: (context: Context) => {
|
|
4
|
+
server: McpServer;
|
|
5
|
+
}, { name, stateful, }?: {
|
|
6
|
+
name?: string;
|
|
7
|
+
stateful?: boolean;
|
|
8
|
+
}) => RouterFactoryResult;
|
package/dist/http/mcp.js
CHANGED
|
@@ -4,7 +4,7 @@ import { Router } from 'express';
|
|
|
4
4
|
import { randomUUID } from 'node:crypto';
|
|
5
5
|
import getRawBody from 'raw-body';
|
|
6
6
|
import { log } from '../logger.js';
|
|
7
|
-
export const mcpRouterFactory = (context, createServer, stateful = true) => {
|
|
7
|
+
export const mcpRouterFactory = (context, createServer, { name, stateful = true, } = {}) => {
|
|
8
8
|
const router = Router();
|
|
9
9
|
const transports = new Map();
|
|
10
10
|
const handleStatelessRequest = async (req, res) => {
|
|
@@ -99,12 +99,12 @@ export const mcpRouterFactory = (context, createServer, stateful = true) => {
|
|
|
99
99
|
const sessionId = req.headers['mcp-session-id'];
|
|
100
100
|
if (!stateful) {
|
|
101
101
|
res.status(405).json({
|
|
102
|
-
jsonrpc:
|
|
102
|
+
jsonrpc: '2.0',
|
|
103
103
|
error: {
|
|
104
104
|
code: -32000,
|
|
105
|
-
message:
|
|
105
|
+
message: 'Method not allowed.',
|
|
106
106
|
},
|
|
107
|
-
id: null
|
|
107
|
+
id: null,
|
|
108
108
|
});
|
|
109
109
|
return;
|
|
110
110
|
}
|
|
@@ -133,7 +133,33 @@ export const mcpRouterFactory = (context, createServer, stateful = true) => {
|
|
|
133
133
|
await transports.get(sessionId).handleRequest(req, res);
|
|
134
134
|
};
|
|
135
135
|
// Handle GET requests for server-to-client notifications via SSE
|
|
136
|
-
router.get('/',
|
|
136
|
+
router.get('/', (req, res) => {
|
|
137
|
+
if (req.accepts('html')) {
|
|
138
|
+
const proto = req.headers['x-forwarded-proto'] || req.protocol;
|
|
139
|
+
const host = req.headers['x-forwarded-host'] || req.get('host');
|
|
140
|
+
const path = req.headers['x-original-request-uri'] ||
|
|
141
|
+
req.headers['x-original-uri'] ||
|
|
142
|
+
req.originalUrl;
|
|
143
|
+
const fullUrl = `${proto}://${host}${path}`;
|
|
144
|
+
res.send(`<!DOCTYPE html>
|
|
145
|
+
<html>
|
|
146
|
+
<head>
|
|
147
|
+
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/water.css@2/out/water.css">
|
|
148
|
+
</head>
|
|
149
|
+
<body>
|
|
150
|
+
<h1>${name}</h1>
|
|
151
|
+
<h2>Model Context Protocol (MCP) Server</h2>
|
|
152
|
+
<p>This endpoint is used for MCP communication. Please use an MCP-compatible client to interact with this server.</p>
|
|
153
|
+
|
|
154
|
+
<h3>Claude Code</h3>
|
|
155
|
+
<p>To connect to this MCP server using Claude Code, run the following command in your terminal:</p>
|
|
156
|
+
<pre><code>claude mcp add --transport http ${name || req.get('host')} ${fullUrl}</code></pre>
|
|
157
|
+
</body>
|
|
158
|
+
</html>`);
|
|
159
|
+
return;
|
|
160
|
+
}
|
|
161
|
+
handleSessionRequest(req, res);
|
|
162
|
+
});
|
|
137
163
|
// Handle DELETE requests for session termination
|
|
138
164
|
router.delete('/', handleSessionRequest);
|
|
139
165
|
const cleanup = async () => {
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import express from 'express';
|
|
3
|
+
import { ApiFactory, PromptFactory } from './types.js';
|
|
4
|
+
import { AdditionalSetupArgs } from './mcpServer.js';
|
|
5
|
+
import { Server } from 'node:http';
|
|
6
|
+
export declare const httpServerFactory: <Context extends Record<string, unknown>>({ name, version, context, apiFactories, promptFactories, additionalSetup, cleanupFn, stateful, }: {
|
|
7
|
+
name: string;
|
|
8
|
+
version?: string;
|
|
9
|
+
context: Context;
|
|
10
|
+
apiFactories?: readonly ApiFactory<Context, any, any>[];
|
|
11
|
+
promptFactories?: readonly PromptFactory<Context, any>[];
|
|
12
|
+
additionalSetup?: (args: AdditionalSetupArgs<Context>) => void;
|
|
13
|
+
cleanupFn?: () => void | Promise<void>;
|
|
14
|
+
stateful?: boolean;
|
|
15
|
+
}) => {
|
|
16
|
+
app: express.Express;
|
|
17
|
+
server: Server;
|
|
18
|
+
apiRouter: express.Router;
|
|
19
|
+
mcpRouter: express.Router;
|
|
20
|
+
registerCleanupFn: (fn: () => Promise<void>) => void;
|
|
21
|
+
};
|
package/dist/httpServer.js
CHANGED
|
@@ -13,6 +13,7 @@ export const httpServerFactory = ({ name, version, context, apiFactories = [], p
|
|
|
13
13
|
const exitHandler = registerExitHandlers(cleanupFns);
|
|
14
14
|
log.info('Starting HTTP server...');
|
|
15
15
|
const app = express();
|
|
16
|
+
app.enable('trust proxy');
|
|
16
17
|
const [mcpRouter, mcpCleanup] = mcpRouterFactory(context, () => mcpServerFactory({
|
|
17
18
|
name,
|
|
18
19
|
version,
|
|
@@ -20,7 +21,7 @@ export const httpServerFactory = ({ name, version, context, apiFactories = [], p
|
|
|
20
21
|
apiFactories,
|
|
21
22
|
promptFactories,
|
|
22
23
|
additionalSetup,
|
|
23
|
-
}), stateful);
|
|
24
|
+
}), { name, stateful });
|
|
24
25
|
cleanupFns.push(mcpCleanup);
|
|
25
26
|
app.use('/mcp', mcpRouter);
|
|
26
27
|
const [apiRouter, apiCleanup] = apiRouterFactory(context, apiFactories);
|
package/dist/logger.d.ts
ADDED
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { LogAttributes } from '@opentelemetry/api-logs';
|
|
2
|
+
interface LogInterface {
|
|
3
|
+
debug: (body: string, attributes?: LogAttributes) => void;
|
|
4
|
+
info: (body: string, attributes?: LogAttributes) => void;
|
|
5
|
+
warn: (body: string, attributes?: LogAttributes) => void;
|
|
6
|
+
error: (body: string, error?: Error | null, attributes?: LogAttributes) => void;
|
|
7
|
+
}
|
|
8
|
+
export declare const log: LogInterface;
|
|
9
|
+
export {};
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
|
|
2
|
+
import { ApiFactory, PromptFactory } from './types.js';
|
|
3
|
+
export interface AdditionalSetupArgs<Context extends Record<string, unknown>> {
|
|
4
|
+
context: Context;
|
|
5
|
+
server: McpServer;
|
|
6
|
+
}
|
|
7
|
+
export declare const mcpServerFactory: <Context extends Record<string, unknown>>({ name, version, context, apiFactories, promptFactories, additionalSetup, }: {
|
|
8
|
+
name: string;
|
|
9
|
+
version?: string;
|
|
10
|
+
context: Context;
|
|
11
|
+
apiFactories: readonly ApiFactory<Context, any, any>[];
|
|
12
|
+
promptFactories?: readonly PromptFactory<Context, any>[];
|
|
13
|
+
additionalSetup?: (args: AdditionalSetupArgs<Context>) => void;
|
|
14
|
+
}) => {
|
|
15
|
+
server: McpServer;
|
|
16
|
+
};
|
package/dist/mcpServer.js
CHANGED
|
@@ -21,6 +21,8 @@ export const mcpServerFactory = ({ name, version = '1.0.0', context, apiFactorie
|
|
|
21
21
|
});
|
|
22
22
|
for (const factory of apiFactories) {
|
|
23
23
|
const tool = factory(context);
|
|
24
|
+
if (tool.disabled)
|
|
25
|
+
continue;
|
|
24
26
|
if (enabledTools && !enabledTools.has(tool.name)) {
|
|
25
27
|
continue;
|
|
26
28
|
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare const registerExitHandlers: (cleanupFns: (() => void | Promise<void>)[]) => ((code?: number) => void);
|
package/dist/stdio.d.ts
ADDED
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import { ApiFactory, PromptFactory } from './types.js';
|
|
3
|
+
import { AdditionalSetupArgs } from './mcpServer.js';
|
|
4
|
+
export declare const stdioServerFactory: <Context extends Record<string, unknown>>({ name, version, context, apiFactories, promptFactories, additionalSetup, cleanupFn, }: {
|
|
5
|
+
name: string;
|
|
6
|
+
version?: string;
|
|
7
|
+
context: Context;
|
|
8
|
+
apiFactories: readonly ApiFactory<Context, any, any>[];
|
|
9
|
+
promptFactories?: readonly PromptFactory<Context, any>[];
|
|
10
|
+
additionalSetup?: (args: AdditionalSetupArgs<Context>) => void;
|
|
11
|
+
cleanupFn?: () => Promise<void>;
|
|
12
|
+
}) => Promise<void>;
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import type { Span, Tracer } from '@opentelemetry/api';
|
|
2
|
+
import type { GenerateTextResult, ModelMessage } from 'ai';
|
|
3
|
+
export declare const withSpan: <T>(tracer: Tracer, name: string, fn: (span: Span) => Promise<T>) => Promise<T>;
|
|
4
|
+
export declare const addAiResultToSpan: (span: Span, aiResult: GenerateTextResult<any, unknown>, inputMessages: ModelMessage[]) => void;
|
package/dist/types.d.ts
ADDED
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
import type { ZodRawShape, ZodTypeAny } from 'zod';
|
|
3
|
+
import type { ToolAnnotations, GetPromptResult } from '@modelcontextprotocol/sdk/types.js';
|
|
4
|
+
import { Router } from 'express';
|
|
5
|
+
export type ToolConfig<InputArgs extends ZodRawShape, OutputArgs extends ZodRawShape> = {
|
|
6
|
+
title?: string;
|
|
7
|
+
description?: string;
|
|
8
|
+
inputSchema: InputArgs;
|
|
9
|
+
outputSchema: OutputArgs;
|
|
10
|
+
annotations?: ToolAnnotations;
|
|
11
|
+
};
|
|
12
|
+
export interface ApiDefinition<InputArgs extends ZodRawShape, OutputArgs extends ZodRawShape, SimplifiedOutputArgs = OutputArgs> {
|
|
13
|
+
name: string;
|
|
14
|
+
method?: 'get' | 'post' | 'put' | 'delete';
|
|
15
|
+
route?: string | string[];
|
|
16
|
+
config: ToolConfig<InputArgs, OutputArgs>;
|
|
17
|
+
disabled?: boolean;
|
|
18
|
+
fn: (args: z.objectOutputType<InputArgs, ZodTypeAny>) => Promise<z.objectOutputType<OutputArgs, ZodTypeAny>>;
|
|
19
|
+
pickResult?: (result: z.objectOutputType<OutputArgs, ZodTypeAny>) => SimplifiedOutputArgs;
|
|
20
|
+
}
|
|
21
|
+
export type ApiFactory<Context extends Record<string, unknown>, Input extends ZodRawShape, Output extends ZodRawShape, RestOutput = Output> = (ctx: Context) => ApiDefinition<Input, Output, RestOutput>;
|
|
22
|
+
export type RouterFactoryResult = [Router, () => void | Promise<void>];
|
|
23
|
+
export type PromptConfig<InputArgs extends ZodRawShape> = {
|
|
24
|
+
title?: string;
|
|
25
|
+
description?: string;
|
|
26
|
+
inputSchema: InputArgs;
|
|
27
|
+
};
|
|
28
|
+
export interface PromptDefinition<InputArgs extends ZodRawShape> {
|
|
29
|
+
name: string;
|
|
30
|
+
config: PromptConfig<InputArgs>;
|
|
31
|
+
fn: (args: z.objectOutputType<InputArgs, ZodTypeAny>) => Promise<GetPromptResult>;
|
|
32
|
+
}
|
|
33
|
+
export type PromptFactory<Context extends Record<string, unknown>, Input extends ZodRawShape> = (ctx: Context) => PromptDefinition<Input>;
|