fix(httpapi): return mcp server not found errors (#28817)

This commit is contained in:
Shoubhit Dash
2026-05-22 17:46:30 +05:30
committed by GitHub
parent 51da3483a9
commit 0beb4de3e8
8 changed files with 158 additions and 72 deletions
@@ -2,6 +2,7 @@ import { MCP } from "@/mcp"
import { Effect, Schema } from "effect"
import { HttpApiBuilder, HttpApiError } from "effect/unstable/httpapi"
import { InstanceHttpApi } from "../api"
import { McpServerNotFoundError } from "../errors"
import { AddPayload, AuthCallbackPayload, StatusMap, UnsupportedOAuthError } from "../groups/mcp"
export const mcpHandlers = HttpApiBuilder.group(InstanceHttpApi, "mcp", (handlers) =>
@@ -20,38 +21,74 @@ export const mcpHandlers = HttpApiBuilder.group(InstanceHttpApi, "mcp", (handler
})
const authStart = Effect.fn("McpHttpApi.authStart")(function* (ctx: { params: { name: string } }) {
if (!(yield* mcp.supportsOAuth(ctx.params.name))) {
return yield* new UnsupportedOAuthError({ error: `MCP server ${ctx.params.name} does not support OAuth` })
}
return yield* mcp.startAuth(ctx.params.name)
return yield* Effect.gen(function* () {
if (!(yield* mcp.supportsOAuth(ctx.params.name))) {
return yield* new UnsupportedOAuthError({ error: `MCP server ${ctx.params.name} does not support OAuth` })
}
return yield* mcp.startAuth(ctx.params.name)
}).pipe(
Effect.catchTag("MCP.NotFoundError", (error) =>
Effect.fail(new McpServerNotFoundError({ name: error.name, message: `MCP server not found: ${error.name}` })),
),
)
})
const authCallback = Effect.fn("McpHttpApi.authCallback")(function* (ctx: {
params: { name: string }
payload: typeof AuthCallbackPayload.Type
}) {
return yield* mcp.finishAuth(ctx.params.name, ctx.payload.code)
return yield* mcp
.finishAuth(ctx.params.name, ctx.payload.code)
.pipe(
Effect.catchTag("MCP.NotFoundError", (error) =>
Effect.fail(new McpServerNotFoundError({ name: error.name, message: `MCP server not found: ${error.name}` })),
),
)
})
const authAuthenticate = Effect.fn("McpHttpApi.authAuthenticate")(function* (ctx: { params: { name: string } }) {
if (!(yield* mcp.supportsOAuth(ctx.params.name))) {
return yield* new UnsupportedOAuthError({ error: `MCP server ${ctx.params.name} does not support OAuth` })
}
return yield* mcp.authenticate(ctx.params.name)
return yield* Effect.gen(function* () {
if (!(yield* mcp.supportsOAuth(ctx.params.name))) {
return yield* new UnsupportedOAuthError({ error: `MCP server ${ctx.params.name} does not support OAuth` })
}
return yield* mcp.authenticate(ctx.params.name)
}).pipe(
Effect.catchTag("MCP.NotFoundError", (error) =>
Effect.fail(new McpServerNotFoundError({ name: error.name, message: `MCP server not found: ${error.name}` })),
),
)
})
const authRemove = Effect.fn("McpHttpApi.authRemove")(function* (ctx: { params: { name: string } }) {
const status = yield* mcp.status()
if (!(ctx.params.name in status))
return yield* new McpServerNotFoundError({
name: ctx.params.name,
message: `MCP server not found: ${ctx.params.name}`,
})
yield* mcp.removeAuth(ctx.params.name)
return { success: true as const }
})
const connect = Effect.fn("McpHttpApi.connect")(function* (ctx: { params: { name: string } }) {
yield* mcp.connect(ctx.params.name)
yield* mcp
.connect(ctx.params.name)
.pipe(
Effect.catchTag("MCP.NotFoundError", (error) =>
Effect.fail(new McpServerNotFoundError({ name: error.name, message: `MCP server not found: ${error.name}` })),
),
)
return true
})
const disconnect = Effect.fn("McpHttpApi.disconnect")(function* (ctx: { params: { name: string } }) {
yield* mcp.disconnect(ctx.params.name)
yield* mcp
.disconnect(ctx.params.name)
.pipe(
Effect.catchTag("MCP.NotFoundError", (error) =>
Effect.fail(new McpServerNotFoundError({ name: error.name, message: `MCP server not found: ${error.name}` })),
),
)
return true
})