Hacktoberfest 2026: le issue che i maintainer hanno segnato per ottobre, aperte e adatte ai principianti. Sfoglia le issue Hacktoberfest

McpServer: middleware and visibility can't use per-request services from HttpRouter middleware under layerHttp

Aperta
#9,854 0 commenti 0 reazioni 0 assegnatari Vedi su GitHub

I maintainer di solito rispondono entro 1 giorno

Nessuno ha ancora preso questa issue.

Valutazione

Difficoltà
4/5
Tempo stimato
3-5 giorni
Idoneità per principianti
55/100
Tipo di issue
Bug
Chiarezza
Abbastanza chiara
Stato di attività
Attiva
Stack tecnologico
typescript

Direzione di ricerca

Start with MiddlewareLayer and its McpRequest.From<"Requires", ...> layer type, then compare how middleware requirements are handled by layerHttp, layer, and layerStdio. The report says the runtime already forwards these dependencies through layerHttp; verify the behavior with the described visibility and tool-call cases. Done when middleware and visibility can use HttpRouter per-request services through layerHttp, while unmet requirements remain visible for layer and layerStdio.

Scritto dal modello di indicizzazione a partire dal testo della issue.

Descrizione

On v4/next-minor (pkg.pr.new 7ce7d03), tools can depend on per-request services provided by HttpRouter middleware: layerHttp converts the remaining McpRequest.From<"Requires", R> into HttpRouter.Request.From<"Requires", R>. MCP middleware and visibility checks can't. MiddlewareLayer turns any requirement outside TransportServices into MissingRequestDependencies, so it can only be satisfied by .combine or the transport.

class CurrentUser extends Context.Service<CurrentUser, { readonly id: number }>()("CurrentUser") {}

// HTTP auth stays at the HTTP layer: OAuth discovery and refresh need a 401 with WWW-Authenticate,
// and MCP middleware never runs for initialize/ping
const Auth = HttpRouter.middleware<{ provides: CurrentUser }>()(/* bearer token -> user */)

const Policy = McpServer.visibility(
  Effect.succeed(({ target }) =>
    Effect.gen(function* () {
      const user = yield* CurrentUser
      return canUse(user, target)
    })
  )
)

Policy.layer
// ^? MissingRequestDependencies<CurrentUser>, although Auth provides CurrentUser to every request under layerHttp

The workaround is an MCP middleware that re-provides what is already on the fiber:

const Bridge = McpServer.middleware<{ provides: CurrentUser }>()((effect) =>
  Effect.gen(function* () {
    const user = yield* Effect.serviceOption(CurrentUser)
    if (Option.isNone(user)) return yield* Effect.die(new Error("missing HTTP auth"))
    return yield* effect.pipe(CurrentUser.provide(user.value))
  })
)

Policy.combine(Bridge).layer

Doing the authentication itself in a combined MCP middleware would mean resolving the token and user a second time on every request.

Proposal

Drop the conditional and always put the per-request requirements in the layer input, as registrations already do. layerHttp then forwards them to HttpRouter, while layer / layerStdio still surface them as unmet requirements:

type MiddlewareLayer<Config extends MiddlewareConfig, R> = Layer.Layer<
  McpRequest.From<"Requires", Config["provides"]>,
  Config["layerError"],
  R | Config["layerRequires"] | McpRequest.From<"Requires", Config["requires"]>
>

The runtime already handles this. With only the .d.ts patched and the bridge removed, through layerHttp + HttpRouter.toWebHandler:

  • tools/list hides the tool the policy rejects
  • the visible tool receives CurrentUser
  • calling the hidden tool returns -32602 Tool '…' not found

Trade-off: an unmet requirement then shows up as a missing layer requirement at the server instead of the named MissingRequestDependencies at .layer. Happy to open a PR if this direction is fine.

Lingua principale
TypeScript
Stelle
16.7k
Fork
808
Merge medio
10h 13m
PR unite (30g)
800

Preparare l'ambiente

Questo progetto non fornisce container di sviluppo, Dockerfile né guida per i contributori, quindi l'ambiente è a tuo carico: parti dal suo README e consulta la nostra guida al primo contributo per i passaggi generali.

Come iniziare

  1. Leggi tutta la issue e poi la guida ai contributi del progetto.
  2. Commenta sulla issue per dire che te ne occupi tu — evita che due persone facciano lo stesso lavoro.
  3. Fai un fork del repository e lavora su un branch.
  4. Apri una pull request che faccia riferimento al numero della issue.

Altre issue di Effect-TS/effect

Tutte le issue di Effect-TS/effect

Issue simili

Altre issue su TypeScript

Ricevi le nuove issue nella tua casella

Un breve riepilogo di issue GitHub adatte ai principianti.