Hacktoberfest 2026: los issues que los mantenedores marcaron para octubre, abiertos y aptos para principiantes. Explorar issues de Hacktoberfest

A handler that throws McpError produces a double-prefixed message on the client

Abierto
#2,786 4 comentarios 0 reacciones 0 asignados Ver en GitHub

Los mantenedores suelen responder en 1 día

@errmakov ya está trabajando en esto.

Desde el 27/9/2026.

  • #2881 de @MustafaKemal0146 — abierto

Evaluación

Dificultad
3/5
Tiempo estimado
1-2 días
Aptitud para principiantes
68/100
Tipo de issue
Error
Claridad
Bastante claro
Estado de actividad
Activo
Stack tecnológico
typescript

Línea de trabajo

Comienza en Protocol._onresponse y McpError.fromError, siguiendo tanto _requestResolvers como las rutas de respuesta normales descritas en el informe. Reproduce el rechazo de callTool mediante InMemoryTransport y verifica después que el mensaje de error solo tenga un prefijo, sin introducir una regresión en la rama UrlElicitationRequired. Se considera terminado cuando las respuestas McpError lanzadas llegan al cliente con un único prefijo de error MCP.

Escrito por el modelo de indexación a partir del texto del issue.

Descripción

v1

What happens

A request handler that throws McpError produces a message the client shows with the prefix twice.
Reproduced with the SDK alone over InMemoryTransport on 1.24.3, and the code path is unchanged in the
current 1.30.0:

server.setRequestHandler(CallToolRequestSchema, async () => {
  throw new McpError(ErrorCode.MethodNotFound, "Unknown tool: nope");
});
// ...
try { await client.callTool({ arguments: {}, name: "nope" }); }
catch (e) { console.log("client received:", e.message); }
server threw:   MCP error -32601: Unknown tool: nope
client received: MCP error -32601: MCP error -32601: Unknown tool: nope

Why

Three steps, each defensible alone:

  1. McpError's constructor calls super(`MCP error ${code}: ${message}`), so .message already carries
    the prefix.
  2. The server serialises a thrown error as message: error.message, so the prefix travels inside the
    JSON-RPC error.message field.
  3. Protocol._onresponse converts it back with McpError.fromError(response.error.code, response.error.message, response.error.data), whose default branch returns
    new McpError(code, message, data) and prefixes what is already prefixed. I confirmed at runtime that
    this is the path a callTool rejection takes, by counting calls into fromError: exactly one.

_onresponse also holds a new McpError(...) conversion in its _requestResolvers branch, for queued
responses, which double-prefixes for the same reason.

Throwing McpError is the SDK's own mechanism and shared/protocol throws it in several places itself, so
this is the default result rather than a misuse.

What I expected

One prefix. Either the JSON-RPC error.message carries the bare message, or the client stops re-wrapping a
message that already has the prefix.

Not checked

Only InMemoryTransport, and only a callTool rejection. The one branch of fromError that does not take
the default path is UrlElicitationRequired carrying elicitations, which returns
UrlElicitationRequiredError; that class calls super with the same code, so I would expect it to prefix
too, but I did not exercise it.

Lenguaje dominante
TypeScript
Estrellas
13.6k
Forks
2.3k
Merge medio
1 d 14 h
PR fusionados (30 d)
53

Preparar el entorno

Primeros pasos

  1. Lee el issue completo y luego la guía de contribución del proyecto.
  2. Comenta en el issue que vas a ocuparte — evita que dos personas hagan lo mismo.
  3. Haz un fork del repositorio y trabaja en una rama.
  4. Abre un pull request que haga referencia al número del issue.

Más de modelcontextprotocol/typescript-sdk

Todos los issues de modelcontextprotocol/typescript-sdk

Issues similares

Más issues de TypeScript

Recibe los nuevos issues en tu correo

Un resumen breve de issues de GitHub para principiantes.