modelcontextprotocol / modelcontextprotocol/python-sdk

support logging to stderr in Jupyter Notebook Environments.

Ouverte
#156 12 commentaires 0 réactions 0 personnes assignées Voir sur GitHub

Personne n'a encore pris cette issue.

bug good first issue P3 ready for work
Langage dominant
Python
Étoiles
24.3k
Forks
4k
Merge moyen
1 j 1 h
PR mergées (30 j)
31

Description

Is your feature request related to a problem? Please describe.
I want to make mcp python-sdk jupyter notebook compatible. When running in a notebook environment, MCP work but do not output stderr as it does normally.

For instance in jupyter notebook:

import mcp
import os
from mcp.client.stdio import stdio_client

serverparams = mcp.StdioServerParameters(
    command="uv",
    args=["--quiet", "run", "../src/echo.py"],
    env={"UV_PYTHON": "3.12", **os.environ},
)

async with stdio_client(serverparams) as (read, write):
    async with mcp.ClientSession(read, write) as session:
        await session.initialize()
        tools = await session.list_tools()
        print(tools)

Outputs:

meta=None nextCursor=None tools=[Tool(name='echo_tool', description='Echo the input text\n\n    Args:\n        text (str): The text to echo\n\n    Returns:\n        str: The echoed text\n    ', inputSchema={'properties': {'text': {'title': 'Text', 'type': 'string'}}, 'required': ['text'], 'title': 'echo_toolArguments', 'type': 'object'})]

while running the server without jupyter notebook:

❯ uv run --quiet src/echo.py
starting echo server

stderr is correctly displayed.

This is a big problem mostly because if the server is crashing or the command is wrong you have no way to know what's wrong: nothing is logged and the jupyter notebook cell just hangs.

Describe the solution you'd like
I found the culprit being the use of:

process = await anyio.open_process(
        [server.command, *server.args],
        env=server.env if server.env is not None else get_default_environment(),
        stderr=sys.stderr,
 )

In particular sys.stderr here is not working in the jupyter / ipython context. Instead I would suggest a working change as follow:

  1. remove the stderr params from the process and handle process.stderr in an async function as stdout / stdin is handled.
  2. to that effect, use a stderr_reader async function like the following:
    async def stderr_reader():
        assert process.stderr, "Opened process is missing stderr"
        try:
            async for line in process.stderr:
                if is_jupyter_notebook():
                    print(f"\033[91m {line.decode().strip()}")
                else:
                    # redirect to stderr as before
                    print(line.decode().strip(), file=sys.stderr)
        except anyio.ClosedResourceError:
            await anyio.lowlevel.checkpoint()

This would result in the same behavior as before while allowing the stderr to be logged in the jupyter notebook context.

Additional context
Jupyter notebook support support is also requested for mcpadapt which bring MCP server tools in any agentic framework, as many agentic framework demonstrate usage in jupyter notebooks.
https://github.com/grll/mcpadapt

Guide de contribution

Ouvrir le guide de contribution

Par où commencer

  1. Lisez l'issue en entier, puis le guide de contribution du projet.
  2. Signalez en commentaire que vous la prenez — cela évite que deux personnes fassent le même travail.
  3. Forkez le dépôt et travaillez sur une branche.
  4. Ouvrez une pull request qui référence le numéro de l'issue.

Piste de recherche

Commencez par stdio_client et son appel à anyio.open_process, puis comparez le fonctionnement de la gestion existante de stdout et stdin avec process.stderr. La tâche sera terminée lorsque les erreurs du serveur seront visibles dans les notebooks Jupyter ou IPython, tandis que stderr conservera son comportement normal ailleurs, y compris lorsque le processus échoue ou que la commande est invalide.

Rédigé par le modèle d'indexation à partir du texte de l'issue.

Évaluation

Stack technique
jupyter-notebook, python
Domaine
backend, cli, developer-experience
Type d'issue
Fonctionnalité
Difficulté
3/5
Temps estimé
1-2 jours
Activité
Active
Clarté
Plutôt claire
Accessibilité débutants
58/100

Recevez les nouvelles issues par e-mail

Un résumé court des issues GitHub adaptées aux débutants.