somamcp 1.4.1 → 1.5.1
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/README.md +35 -2
- package/dist/backend/index.d.ts +2 -2
- package/dist/backend/index.js +1 -1
- package/dist/backend-D0qSyfXw.js +1 -0
- package/dist/edge.d.ts +57 -38
- package/dist/{index-CSy9en2A.d.ts → index-C2wa9nmp.d.ts} +45 -1
- package/dist/index.d.ts +43 -43
- package/dist/index.js +1 -1
- package/dist/listen-ZkXBwyaw.js +1 -0
- package/package.json +14 -11
- package/dist/backend-Dd0n_9Ai.js +0 -1
package/README.md
CHANGED
|
@@ -400,6 +400,39 @@ The ⚠️ rows are limits of `EdgeFastMCP`, which exposes no removal API, has n
|
|
|
400
400
|
|
|
401
401
|
Bun deliberately reports `"node"`: it is a Node-family server runtime with full Node APIs, so that is the accurate answer even though `somamcp/edge` runs there.
|
|
402
402
|
|
|
403
|
+
## MCP SDK 2.x Backend (opt-in)
|
|
404
|
+
|
|
405
|
+
`createSdkBackend` builds on the official MCP TypeScript SDK 2.x (`@modelcontextprotocol/server`). One endpoint serves both protocol revisions:
|
|
406
|
+
|
|
407
|
+
- **`2026-07-28`**, which current Claude clients request first. The default FastMCP 4.x backend answers that request with HTTP 400, and a client that doesn't retry with the older handshake ends up with no tools.
|
|
408
|
+
- **2025-era clients**, which open with `initialize`.
|
|
409
|
+
|
|
410
|
+
Pass it as `backend`. Nothing else changes:
|
|
411
|
+
|
|
412
|
+
```typescript
|
|
413
|
+
import { createServer } from "somamcp"
|
|
414
|
+
import { createSdkBackend } from "somamcp/backend"
|
|
415
|
+
|
|
416
|
+
const server = createServer({ name: "my-server", version: "1.0.0", backend: createSdkBackend })
|
|
417
|
+
|
|
418
|
+
await server.start({ transportType: "httpStream", httpStream: { port: 3000 } })
|
|
419
|
+
// or: await server.start({ transportType: "stdio" })
|
|
420
|
+
```
|
|
421
|
+
|
|
422
|
+
How it differs from the FastMCP backend:
|
|
423
|
+
|
|
424
|
+
- **Stateless only.** Every request gets a fresh SDK server built from somamcp's registry. There are no sessions, `connect`/`disconnect` events never fire, and a 2025 client's `GET` or `DELETE` is answered `405`. `httpStream.stateless: false` and `eventStore` are ignored, with a warning through `logger`.
|
|
425
|
+
- **`authenticate` receives a web `Request`**, not Node's `http.IncomingMessage`. Read headers with `getRequestHeader` and the same function works on both backends. Rejecting with a `Response` serves that response as-is. Any other rejection, a synchronous throw, or a nullish result (as on FastMCP) is a `401`. `canAccess` is only ever called with a real session: with none, gated tools are hidden when `authenticate` is configured and shown otherwise, as on FastMCP.
|
|
426
|
+
- **Errors follow SDK 2.x and the current spec.** Calling an unknown tool, or one hidden by `canAccess`, is a JSON-RPC `InvalidParams` error, as on FastMCP. Invalid arguments are an `isError` tool result, so the model can read the message and retry. FastMCP reports them as an `InvalidParams` protocol error.
|
|
427
|
+
- **Schemas must describe themselves as JSON Schema** (`~standard.jsonSchema`): zod 4, ArkType, or Valibot via `@valibot/to-json-schema`. Other schemas still validate, but clients see an empty argument list; `addTool` warns through `logger`.
|
|
428
|
+
- **`context.client.version`** is filled in for `2026-07-28` clients, which send their client info on every request. It is `undefined` for 2025 clients, which send it only during `initialize`.
|
|
429
|
+
- **`httpStream.host` defaults to `localhost`**, as on FastMCP. Pass `host: "0.0.0.0"` to listen on every interface.
|
|
430
|
+
- **`streamKeepalive`** maps to the SDK's SSE comment frames (`enabled` and `intervalMs`; the default is 20 s, as on FastMCP). FastMCP sends log notifications instead. With it on, every tool call is answered as an SSE stream, so a long call that produces no output still gets keepalives. `enableJsonResponse` turns them off; it applies to `2026-07-28` exchanges only, so a 2025 client's responses are unchanged by it.
|
|
431
|
+
- **`context.log` follows the client's log level.** A `2026-07-28` client receives tool logs only when its request asks for a log level (`io.modelcontextprotocol/logLevel`); otherwise the SDK drops them. 2025 clients receive them as before. Progress (`reportProgress`) is unaffected.
|
|
432
|
+
- **Health reports `running` from construction**, because the backend can answer `fetch()` before `start()`. FastMCP reports `stopped` until `start()`. Both report `stopped` after `stop()`.
|
|
433
|
+
- **Removal is real:** `removeTool`, `removeResource` and `removePrompt` apply from the next request.
|
|
434
|
+
- **`backendOptions`** takes `mcpPath` (the endpoint for `fetch()` use; `httpStream.endpoint` overrides it) and `stdioTransport` (a transport to use in place of the process's stdin/stdout). FastMCP's `ping`, `health`, `roots` and `oauth` options don't apply.
|
|
435
|
+
|
|
403
436
|
## Backend Abstraction
|
|
404
437
|
|
|
405
438
|
The underlying MCP framework is accessed exclusively through the `BackendAdapter` interface. `createServer` accepts a `backend` factory — this is how `somamcp/edge` swaps in the edge adapter:
|
|
@@ -501,8 +534,8 @@ createServer({
|
|
|
501
534
|
|
|
502
535
|
**Backend** (via `somamcp/backend`)
|
|
503
536
|
|
|
504
|
-
- `createFastMCPBackend`
|
|
505
|
-
- Types: `BackendAdapter`, `BackendFactory`, `BackendSession`
|
|
537
|
+
- `createFastMCPBackend`, `createSdkBackend`
|
|
538
|
+
- Types: `BackendAdapter`, `BackendFactory`, `BackendSession`, `SdkBackendOptions`
|
|
506
539
|
|
|
507
540
|
## Scripts
|
|
508
541
|
|
package/dist/backend/index.d.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { a as
|
|
2
|
-
export { type BackendAdapter, type BackendEvents, type BackendFactory, type BackendSession, createFastMCPBackend };
|
|
1
|
+
import { a as BackendEvents, i as BackendAdapter, n as createSdkBackend, o as BackendFactory, r as createFastMCPBackend, s as BackendSession, t as SdkBackendOptions } from "../index-C2wa9nmp.js";
|
|
2
|
+
export { type BackendAdapter, type BackendEvents, type BackendFactory, type BackendSession, type SdkBackendOptions, createFastMCPBackend, createSdkBackend };
|
package/dist/backend/index.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
export{n as createFastMCPBackend,t as createSdkBackend}from"../backend-D0qSyfXw.js";
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import{FastMCP as e,ServerState as t}from"fastmcp";import{ProtocolError as n,ProtocolErrorCode as r,ResourceNotFoundError as i,Server as a,UriTemplate as o,createMcpHandler as s}from"@modelcontextprotocol/server";import{List as c,Map as l,Option as u,Ref as d,Try as f,Tuple as p}from"functype";import{Hono as m}from"hono";import{cors as h}from"hono/cors";const g=e=>{switch(e){case t.Running:return`running`;case t.Error:return`error`;default:return`stopped`}},_=(t,n)=>{let r={...n,authenticate:t.authenticate,instructions:t.instructions,logger:t.logger,name:t.name,...t.streamKeepalive?{streamKeepalive:t.streamKeepalive}:{},version:t.version},i=new e(r);return{get serverState(){return g(i.serverState)},get sessions(){return i.sessions.map(e=>({sessionId:e.sessionId}))},addPrompt:e=>{i.addPrompt(e)},addResource:e=>{i.addResource(e)},addResourceTemplate:(...e)=>{i.addResourceTemplate(...e)},addTool:e=>{i.addTool(e)},fetch:async e=>i.getApp().fetch(e),getApp:()=>i.getApp(),on:(e,t)=>{i.on(e,t)},removePrompt:e=>i.removePrompt(e),removeResource:e=>i.removeResource(e),removeTool:e=>i.removeTool(e),start:async e=>{e?e.transportType===`httpStream`?await i.start({httpStream:e.httpStream,transportType:`httpStream`}):await i.start({transportType:`stdio`}):await i.start()},stop:()=>i.stop()}},v={properties:{},type:`object`},y=e=>u(e[`~standard`].jsonSchema).isSome(),b=e=>e.flatMap(e=>u(e[`~standard`].jsonSchema)).map(e=>e.input({target:`draft-2020-12`})).orElse(v),x=e=>typeof e==`string`?{content:[{text:e,type:`text`}]}:e===void 0?{content:[]}:`content`in e?e:{content:[e]},S=e=>({content:[{text:e,type:`text`}],isError:!0}),C=(e,t)=>({contents:(Array.isArray(e)?e:[e]).map(e=>({mimeType:e.mimeType??t.mimeType,uri:e.uri??t.uri,...`blob`in e?{blob:e.blob}:{text:e.text}}))}),w=e=>typeof e==`string`?{messages:[{content:{text:e,type:`text`},role:`user`}]}:e,T={values:[]},E=e=>({completion:e.orElse(T)}),D=(e,t)=>{let n=e.filter(e=>e.startsWith(t));return{total:n.length,values:n}},O=(e,t,n)=>{let r=t=>e.mcpReq.notify(t).catch(()=>{}),i=t=>(n,r)=>{e.mcpReq.log(t,r===void 0?n:{data:r,message:n}).catch(()=>{})},a=u(e.mcpReq._meta?.progressToken);return{client:{version:u(e.mcpReq.envelope?.[`io.modelcontextprotocol/clientInfo`]).map(e=>e.version).orUndefined()},log:{debug:i(`debug`),error:i(`error`),info:i(`info`),warn:i(`warning`)},reportProgress:async({progress:e,total:t})=>{await a.fold(async()=>{},n=>r({method:`notifications/progress`,params:{progress:e,progressToken:n,total:t}}))},requestId:String(e.mcpReq.id),session:t.orUndefined(),sessionId:e.sessionId,streamContent:async e=>{await r({method:`notifications/tool/streamContent`,params:{content:Array.isArray(e)?e:[e],toolName:n}})}}},k=e=>c([...e].map(([,e])=>e)),A=(...e)=>e.reduce((e,t)=>e.fold(()=>t(),()=>e),u.none()),j=e=>e instanceof Error?e.message:String(e),M=e=>`Tool '${e.name}' timed out after ${e.timeoutMs}ms. Consider increasing timeoutMs or optimizing the tool implementation.`,N=(e,t)=>u(e.timeoutMs).fold(()=>t,n=>{let r=d(u.none()),i=new Promise((t,i)=>{r.set(u(setTimeout(()=>i(Error(M(e))),n)))});return Promise.race([t,i]).finally(()=>r.get().forEach(clearTimeout))}),P=(e,t)=>u(e.parameters).fold(()=>Promise.resolve({value:t}),e=>Promise.resolve(e[`~standard`].validate(t))),F=e=>Object.fromEntries(Object.entries(e).map(([e,t])=>[e,Array.isArray(t)?t.join(`,`):t])),I=(e,t,s)=>{let l=s.orUndefined(),d=e=>s.fold(()=>!(t.authRequired&&e.canAccess),t=>!e.canAccess||e.canAccess(t)),p=t=>e.tools().get(t).filter(d),m=new a({name:t.name,version:t.version},{capabilities:{completions:{},logging:{},prompts:{},resources:{},tools:{}},instructions:t.instructions});m.setRequestHandler(`tools/list`,()=>({tools:k(e.tools()).filter(d).map(e=>({...e._meta?{_meta:e._meta}:{},...e.annotations?{annotations:e.annotations}:{},description:e.description,inputSchema:b(u(e.parameters)),name:e.name,...e.outputSchema?{outputSchema:b(u(e.outputSchema))}:{},...e.annotations?.title?{title:e.annotations.title}:{}})).toArray()}));let h=async(e,t,n)=>{let r=await P(e,t);return`issues`in r?S(`Invalid arguments for tool '${e.name}': ${r.issues.map(e=>e.message).join(`; `)}`):(await f.fromPromise(N(e,e.execute(r.value,n)))).fold(e=>S(j(e)),e=>x(e))},g=e=>p(e).orThrow(()=>new n(r.InvalidParams,`Unknown tool: ${e}`));m.setRequestHandler(`tools/call`,(e,t)=>{let{arguments:n,name:r}=e.params;return h(g(r),n??{},O(t,s,r))}),m.setRequestHandler(`resources/list`,()=>({resources:k(e.resources()).map(e=>({description:e.description,mimeType:e.mimeType,name:e.name,uri:e.uri})).toArray()})),m.setRequestHandler(`resources/templates/list`,()=>({resourceTemplates:k(e.templates()).map(e=>({description:e.description,mimeType:e.mimeType,name:e.name,uriTemplate:e.uriTemplate})).toArray()}));let _=t=>A(()=>k(e.resources()).find(e=>e.uri===t).map(e=>({load:()=>e.load(l),mimeType:e.mimeType})),()=>k(e.templates()).map(e=>({template:e,variables:u(new o(e.uriTemplate).match(t))})).find(e=>e.variables.isSome()).map(({template:e,variables:t})=>({load:()=>e.load(F(t.orElse({})),l),mimeType:e.mimeType}))),v=async e=>{let t=_(e).orThrow(()=>new i(e));return C(await t.load(),{mimeType:t.mimeType,uri:e})};m.setRequestHandler(`resources/read`,e=>v(e.params.uri)),m.setRequestHandler(`prompts/list`,()=>({prompts:k(e.prompts()).map(e=>({arguments:e.arguments?.map(e=>({description:e.description,name:e.name,required:e.required})),description:e.description,name:e.name})).toArray()}));let y=async(t,i)=>{let a=e.prompts().get(t).orThrow(()=>new n(r.InvalidParams,`Unknown prompt: ${t}`)),o=c(a.arguments??[]).filter(e=>e.required===!0&&!(e.name in i));if(!o.isEmpty){let e=o.map(e=>e.name).toArray().join(`, `);throw new n(r.InvalidParams,`Prompt '${t}' is missing required arguments: ${e}`)}return w(await a.load(i,l))};m.setRequestHandler(`prompts/get`,e=>y(e.params.name,e.params.arguments??{}));let T=(t,n,r)=>{let i=e.prompts().get(t),a=i.flatMap(e=>c(e.arguments??[]).find(e=>e.name===n));return A(()=>a.flatMap(e=>u(e.complete)).map(e=>()=>e(r,l)),()=>a.flatMap(e=>u(e.enum)).map(e=>()=>Promise.resolve(D(e,r))),()=>i.flatMap(e=>u(e.complete)).map(e=>()=>e(n,r,l)))},M=(t,n,r)=>{let i=k(e.templates()).find(e=>e.uriTemplate===t),a=i.flatMap(e=>c(e.arguments).find(e=>e.name===n));return A(()=>a.flatMap(e=>u(e.complete)).map(e=>()=>e(r,l)),()=>i.flatMap(e=>u(e.complete)).map(e=>()=>e(n,r,l)))};return m.setRequestHandler(`completion/complete`,async e=>{let{argument:t,ref:n}=e.params,r=n.type===`ref/prompt`?T(n.name,t.name,t.value):M(n.uri,t.name,t.value);return E(await r.foldAsync(()=>Promise.resolve(u.none()),async e=>u(await e())))}),m},L=`somamcp/session`,R=(e,t)=>{let n=u(e.logger),r=e=>n.forEach(t=>t.warn(`[somamcp/sdk] ${e}`)),i=d(l.empty()),a=d(l.empty()),o=d(l.empty()),c=d(l.empty()),g={prompts:()=>c.get(),resources:()=>a.get(),templates:()=>o.get(),tools:()=>i.get()},_=(e,t,n)=>{e.set(e.get().add(p([t,n])))},v=(e,t)=>{e.set(e.get().remove(t))},b={authRequired:e.authenticate!==void 0,instructions:e.instructions,name:e.name,version:e.version},x=u(e.streamKeepalive).filter(e=>e.enabled===!0).map(e=>e.intervalMs??2e4),S=x.fold(()=>`auto`,()=>`sse`),C=e=>s(({authInfo:e})=>I(g,b,u(e).flatMap(e=>u(e.extra?.[L]))),{keepAliveMs:x.orUndefined(),onerror:e=>n.forEach(t=>t.error(`[somamcp/sdk]`,e)),responseMode:e}),w=d(S),T=d(C(w.get())),E=d(u(t).flatMap(e=>u(e.mcpPath)).orElse(`/mcp`)),D=d(u.none()),O=d(u.none()),k=d(`running`),A=(e,t)=>t instanceof Response?t:e.json({error:`Unauthorized`},401),j=(e,t)=>Promise.resolve().then(()=>e(t)).then(e=>u(e).fold(()=>Promise.reject(/* @__PURE__ */ Error(`Authentication required`)),e=>Promise.resolve(e))),M=async t=>{let n=t.req.raw;return e.authenticate?j(e.authenticate,n).then(e=>T.get().fetch(n,{authInfo:{clientId:``,extra:{[L]:e},scopes:[],token:``}}),e=>A(t,e)):T.get().fetch(n)},N=new m;N.use(`*`,async(e,t)=>e.req.path===E.get()?D.get().fold(()=>M(e),async t=>await t(e,async()=>{e.res=await M(e)})??e.res):t());let P=e=>{u(e.endpoint).forEach(e=>E.set(e)),u(e.cors).filter(e=>e!==!1).forEach(e=>D.set(u(h(e===!0?{}:e)))),e.enableJsonResponse===!0&&(x.isSome()&&r(`enableJsonResponse disables streamKeepalive: JSON responses cannot carry keepalive frames.`),w.set(`json`),T.set(C(`json`))),e.stateless===!1&&r(`stateful sessions are not supported by the SDK backend; serving statelessly.`),e.eventStore!==void 0&&r(`eventStore is not supported by the SDK backend; ignoring.`)},F=async()=>{let{listenStdio:r}=await import(`./listen-ZkXBwyaw.js`),i=e.authenticate?(await f.fromPromise(j(e.authenticate,void 0))).fold(e=>(n.forEach(t=>t.error(`[somamcp/sdk] authentication failed for stdio transport:`,e.message)),u.none()),e=>u(e)):u.none();return r(()=>I(g,b,i),u(t).flatMap(e=>u(e.stdioTransport)).orUndefined())},R=async e=>{let{listenHttp:t}=await import(`./listen-ZkXBwyaw.js`);return P(e),t(N,e)};return{get serverState(){return k.get()},get sessions(){return[]},addPrompt:e=>{_(c,e.name,e)},addResource:e=>{_(a,e.name,e)},addResourceTemplate:(...e)=>{let t=e[0];_(o,t.name,t)},addTool:e=>{e.parameters&&!y(e.parameters)&&r(`tool "${e.name}": its schema has no ~standard.jsonSchema, so clients see an empty argument list. Use zod 4, ArkType, or Valibot with @valibot/to-json-schema.`),_(i,e.name,e)},fetch:async e=>N.fetch(e),getApp:()=>N,on:()=>{},removePrompt:e=>{v(c,e)},removeResource:e=>{v(a,e)},removeTool:e=>{v(i,e)},start:async e=>{if(O.get().isSome()){r(`start() called while already listening; ignoring. Call stop() first to restart.`);return}let t=await f.fromPromise(e?.transportType===`httpStream`?R(e.httpStream):F());t.isFailure()&&k.set(`error`),O.set(u(t.orThrow())),k.set(`running`)},stop:async()=>{await T.get().close(),await O.get().fold(async()=>{},e=>e.close()),O.set(u.none()),T.set(C(w.get())),k.set(`stopped`)}}};export{_ as n,R as t};
|
package/dist/edge.d.ts
CHANGED
|
@@ -156,6 +156,25 @@ type Resource<T extends SessionAuth = SessionAuth> = {
|
|
|
156
156
|
name: string;
|
|
157
157
|
uri: string;
|
|
158
158
|
};
|
|
159
|
+
type ResourceTemplateArgument<T extends SessionAuth = SessionAuth> = Readonly<{
|
|
160
|
+
complete?: (value: string, auth?: T) => Promise<Completion>;
|
|
161
|
+
description?: string;
|
|
162
|
+
name: string;
|
|
163
|
+
required?: boolean;
|
|
164
|
+
}>;
|
|
165
|
+
/**
|
|
166
|
+
* A family of resources addressed by an RFC 6570 URI template, e.g. `docs://{path}`.
|
|
167
|
+
* `load` receives the variables matched from the requested URI.
|
|
168
|
+
*/
|
|
169
|
+
type ResourceTemplate<T extends SessionAuth = SessionAuth> = {
|
|
170
|
+
arguments: ResourceTemplateArgument<T>[];
|
|
171
|
+
complete?: (name: string, value: string, auth?: T) => Promise<Completion>;
|
|
172
|
+
description?: string;
|
|
173
|
+
load: (args: Record<string, string>, auth?: T) => Promise<ResourceResult | ResourceResult[]>;
|
|
174
|
+
mimeType?: string;
|
|
175
|
+
name: string;
|
|
176
|
+
uriTemplate: string;
|
|
177
|
+
};
|
|
159
178
|
type PromptArgument<T extends SessionAuth = SessionAuth> = Readonly<{
|
|
160
179
|
complete?: (value: string, auth?: T) => Promise<Completion>;
|
|
161
180
|
description?: string;
|
|
@@ -174,7 +193,7 @@ type Prompt<T extends SessionAuth = SessionAuth, Args extends PromptArgument<T>[
|
|
|
174
193
|
name: string;
|
|
175
194
|
};
|
|
176
195
|
type ServerStatus = "error" | "running" | "stopped";
|
|
177
|
-
declare class UserError extends Error {
|
|
196
|
+
export declare class UserError extends Error {
|
|
178
197
|
constructor(message: string);
|
|
179
198
|
}
|
|
180
199
|
//#endregion
|
|
@@ -315,9 +334,9 @@ type RuntimeInfo = {
|
|
|
315
334
|
/** Which runtime family reported the fields above. Absent on pre-1.2 builds. */
|
|
316
335
|
runtime?: "edge" | "node";
|
|
317
336
|
};
|
|
318
|
-
declare const readBuildInfoFromEnv: () => BuildInfo;
|
|
319
|
-
declare const resolveBuildInfo: (override?: BuildInfo) => BuildInfo;
|
|
320
|
-
declare const getRuntimeInfo: () => RuntimeInfo;
|
|
337
|
+
export declare const readBuildInfoFromEnv: () => BuildInfo;
|
|
338
|
+
export declare const resolveBuildInfo: (override?: BuildInfo) => BuildInfo;
|
|
339
|
+
export declare const getRuntimeInfo: () => RuntimeInfo;
|
|
321
340
|
//#endregion
|
|
322
341
|
//#region src/gateway/types.d.ts
|
|
323
342
|
type GatewayConfig = {
|
|
@@ -402,7 +421,7 @@ type AuthMiddlewareConfig = {
|
|
|
402
421
|
authenticate?: Authenticate;
|
|
403
422
|
onUnauthorized?: OnUnauthorized;
|
|
404
423
|
};
|
|
405
|
-
declare const createAuthMiddleware: ({ authenticate, onUnauthorized }: AuthMiddlewareConfig) => MiddlewareHandler;
|
|
424
|
+
export declare const createAuthMiddleware: ({ authenticate, onUnauthorized }: AuthMiddlewareConfig) => MiddlewareHandler;
|
|
406
425
|
//#endregion
|
|
407
426
|
//#region src/auth/request.d.ts
|
|
408
427
|
/**
|
|
@@ -417,7 +436,7 @@ declare const createAuthMiddleware: ({ authenticate, onUnauthorized }: AuthMiddl
|
|
|
417
436
|
* absent or the request shape is not recognized — matches the `Headers.get`
|
|
418
437
|
* shape callers already write against.
|
|
419
438
|
*/
|
|
420
|
-
declare const getRequestHeader: (request: unknown, name: string) => string | undefined;
|
|
439
|
+
export declare const getRequestHeader: (request: unknown, name: string) => string | undefined;
|
|
421
440
|
//#endregion
|
|
422
441
|
//#region src/types/routes.d.ts
|
|
423
442
|
type RouteMethod = "GET" | "POST" | "PUT" | "PATCH" | "DELETE";
|
|
@@ -546,7 +565,7 @@ type SomaServerInstance<T extends SessionAuth = SessionAuth> = {
|
|
|
546
565
|
* module — including `somamcp/edge`. The entry barrels supply the default instead:
|
|
547
566
|
* `somamcp` binds createFastMCPBackend, `somamcp/edge` binds createEdgeBackend.
|
|
548
567
|
*/
|
|
549
|
-
declare const createServerCore: <T extends SessionAuth = SessionAuth>(options: SomaServerOptions<T> & {
|
|
568
|
+
export declare const createServerCore: <T extends SessionAuth = SessionAuth>(options: SomaServerOptions<T> & {
|
|
550
569
|
backend: BackendFactory<T>;
|
|
551
570
|
}) => SomaServerInstance<T>;
|
|
552
571
|
//#endregion
|
|
@@ -564,13 +583,13 @@ type EdgeBackendOptions = {
|
|
|
564
583
|
* registers its own `/health` at construction, and Hono is first-match-wins, so
|
|
565
584
|
* mounting it first would shadow somamcp's health artifact.
|
|
566
585
|
*/
|
|
567
|
-
declare const createEdgeBackend: <T extends SessionAuth = SessionAuth>(config: ServerConfig<T>, backendOptions?: Record<string, unknown>) => BackendAdapter<T>;
|
|
586
|
+
export declare const createEdgeBackend: <T extends SessionAuth = SessionAuth>(config: ServerConfig<T>, backendOptions?: Record<string, unknown>) => BackendAdapter<T>;
|
|
568
587
|
//#endregion
|
|
569
588
|
//#region src/telemetry/CompositeTelemetry.d.ts
|
|
570
|
-
declare const createCompositeTelemetry: (collectors: ReadonlyArray<TelemetryCollector>) => TelemetryCollector;
|
|
589
|
+
export declare const createCompositeTelemetry: (collectors: ReadonlyArray<TelemetryCollector>) => TelemetryCollector;
|
|
571
590
|
//#endregion
|
|
572
591
|
//#region src/telemetry/ConsoleTelemetry.d.ts
|
|
573
|
-
declare const createConsoleTelemetry: (prefix?: string) => TelemetryCollector;
|
|
592
|
+
export declare const createConsoleTelemetry: (prefix?: string) => TelemetryCollector;
|
|
574
593
|
//#endregion
|
|
575
594
|
//#region src/telemetry/EnrichedError.d.ts
|
|
576
595
|
type EnrichedErrorResponse = {
|
|
@@ -579,14 +598,14 @@ type EnrichedErrorResponse = {
|
|
|
579
598
|
relatedState?: Record<string, unknown>;
|
|
580
599
|
suggestions?: ReadonlyArray<string>;
|
|
581
600
|
};
|
|
582
|
-
declare const classifyError: (error: unknown) => ErrorCategory;
|
|
583
|
-
declare const createEnrichedError: (error: unknown, context?: {
|
|
601
|
+
export declare const classifyError: (error: unknown) => ErrorCategory;
|
|
602
|
+
export declare const createEnrichedError: (error: unknown, context?: {
|
|
584
603
|
gatewayStatus?: string;
|
|
585
604
|
toolName?: string;
|
|
586
605
|
}) => EnrichedErrorResponse;
|
|
587
606
|
//#endregion
|
|
588
607
|
//#region src/telemetry/NoopTelemetry.d.ts
|
|
589
|
-
declare const NoopTelemetry: TelemetryCollector;
|
|
608
|
+
export declare const NoopTelemetry: TelemetryCollector;
|
|
590
609
|
//#endregion
|
|
591
610
|
//#region src/telemetry/telemetryWrapper.d.ts
|
|
592
611
|
/**
|
|
@@ -602,37 +621,37 @@ declare const NoopTelemetry: TelemetryCollector;
|
|
|
602
621
|
* The failure path converts an error to a `ContentResult` with `isError: true`
|
|
603
622
|
* and the enriched error payload as the text content.
|
|
604
623
|
*/
|
|
605
|
-
declare const wrapTool: <T extends SessionAuth, P extends SchemaParams>(tool: Tool<T, P>, telemetry: TelemetryCollector, captureConfig?: ToolCaptureConfig) => Tool<T, P>;
|
|
606
|
-
declare const wrapResource: <T extends SessionAuth>(resource: Resource<T>, telemetry: TelemetryCollector) => Resource<T>;
|
|
607
|
-
declare const wrapPrompt: <T extends SessionAuth, Args extends PromptArgument<T>[] = PromptArgument<T>[]>(prompt: Prompt<T, Args>, telemetry: TelemetryCollector) => Prompt<T, Args>;
|
|
624
|
+
export declare const wrapTool: <T extends SessionAuth, P extends SchemaParams>(tool: Tool<T, P>, telemetry: TelemetryCollector, captureConfig?: ToolCaptureConfig) => Tool<T, P>;
|
|
625
|
+
export declare const wrapResource: <T extends SessionAuth>(resource: Resource<T>, telemetry: TelemetryCollector) => Resource<T>;
|
|
626
|
+
export declare const wrapPrompt: <T extends SessionAuth, Args extends PromptArgument<T>[] = PromptArgument<T>[]>(prompt: Prompt<T, Args>, telemetry: TelemetryCollector) => Prompt<T, Args>;
|
|
608
627
|
//#endregion
|
|
609
628
|
//#region src/artifacts/ArtifactManager.d.ts
|
|
610
|
-
declare const registerArtifacts: (app: Hono, artifacts: ReadonlyArray<ArtifactConfig>, authenticate?: ArtifactAuthenticate) => void;
|
|
629
|
+
export declare const registerArtifacts: (app: Hono, artifacts: ReadonlyArray<ArtifactConfig>, authenticate?: ArtifactAuthenticate) => void;
|
|
611
630
|
//#endregion
|
|
612
631
|
//#region src/artifacts/DashboardArtifact.d.ts
|
|
613
|
-
declare const createDashboardArtifact: (getHealth: () => ServerHealth, getCapabilities: () => ServerCapabilities, getConnections: () => ReadonlyArray<GatewayInfo>) => ArtifactConfig;
|
|
632
|
+
export declare const createDashboardArtifact: (getHealth: () => ServerHealth, getCapabilities: () => ServerCapabilities, getConnections: () => ReadonlyArray<GatewayInfo>) => ArtifactConfig;
|
|
614
633
|
//#endregion
|
|
615
634
|
//#region src/artifacts/HealthArtifact.d.ts
|
|
616
|
-
declare const DEFAULT_HEALTH_PATH = "/health";
|
|
617
|
-
declare const DEFAULT_HEALTH_DETAIL_PATH = "/health/detail";
|
|
618
|
-
declare const createHealthArtifact: (getHealth: () => ServerHealth, path?: string) => ArtifactConfig;
|
|
619
|
-
declare const createHealthDetailArtifact: (getHealth: () => ServerHealth, path?: string) => ArtifactConfig;
|
|
635
|
+
export declare const DEFAULT_HEALTH_PATH = "/health";
|
|
636
|
+
export declare const DEFAULT_HEALTH_DETAIL_PATH = "/health/detail";
|
|
637
|
+
export declare const createHealthArtifact: (getHealth: () => ServerHealth, path?: string) => ArtifactConfig;
|
|
638
|
+
export declare const createHealthDetailArtifact: (getHealth: () => ServerHealth, path?: string) => ArtifactConfig;
|
|
620
639
|
//#endregion
|
|
621
640
|
//#region src/artifacts/InfoArtifact.d.ts
|
|
622
|
-
declare const DEFAULT_INFO_PATH = "/info";
|
|
623
|
-
declare const createInfoArtifact: (getInfo: () => ServerInfo, path?: string) => ArtifactConfig;
|
|
641
|
+
export declare const DEFAULT_INFO_PATH = "/info";
|
|
642
|
+
export declare const createInfoArtifact: (getInfo: () => ServerInfo, path?: string) => ArtifactConfig;
|
|
624
643
|
//#endregion
|
|
625
644
|
//#region src/introspection/capabilitiesTool.d.ts
|
|
626
|
-
declare const createCapabilitiesTool: <T extends SessionAuth>(getCapabilities: () => ServerCapabilities) => Tool<T>;
|
|
645
|
+
export declare const createCapabilitiesTool: <T extends SessionAuth>(getCapabilities: () => ServerCapabilities) => Tool<T>;
|
|
627
646
|
//#endregion
|
|
628
647
|
//#region src/introspection/connectionsTool.d.ts
|
|
629
|
-
declare const createConnectionsTool: <T extends SessionAuth>(getConnections: () => ReadonlyArray<GatewayInfo>) => Tool<T>;
|
|
648
|
+
export declare const createConnectionsTool: <T extends SessionAuth>(getConnections: () => ReadonlyArray<GatewayInfo>) => Tool<T>;
|
|
630
649
|
//#endregion
|
|
631
650
|
//#region src/introspection/healthTool.d.ts
|
|
632
|
-
declare const createHealthTool: <T extends SessionAuth>(getHealth: () => ServerHealth) => Tool<T>;
|
|
651
|
+
export declare const createHealthTool: <T extends SessionAuth>(getHealth: () => ServerHealth) => Tool<T>;
|
|
633
652
|
//#endregion
|
|
634
653
|
//#region src/introspection/infoTool.d.ts
|
|
635
|
-
declare const createInfoTool: <T extends SessionAuth>(getInfo: () => ServerInfo, name?: string) => Tool<T>;
|
|
654
|
+
export declare const createInfoTool: <T extends SessionAuth>(getInfo: () => ServerInfo, name?: string) => Tool<T>;
|
|
636
655
|
//#endregion
|
|
637
656
|
//#region src/feedback/redaction.d.ts
|
|
638
657
|
type RedactionPattern = {
|
|
@@ -649,8 +668,8 @@ type RedactionResult = {
|
|
|
649
668
|
redacted: boolean;
|
|
650
669
|
text: string;
|
|
651
670
|
};
|
|
652
|
-
declare const DEFAULT_REDACTION_PATTERNS: ReadonlyArray<RedactionPattern>;
|
|
653
|
-
declare const redact: (input: string, patterns?: ReadonlyArray<RedactionPattern>) => RedactionResult;
|
|
671
|
+
export declare const DEFAULT_REDACTION_PATTERNS: ReadonlyArray<RedactionPattern>;
|
|
672
|
+
export declare const redact: (input: string, patterns?: ReadonlyArray<RedactionPattern>) => RedactionResult;
|
|
654
673
|
//#endregion
|
|
655
674
|
//#region src/feedback/types.d.ts
|
|
656
675
|
type FeedbackType = "bug" | "feature" | "feedback" | "question";
|
|
@@ -703,7 +722,7 @@ declare const PARAMETERS: z.ZodObject<{
|
|
|
703
722
|
question: "question";
|
|
704
723
|
}>>;
|
|
705
724
|
}, z.core.$strip>;
|
|
706
|
-
declare const createFeedbackTool: <T extends SessionAuth>(options: FeedbackToolOptions) => Tool<T, typeof PARAMETERS>;
|
|
725
|
+
export declare const createFeedbackTool: <T extends SessionAuth>(options: FeedbackToolOptions) => Tool<T, typeof PARAMETERS>;
|
|
707
726
|
//#endregion
|
|
708
727
|
//#region src/feedback/providers/github.d.ts
|
|
709
728
|
type GithubFeedbackOptions = {
|
|
@@ -713,7 +732,7 @@ type GithubFeedbackOptions = {
|
|
|
713
732
|
getToken: () => Option<string>;
|
|
714
733
|
repo: `${string}/${string}`;
|
|
715
734
|
};
|
|
716
|
-
declare const createGithubFeedback: (options: GithubFeedbackOptions) => FeedbackProvider;
|
|
735
|
+
export declare const createGithubFeedback: (options: GithubFeedbackOptions) => FeedbackProvider;
|
|
717
736
|
//#endregion
|
|
718
737
|
//#region src/feedback/providers/webhook.d.ts
|
|
719
738
|
type WebhookFeedbackOptions = {
|
|
@@ -722,16 +741,16 @@ type WebhookFeedbackOptions = {
|
|
|
722
741
|
transform?: (payload: NormalizedFeedback) => unknown;
|
|
723
742
|
url: string;
|
|
724
743
|
};
|
|
725
|
-
declare const createWebhookFeedback: (options: WebhookFeedbackOptions) => FeedbackProvider;
|
|
744
|
+
export declare const createWebhookFeedback: (options: WebhookFeedbackOptions) => FeedbackProvider;
|
|
726
745
|
//#endregion
|
|
727
746
|
//#region src/gateway/Gateway.d.ts
|
|
728
|
-
declare const createGateway: (config: GatewayConfig, telemetry: TelemetryCollector) => GatewayInstance;
|
|
747
|
+
export declare const createGateway: (config: GatewayConfig, telemetry: TelemetryCollector) => GatewayInstance;
|
|
729
748
|
//#endregion
|
|
730
749
|
//#region src/gateway/GatewayManager.d.ts
|
|
731
|
-
declare const createGatewayManager: (telemetry: TelemetryCollector) => GatewayManagerInstance;
|
|
750
|
+
export declare const createGatewayManager: (telemetry: TelemetryCollector) => GatewayManagerInstance;
|
|
732
751
|
//#endregion
|
|
733
752
|
//#region src/gateway/toolProxy.d.ts
|
|
734
|
-
declare const createProxiedTools: <T extends SessionAuth>(gateway: GatewayInstance, telemetry?: TelemetryCollector) => ReadonlyArray<Tool<T>>;
|
|
753
|
+
export declare const createProxiedTools: <T extends SessionAuth>(gateway: GatewayInstance, telemetry?: TelemetryCollector) => ReadonlyArray<Tool<T>>;
|
|
735
754
|
//#endregion
|
|
736
755
|
//#region src/edge.d.ts
|
|
737
756
|
/**
|
|
@@ -743,6 +762,6 @@ declare const createProxiedTools: <T extends SessionAuth>(gateway: GatewayInstan
|
|
|
743
762
|
* export default { fetch: (req: Request) => server.fetch(req) }
|
|
744
763
|
* ```
|
|
745
764
|
*/
|
|
746
|
-
declare const createServer: <T extends SessionAuth = SessionAuth>(options: SomaServerOptions<T>) => SomaServerInstance<T>;
|
|
765
|
+
export declare const createServer: <T extends SessionAuth = SessionAuth>(options: SomaServerOptions<T>) => SomaServerInstance<T>;
|
|
747
766
|
//#endregion
|
|
748
|
-
export {
|
|
767
|
+
export type { ArtifactAuthenticate, ArtifactConfig, AudioContent, AuthMiddlewareConfig, Authenticate, BackendAdapter, BackendFactory, BackendSession, BuildInfo, CapabilitiesSummary, CaptureLevel, Completion, Content, ContentResult, Context, DirectoryArtifact, DynamicArtifact, EdgeBackendOptions, EnrichedErrorResponse, ErrorCategory, FeedbackEnrichmentContext, FeedbackProvider, FeedbackSeverity, FeedbackSubmitFailure, FeedbackSubmitResult, FeedbackSubmitSuccess, FeedbackToolOptions, FeedbackType, GatewayConfig, GatewayInfo, GatewayInstance, GatewayManagerInstance, GatewayStatus, GithubFeedbackOptions, HttpStreamConfig, ImageContent, InferSchemaOutput, Logger, NormalizedFeedback, OnUnauthorized, Progress, Prompt, PromptArgument, PromptResult, RedactionPattern, RedactionResult, Resource, ResourceContent, ResourceLink, ResourceResult, ResourceTemplate, ResourceTemplateArgument, RouteConfig, RouteMethod, RuntimeInfo, SchemaParams, ServerCapabilities, ServerConfig, ServerHealth, ServerInfo, ServerStatus, SessionAuth, SomaServerInstance, SomaServerOptions, StaticArtifact, TelemetryCollector, TelemetryEvent, TelemetryEventType, TextContent, Tool, ToolAnnotations, ToolCaptureConfig, ToolOptions, TransportConfig, WebhookFeedbackOptions };
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { Transport } from "@modelcontextprotocol/server";
|
|
1
2
|
import { Hono } from "hono";
|
|
2
3
|
//#region src/types/core.d.ts
|
|
3
4
|
type SessionAuth = Record<string, unknown> | undefined;
|
|
@@ -129,6 +130,25 @@ type Resource<T extends SessionAuth = SessionAuth> = {
|
|
|
129
130
|
name: string;
|
|
130
131
|
uri: string;
|
|
131
132
|
};
|
|
133
|
+
type ResourceTemplateArgument<T extends SessionAuth = SessionAuth> = Readonly<{
|
|
134
|
+
complete?: (value: string, auth?: T) => Promise<Completion>;
|
|
135
|
+
description?: string;
|
|
136
|
+
name: string;
|
|
137
|
+
required?: boolean;
|
|
138
|
+
}>;
|
|
139
|
+
/**
|
|
140
|
+
* A family of resources addressed by an RFC 6570 URI template, e.g. `docs://{path}`.
|
|
141
|
+
* `load` receives the variables matched from the requested URI.
|
|
142
|
+
*/
|
|
143
|
+
type ResourceTemplate<T extends SessionAuth = SessionAuth> = {
|
|
144
|
+
arguments: ResourceTemplateArgument<T>[];
|
|
145
|
+
complete?: (name: string, value: string, auth?: T) => Promise<Completion>;
|
|
146
|
+
description?: string;
|
|
147
|
+
load: (args: Record<string, string>, auth?: T) => Promise<ResourceResult | ResourceResult[]>;
|
|
148
|
+
mimeType?: string;
|
|
149
|
+
name: string;
|
|
150
|
+
uriTemplate: string;
|
|
151
|
+
};
|
|
132
152
|
type PromptArgument<T extends SessionAuth = SessionAuth> = Readonly<{
|
|
133
153
|
complete?: (value: string, auth?: T) => Promise<Completion>;
|
|
134
154
|
description?: string;
|
|
@@ -277,4 +297,28 @@ type BackendFactory<T extends SessionAuth = SessionAuth> = (config: ServerConfig
|
|
|
277
297
|
//#region src/backend/fastmcp.d.ts
|
|
278
298
|
declare const createFastMCPBackend: <T extends SessionAuth = SessionAuth>(config: ServerConfig<T>, backendOptions?: Record<string, unknown>) => BackendAdapter<T>;
|
|
279
299
|
//#endregion
|
|
280
|
-
|
|
300
|
+
//#region src/backend/sdk/index.d.ts
|
|
301
|
+
type SdkBackendOptions = {
|
|
302
|
+
/** MCP endpoint path when serving through `fetch`. `start({ httpStream: { endpoint } })` overrides it. Defaults to "/mcp". */
|
|
303
|
+
mcpPath?: string;
|
|
304
|
+
/**
|
|
305
|
+
* Transport for `start({ transportType: "stdio" })` in place of the process's
|
|
306
|
+
* stdin/stdout, e.g. a `StdioServerTransport` over a Unix socket.
|
|
307
|
+
*/
|
|
308
|
+
stdioTransport?: Transport;
|
|
309
|
+
};
|
|
310
|
+
/**
|
|
311
|
+
* Backend built on the official MCP TypeScript SDK 2.x (`@modelcontextprotocol/server`).
|
|
312
|
+
*
|
|
313
|
+
* One endpoint serves both protocol eras: the `2026-07-28` revision that current
|
|
314
|
+
* Claude clients request first, and 2025-era clients (`initialize`). Serving is
|
|
315
|
+
* stateless: every request gets a fresh SDK server built from somamcp's registry,
|
|
316
|
+
* so there are no sessions, `connect`/`disconnect` never fire, and a 2025 client's
|
|
317
|
+
* GET or DELETE is answered `405`.
|
|
318
|
+
*
|
|
319
|
+
* `start()` serves a port (`httpStream`) or stdio on Node; `fetch()` serves any
|
|
320
|
+
* runtime with web-standard `Request`/`Response`.
|
|
321
|
+
*/
|
|
322
|
+
declare const createSdkBackend: <T extends SessionAuth = SessionAuth>(config: ServerConfig<T>, backendOptions?: Record<string, unknown>) => BackendAdapter<T>;
|
|
323
|
+
//#endregion
|
|
324
|
+
export { ServerStatus as A, Resource as C, ResourceTemplate as D, ResourceResult as E, UserError as F, TextContent as M, Tool as N, ResourceTemplateArgument as O, ToolAnnotations as P, PromptResult as S, ResourceLink as T, ImageContent as _, BackendEvents as a, Prompt as b, HttpStreamConfig as c, TransportConfig as d, AudioContent as f, Context$1 as g, ContentResult as h, BackendAdapter as i, SessionAuth as j, SchemaParams as k, Logger as l, Content as m, createSdkBackend as n, BackendFactory as o, Completion as p, createFastMCPBackend as r, BackendSession as s, SdkBackendOptions as t, ServerConfig as u, InferSchemaOutput as v, ResourceContent as w, PromptArgument as x, Progress as y };
|
package/dist/index.d.ts
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { A as
|
|
1
|
+
import { A as ServerStatus, C as Resource, D as ResourceTemplate, E as ResourceResult, F as UserError, M as TextContent, N as Tool, O as ResourceTemplateArgument, P as ToolAnnotations, S as PromptResult, T as ResourceLink, _ as ImageContent, b as Prompt, c as HttpStreamConfig, d as TransportConfig, f as AudioContent, g as Context, h as ContentResult, i as BackendAdapter, j as SessionAuth, k as SchemaParams, l as Logger, m as Content, o as BackendFactory, p as Completion, r as createFastMCPBackend, s as BackendSession, u as ServerConfig, v as InferSchemaOutput, w as ResourceContent, x as PromptArgument, y as Progress } from "./index-C2wa9nmp.js";
|
|
2
2
|
import { Option } from "functype";
|
|
3
|
+
import { Context as Context$1, Hono, MiddlewareHandler } from "hono";
|
|
3
4
|
import { DirectLogger, DirectLogger as DirectLogger$1 } from "functype-log";
|
|
4
5
|
import { z } from "zod";
|
|
5
|
-
import { Context as Context$1, Hono, MiddlewareHandler } from "hono";
|
|
6
6
|
import { Tool as Tool$1 } from "@modelcontextprotocol/sdk/types.js";
|
|
7
7
|
//#region src/artifacts/types.d.ts
|
|
8
8
|
type ArtifactCommon = {
|
|
@@ -41,9 +41,9 @@ type RuntimeInfo = {
|
|
|
41
41
|
/** Which runtime family reported the fields above. Absent on pre-1.2 builds. */
|
|
42
42
|
runtime?: "edge" | "node";
|
|
43
43
|
};
|
|
44
|
-
declare const readBuildInfoFromEnv: () => BuildInfo;
|
|
45
|
-
declare const resolveBuildInfo: (override?: BuildInfo) => BuildInfo;
|
|
46
|
-
declare const getRuntimeInfo: () => RuntimeInfo;
|
|
44
|
+
export declare const readBuildInfoFromEnv: () => BuildInfo;
|
|
45
|
+
export declare const resolveBuildInfo: (override?: BuildInfo) => BuildInfo;
|
|
46
|
+
export declare const getRuntimeInfo: () => RuntimeInfo;
|
|
47
47
|
//#endregion
|
|
48
48
|
//#region src/gateway/types.d.ts
|
|
49
49
|
type GatewayConfig = {
|
|
@@ -128,7 +128,7 @@ type AuthMiddlewareConfig = {
|
|
|
128
128
|
authenticate?: Authenticate;
|
|
129
129
|
onUnauthorized?: OnUnauthorized;
|
|
130
130
|
};
|
|
131
|
-
declare const createAuthMiddleware: ({ authenticate, onUnauthorized }: AuthMiddlewareConfig) => MiddlewareHandler;
|
|
131
|
+
export declare const createAuthMiddleware: ({ authenticate, onUnauthorized }: AuthMiddlewareConfig) => MiddlewareHandler;
|
|
132
132
|
//#endregion
|
|
133
133
|
//#region src/auth/request.d.ts
|
|
134
134
|
/**
|
|
@@ -143,7 +143,7 @@ declare const createAuthMiddleware: ({ authenticate, onUnauthorized }: AuthMiddl
|
|
|
143
143
|
* absent or the request shape is not recognized — matches the `Headers.get`
|
|
144
144
|
* shape callers already write against.
|
|
145
145
|
*/
|
|
146
|
-
declare const getRequestHeader: (request: unknown, name: string) => string | undefined;
|
|
146
|
+
export declare const getRequestHeader: (request: unknown, name: string) => string | undefined;
|
|
147
147
|
//#endregion
|
|
148
148
|
//#region src/types/routes.d.ts
|
|
149
149
|
type RouteMethod = "GET" | "POST" | "PUT" | "PATCH" | "DELETE";
|
|
@@ -272,7 +272,7 @@ type SomaServerInstance<T extends SessionAuth = SessionAuth> = {
|
|
|
272
272
|
* module — including `somamcp/edge`. The entry barrels supply the default instead:
|
|
273
273
|
* `somamcp` binds createFastMCPBackend, `somamcp/edge` binds createEdgeBackend.
|
|
274
274
|
*/
|
|
275
|
-
declare const createServerCore: <T extends SessionAuth = SessionAuth>(options: SomaServerOptions<T> & {
|
|
275
|
+
export declare const createServerCore: <T extends SessionAuth = SessionAuth>(options: SomaServerOptions<T> & {
|
|
276
276
|
backend: BackendFactory<T>;
|
|
277
277
|
}) => SomaServerInstance<T>;
|
|
278
278
|
//#endregion
|
|
@@ -284,14 +284,14 @@ type ContentInput = {
|
|
|
284
284
|
} | {
|
|
285
285
|
url: string;
|
|
286
286
|
};
|
|
287
|
-
declare const imageContent: (input: ContentInput) => Promise<ImageContent>;
|
|
288
|
-
declare const audioContent: (input: ContentInput) => Promise<AudioContent>;
|
|
287
|
+
export declare const imageContent: (input: ContentInput) => Promise<ImageContent>;
|
|
288
|
+
export declare const audioContent: (input: ContentInput) => Promise<AudioContent>;
|
|
289
289
|
//#endregion
|
|
290
290
|
//#region src/telemetry/CompositeTelemetry.d.ts
|
|
291
|
-
declare const createCompositeTelemetry: (collectors: ReadonlyArray<TelemetryCollector>) => TelemetryCollector;
|
|
291
|
+
export declare const createCompositeTelemetry: (collectors: ReadonlyArray<TelemetryCollector>) => TelemetryCollector;
|
|
292
292
|
//#endregion
|
|
293
293
|
//#region src/telemetry/ConsoleTelemetry.d.ts
|
|
294
|
-
declare const createConsoleTelemetry: (prefix?: string) => TelemetryCollector;
|
|
294
|
+
export declare const createConsoleTelemetry: (prefix?: string) => TelemetryCollector;
|
|
295
295
|
//#endregion
|
|
296
296
|
//#region src/telemetry/EnrichedError.d.ts
|
|
297
297
|
type EnrichedErrorResponse = {
|
|
@@ -300,8 +300,8 @@ type EnrichedErrorResponse = {
|
|
|
300
300
|
relatedState?: Record<string, unknown>;
|
|
301
301
|
suggestions?: ReadonlyArray<string>;
|
|
302
302
|
};
|
|
303
|
-
declare const classifyError: (error: unknown) => ErrorCategory;
|
|
304
|
-
declare const createEnrichedError: (error: unknown, context?: {
|
|
303
|
+
export declare const classifyError: (error: unknown) => ErrorCategory;
|
|
304
|
+
export declare const createEnrichedError: (error: unknown, context?: {
|
|
305
305
|
gatewayStatus?: string;
|
|
306
306
|
toolName?: string;
|
|
307
307
|
}) => EnrichedErrorResponse;
|
|
@@ -311,13 +311,13 @@ type JsonFileTelemetryOptions = {
|
|
|
311
311
|
filePath: string;
|
|
312
312
|
flushIntervalMs?: number;
|
|
313
313
|
};
|
|
314
|
-
declare const createJsonFileTelemetry: (options: JsonFileTelemetryOptions) => TelemetryCollector;
|
|
314
|
+
export declare const createJsonFileTelemetry: (options: JsonFileTelemetryOptions) => TelemetryCollector;
|
|
315
315
|
//#endregion
|
|
316
316
|
//#region src/telemetry/LogLayerTelemetry.d.ts
|
|
317
|
-
declare const createLogLayerTelemetry: (logger: DirectLogger$1) => TelemetryCollector;
|
|
317
|
+
export declare const createLogLayerTelemetry: (logger: DirectLogger$1) => TelemetryCollector;
|
|
318
318
|
//#endregion
|
|
319
319
|
//#region src/telemetry/NoopTelemetry.d.ts
|
|
320
|
-
declare const NoopTelemetry: TelemetryCollector;
|
|
320
|
+
export declare const NoopTelemetry: TelemetryCollector;
|
|
321
321
|
//#endregion
|
|
322
322
|
//#region src/telemetry/telemetryWrapper.d.ts
|
|
323
323
|
/**
|
|
@@ -333,40 +333,40 @@ declare const NoopTelemetry: TelemetryCollector;
|
|
|
333
333
|
* The failure path converts an error to a `ContentResult` with `isError: true`
|
|
334
334
|
* and the enriched error payload as the text content.
|
|
335
335
|
*/
|
|
336
|
-
declare const wrapTool: <T extends SessionAuth, P extends SchemaParams>(tool: Tool<T, P>, telemetry: TelemetryCollector, captureConfig?: ToolCaptureConfig) => Tool<T, P>;
|
|
337
|
-
declare const wrapResource: <T extends SessionAuth>(resource: Resource<T>, telemetry: TelemetryCollector) => Resource<T>;
|
|
338
|
-
declare const wrapPrompt: <T extends SessionAuth, Args extends PromptArgument<T>[] = PromptArgument<T>[]>(prompt: Prompt<T, Args>, telemetry: TelemetryCollector) => Prompt<T, Args>;
|
|
336
|
+
export declare const wrapTool: <T extends SessionAuth, P extends SchemaParams>(tool: Tool<T, P>, telemetry: TelemetryCollector, captureConfig?: ToolCaptureConfig) => Tool<T, P>;
|
|
337
|
+
export declare const wrapResource: <T extends SessionAuth>(resource: Resource<T>, telemetry: TelemetryCollector) => Resource<T>;
|
|
338
|
+
export declare const wrapPrompt: <T extends SessionAuth, Args extends PromptArgument<T>[] = PromptArgument<T>[]>(prompt: Prompt<T, Args>, telemetry: TelemetryCollector) => Prompt<T, Args>;
|
|
339
339
|
//#endregion
|
|
340
340
|
//#region src/logging.d.ts
|
|
341
|
-
declare const createDefaultLogger: (name: string) => DirectLogger$1;
|
|
341
|
+
export declare const createDefaultLogger: (name: string) => DirectLogger$1;
|
|
342
342
|
//#endregion
|
|
343
343
|
//#region src/artifacts/ArtifactManager.d.ts
|
|
344
|
-
declare const registerArtifacts: (app: Hono, artifacts: ReadonlyArray<ArtifactConfig>, authenticate?: ArtifactAuthenticate) => void;
|
|
344
|
+
export declare const registerArtifacts: (app: Hono, artifacts: ReadonlyArray<ArtifactConfig>, authenticate?: ArtifactAuthenticate) => void;
|
|
345
345
|
//#endregion
|
|
346
346
|
//#region src/artifacts/DashboardArtifact.d.ts
|
|
347
|
-
declare const createDashboardArtifact: (getHealth: () => ServerHealth, getCapabilities: () => ServerCapabilities, getConnections: () => ReadonlyArray<GatewayInfo>) => ArtifactConfig;
|
|
347
|
+
export declare const createDashboardArtifact: (getHealth: () => ServerHealth, getCapabilities: () => ServerCapabilities, getConnections: () => ReadonlyArray<GatewayInfo>) => ArtifactConfig;
|
|
348
348
|
//#endregion
|
|
349
349
|
//#region src/artifacts/HealthArtifact.d.ts
|
|
350
|
-
declare const DEFAULT_HEALTH_PATH = "/health";
|
|
351
|
-
declare const DEFAULT_HEALTH_DETAIL_PATH = "/health/detail";
|
|
352
|
-
declare const createHealthArtifact: (getHealth: () => ServerHealth, path?: string) => ArtifactConfig;
|
|
353
|
-
declare const createHealthDetailArtifact: (getHealth: () => ServerHealth, path?: string) => ArtifactConfig;
|
|
350
|
+
export declare const DEFAULT_HEALTH_PATH = "/health";
|
|
351
|
+
export declare const DEFAULT_HEALTH_DETAIL_PATH = "/health/detail";
|
|
352
|
+
export declare const createHealthArtifact: (getHealth: () => ServerHealth, path?: string) => ArtifactConfig;
|
|
353
|
+
export declare const createHealthDetailArtifact: (getHealth: () => ServerHealth, path?: string) => ArtifactConfig;
|
|
354
354
|
//#endregion
|
|
355
355
|
//#region src/artifacts/InfoArtifact.d.ts
|
|
356
|
-
declare const DEFAULT_INFO_PATH = "/info";
|
|
357
|
-
declare const createInfoArtifact: (getInfo: () => ServerInfo, path?: string) => ArtifactConfig;
|
|
356
|
+
export declare const DEFAULT_INFO_PATH = "/info";
|
|
357
|
+
export declare const createInfoArtifact: (getInfo: () => ServerInfo, path?: string) => ArtifactConfig;
|
|
358
358
|
//#endregion
|
|
359
359
|
//#region src/introspection/capabilitiesTool.d.ts
|
|
360
|
-
declare const createCapabilitiesTool: <T extends SessionAuth>(getCapabilities: () => ServerCapabilities) => Tool<T>;
|
|
360
|
+
export declare const createCapabilitiesTool: <T extends SessionAuth>(getCapabilities: () => ServerCapabilities) => Tool<T>;
|
|
361
361
|
//#endregion
|
|
362
362
|
//#region src/introspection/connectionsTool.d.ts
|
|
363
|
-
declare const createConnectionsTool: <T extends SessionAuth>(getConnections: () => ReadonlyArray<GatewayInfo>) => Tool<T>;
|
|
363
|
+
export declare const createConnectionsTool: <T extends SessionAuth>(getConnections: () => ReadonlyArray<GatewayInfo>) => Tool<T>;
|
|
364
364
|
//#endregion
|
|
365
365
|
//#region src/introspection/healthTool.d.ts
|
|
366
|
-
declare const createHealthTool: <T extends SessionAuth>(getHealth: () => ServerHealth) => Tool<T>;
|
|
366
|
+
export declare const createHealthTool: <T extends SessionAuth>(getHealth: () => ServerHealth) => Tool<T>;
|
|
367
367
|
//#endregion
|
|
368
368
|
//#region src/introspection/infoTool.d.ts
|
|
369
|
-
declare const createInfoTool: <T extends SessionAuth>(getInfo: () => ServerInfo, name?: string) => Tool<T>;
|
|
369
|
+
export declare const createInfoTool: <T extends SessionAuth>(getInfo: () => ServerInfo, name?: string) => Tool<T>;
|
|
370
370
|
//#endregion
|
|
371
371
|
//#region src/feedback/redaction.d.ts
|
|
372
372
|
type RedactionPattern = {
|
|
@@ -383,8 +383,8 @@ type RedactionResult = {
|
|
|
383
383
|
redacted: boolean;
|
|
384
384
|
text: string;
|
|
385
385
|
};
|
|
386
|
-
declare const DEFAULT_REDACTION_PATTERNS: ReadonlyArray<RedactionPattern>;
|
|
387
|
-
declare const redact: (input: string, patterns?: ReadonlyArray<RedactionPattern>) => RedactionResult;
|
|
386
|
+
export declare const DEFAULT_REDACTION_PATTERNS: ReadonlyArray<RedactionPattern>;
|
|
387
|
+
export declare const redact: (input: string, patterns?: ReadonlyArray<RedactionPattern>) => RedactionResult;
|
|
388
388
|
//#endregion
|
|
389
389
|
//#region src/feedback/types.d.ts
|
|
390
390
|
type FeedbackType = "bug" | "feature" | "feedback" | "question";
|
|
@@ -437,7 +437,7 @@ declare const PARAMETERS: z.ZodObject<{
|
|
|
437
437
|
question: "question";
|
|
438
438
|
}>>;
|
|
439
439
|
}, z.core.$strip>;
|
|
440
|
-
declare const createFeedbackTool: <T extends SessionAuth>(options: FeedbackToolOptions) => Tool<T, typeof PARAMETERS>;
|
|
440
|
+
export declare const createFeedbackTool: <T extends SessionAuth>(options: FeedbackToolOptions) => Tool<T, typeof PARAMETERS>;
|
|
441
441
|
//#endregion
|
|
442
442
|
//#region src/feedback/providers/github.d.ts
|
|
443
443
|
type GithubFeedbackOptions = {
|
|
@@ -447,7 +447,7 @@ type GithubFeedbackOptions = {
|
|
|
447
447
|
getToken: () => Option<string>;
|
|
448
448
|
repo: `${string}/${string}`;
|
|
449
449
|
};
|
|
450
|
-
declare const createGithubFeedback: (options: GithubFeedbackOptions) => FeedbackProvider;
|
|
450
|
+
export declare const createGithubFeedback: (options: GithubFeedbackOptions) => FeedbackProvider;
|
|
451
451
|
//#endregion
|
|
452
452
|
//#region src/feedback/providers/webhook.d.ts
|
|
453
453
|
type WebhookFeedbackOptions = {
|
|
@@ -456,19 +456,19 @@ type WebhookFeedbackOptions = {
|
|
|
456
456
|
transform?: (payload: NormalizedFeedback) => unknown;
|
|
457
457
|
url: string;
|
|
458
458
|
};
|
|
459
|
-
declare const createWebhookFeedback: (options: WebhookFeedbackOptions) => FeedbackProvider;
|
|
459
|
+
export declare const createWebhookFeedback: (options: WebhookFeedbackOptions) => FeedbackProvider;
|
|
460
460
|
//#endregion
|
|
461
461
|
//#region src/gateway/Gateway.d.ts
|
|
462
|
-
declare const createGateway: (config: GatewayConfig, telemetry: TelemetryCollector) => GatewayInstance;
|
|
462
|
+
export declare const createGateway: (config: GatewayConfig, telemetry: TelemetryCollector) => GatewayInstance;
|
|
463
463
|
//#endregion
|
|
464
464
|
//#region src/gateway/GatewayManager.d.ts
|
|
465
|
-
declare const createGatewayManager: (telemetry: TelemetryCollector) => GatewayManagerInstance;
|
|
465
|
+
export declare const createGatewayManager: (telemetry: TelemetryCollector) => GatewayManagerInstance;
|
|
466
466
|
//#endregion
|
|
467
467
|
//#region src/gateway/toolProxy.d.ts
|
|
468
|
-
declare const createProxiedTools: <T extends SessionAuth>(gateway: GatewayInstance, telemetry?: TelemetryCollector) => ReadonlyArray<Tool<T>>;
|
|
468
|
+
export declare const createProxiedTools: <T extends SessionAuth>(gateway: GatewayInstance, telemetry?: TelemetryCollector) => ReadonlyArray<Tool<T>>;
|
|
469
469
|
//#endregion
|
|
470
470
|
//#region src/index.d.ts
|
|
471
471
|
/** Create a server backed by FastMCP (Node). For edge runtimes, use `somamcp/edge`. */
|
|
472
|
-
declare const createServer: <T extends SessionAuth = SessionAuth>(options: SomaServerOptions<T>) => SomaServerInstance<T>;
|
|
472
|
+
export declare const createServer: <T extends SessionAuth = SessionAuth>(options: SomaServerOptions<T>) => SomaServerInstance<T>;
|
|
473
473
|
//#endregion
|
|
474
|
-
export { type ArtifactAuthenticate, type ArtifactConfig, type AudioContent, type AuthMiddlewareConfig, type Authenticate, type BackendAdapter, type BackendFactory, type BackendSession, type BuildInfo, type CapabilitiesSummary, type CaptureLevel, type Completion, type Content, type ContentResult, type Context,
|
|
474
|
+
export { type ArtifactAuthenticate, type ArtifactConfig, type AudioContent, type AuthMiddlewareConfig, type Authenticate, type BackendAdapter, type BackendFactory, type BackendSession, type BuildInfo, type CapabilitiesSummary, type CaptureLevel, type Completion, type Content, type ContentResult, type Context, type DirectLogger, type DirectoryArtifact, type DynamicArtifact, type EnrichedErrorResponse, type ErrorCategory, type FeedbackEnrichmentContext, type FeedbackProvider, type FeedbackSeverity, type FeedbackSubmitFailure, type FeedbackSubmitResult, type FeedbackSubmitSuccess, type FeedbackToolOptions, type FeedbackType, type GatewayConfig, type GatewayInfo, type GatewayInstance, type GatewayManagerInstance, type GatewayStatus, type GithubFeedbackOptions, type HttpStreamConfig, type ImageContent, type InferSchemaOutput, type JsonFileTelemetryOptions, type Logger, type NormalizedFeedback, type OnUnauthorized, type Progress, type Prompt, type PromptArgument, type PromptResult, type RedactionPattern, type RedactionResult, type Resource, type ResourceContent, type ResourceLink, type ResourceResult, type ResourceTemplate, type ResourceTemplateArgument, type RouteConfig, type RouteMethod, type RuntimeInfo, type SchemaParams, type ServerCapabilities, type ServerConfig, type ServerHealth, type ServerInfo, type ServerStatus, type SessionAuth, type SomaServerInstance, type SomaServerOptions, type StaticArtifact, type TelemetryCollector, type TelemetryEvent, type TelemetryEventType, type TextContent, type Tool, type ToolAnnotations, type ToolCaptureConfig, type ToolOptions, type TransportConfig, UserError, type WebhookFeedbackOptions, createFastMCPBackend };
|
package/dist/index.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import{
|
|
1
|
+
import{n as e}from"./backend-D0qSyfXw.js";import{Map as t,Option as n,Ref as r,Set as i,Try as a,Tuple as o}from"functype";import{Client as s}from"@modelcontextprotocol/sdk/client/index.js";import{StreamableHTTPClientTransport as c}from"@modelcontextprotocol/sdk/client/streamableHttp.js";import{appendFile as l,mkdir as u,readFile as d}from"node:fs/promises";import{dirname as f,extname as p}from"node:path";import{createDirectConsoleLogger as m}from"functype-log";import{z as h}from"zod";const g=e=>e.json({error:`Unauthorized`},401),_=({authenticate:e,onUnauthorized:t})=>{let r=t??g;return async(t,i)=>{if(!e)return r(t);let o=n(t.env).flatMap(e=>n(e.incoming)).orElse(t.req.raw);if((await a.fromPromise(e(o))).isFailure())return r(t);await i()}},v=(e,t)=>typeof e.get==`function`?n(e.get(t)):n.none(),y=(e,t,r)=>{let i=e;return n(i[t]??i[r]).map(e=>Array.isArray(e)?e[0]??``:e)},b=(e,t,r)=>v(e,t).fold(()=>y(e,t,r),e=>n(e)),x=e=>n(e).flatMap(e=>n(e.headers)),S=(e,t)=>{let n=t.toLowerCase();return x(e).flatMap(e=>b(e,n,t)).orUndefined()},C=(e,t,n)=>{t.forEach(t=>{switch(t.protected&&e.use(t.path,_({authenticate:n})),t.type){case`static`:e.get(t.path,e=>e.body(t.content,{headers:{"Content-Type":t.contentType}}));break;case`dynamic`:e.get(t.path,e=>t.handler(e))}})},w=(e,t,n)=>({handler:()=>{let r=e(),i=t(),a=n(),o=T(r,i,a);return new Response(o,{headers:{"Content-Type":`text/html; charset=utf-8`}})},path:`/dashboard`,protected:!0,type:`dynamic`}),T=(e,t,n)=>`<!DOCTYPE html>
|
|
2
2
|
<html lang="en">
|
|
3
3
|
<head>
|
|
4
4
|
<meta charset="UTF-8">
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
const e=async(e,t)=>{let{serve:n}=await import(`@hono/node-server`),r=t.sslCert&&t.sslKey?(await import(`node:https`)).createServer:void 0;return new Promise((i,a)=>{let o=n({fetch:e.fetch,hostname:t.host??`localhost`,port:t.port,...r?{createServer:r,serverOptions:{ca:t.sslCa,cert:t.sslCert,key:t.sslKey}}:{}},()=>i({close:()=>new Promise((e,t)=>{o.close(n=>n?t(n):e()),`closeAllConnections`in o&&o.closeAllConnections()})}));o.once(`error`,a)})},t=async(e,t)=>{let{serveStdio:n}=await import(`@modelcontextprotocol/server/stdio`),r=n(e,t?{transport:t}:{});return{close:()=>r.close()}};export{e as listenHttp,t as listenStdio};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "somamcp",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.5.1",
|
|
4
4
|
"description": "Framework for building MCP servers with telemetry, introspection, and backend abstraction",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./dist/index.js",
|
|
@@ -59,19 +59,22 @@
|
|
|
59
59
|
},
|
|
60
60
|
"homepage": "https://github.com/sapientsai/SomaMCP#readme",
|
|
61
61
|
"dependencies": {
|
|
62
|
-
"@
|
|
63
|
-
"
|
|
64
|
-
"
|
|
65
|
-
"
|
|
66
|
-
"
|
|
67
|
-
"
|
|
62
|
+
"@hono/node-server": "^2.1.5",
|
|
63
|
+
"@modelcontextprotocol/sdk": "^1.32.1",
|
|
64
|
+
"@modelcontextprotocol/server": "~2.3.1",
|
|
65
|
+
"fastmcp": "^4.23.5",
|
|
66
|
+
"functype": "^1.18.0",
|
|
67
|
+
"functype-log": "^1.18.0",
|
|
68
|
+
"hono": "^4.13.13",
|
|
69
|
+
"zod": "^4.6.7"
|
|
68
70
|
},
|
|
69
71
|
"prettier": "ts-builds/prettier",
|
|
70
72
|
"devDependencies": {
|
|
71
|
-
"@
|
|
73
|
+
"@modelcontextprotocol/client": "~2.3.1",
|
|
74
|
+
"@types/node": "^24.19.2",
|
|
72
75
|
"get-port-please": "^3.2.0",
|
|
73
|
-
"ts-builds": "^
|
|
74
|
-
"tsdown": "^0.
|
|
76
|
+
"ts-builds": "^4.0.0",
|
|
77
|
+
"tsdown": "^0.23.1"
|
|
75
78
|
},
|
|
76
|
-
"packageManager": "pnpm@11.
|
|
79
|
+
"packageManager": "pnpm@11.28.6+sha512.55d90390c3b39042f1505a2697789f0256c6d95bb28bdd7cb731af1887c9f2629ef581acb9f4e4ec772024c8203c2aed22a03299b97103fdcf32668e905d0024"
|
|
77
80
|
}
|
package/dist/backend-Dd0n_9Ai.js
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
import{FastMCP as e,ServerState as t}from"fastmcp";const n=e=>{switch(e){case t.Running:return`running`;case t.Error:return`error`;default:return`stopped`}},r=(t,r)=>{let i={...r,authenticate:t.authenticate,instructions:t.instructions,logger:t.logger,name:t.name,...t.streamKeepalive?{streamKeepalive:t.streamKeepalive}:{},version:t.version},a=new e(i);return{get serverState(){return n(a.serverState)},get sessions(){return a.sessions.map(e=>({sessionId:e.sessionId}))},addPrompt:e=>{a.addPrompt(e)},addResource:e=>{a.addResource(e)},addResourceTemplate:(...e)=>{a.addResourceTemplate(...e)},addTool:e=>{a.addTool(e)},fetch:async e=>a.getApp().fetch(e),getApp:()=>a.getApp(),on:(e,t)=>{a.on(e,t)},removePrompt:e=>a.removePrompt(e),removeResource:e=>a.removeResource(e),removeTool:e=>a.removeTool(e),start:async e=>{if(!e){await a.start();return}e.transportType===`httpStream`?await a.start({httpStream:e.httpStream,transportType:`httpStream`}):await a.start({transportType:`stdio`})},stop:()=>a.stop()}};export{r as t};
|