Skip to main content

Model Context Protocol (MCP) Client and Server

Client supports Stdio and Streamable HTTP. Server supports Stdio and Streamable HTTP.

Install

pip install mcp-nequeo

Usage

Client

from ..McpClient import McpClient

class SampleClient(McpClient):
    """
    Sample Client.
    """
    def __init__(self):
        super().__init__()

Server

from ..McpServerBase import McpServerBase
from ..McpTypes import McpPromptHelper

class SampleServer(McpServerBase):
    """
    Sample Server
    """
    def __init__(self):
        super().__init__("SampleServer", "1.0.1", "Sample server", 
                         dict( resources={}, tools={}, prompts={}))

SymPy Client

from typing import Optional, Any, List, Union

from ..McpClient import McpClient

# SymPy Math Expression Evaluator.
class SymPyMath(McpClient):
    """
    SymPy Math Expression Evaluator.
    """
    def __init__(self):
        super().__init__()

    async def callMathExpressionEvaluatorTool(self, expression: str) -> Union[Any, None]:
        """
        call the math expression evaluator tool.

        Args:
            expression: the math expression.

        Return:
            the evaluated expression.
        """
        res: Any = await self.callTool("SymPy_MathExpressionEvaluator", args={"expression": expression})

        # return the result.
        return res

    async def callMathExpressionEvaluatorPrompt(self, expression: str) -> Union[Any, None]:
        """
        call the math expression evaluator prompt.

        Args:
            expression: the math expression.

        Return:
            the evaluated expression.
        """
        res: Any = await self.callPrompt("MathExpressionEvaluator", args={"expression": expression})

        # return the result.
        return res

    async def callMathExpressionResultPrompt(self, result: str) -> Union[Any, None]:
        """
        call the math expression result prompt.

        Args:
            result: the math result.

        Return:
            the evaluated result.
        """
        res: Any = await self.callPrompt("MathExpressionResult", args={"result": result})

        # return the result.
        return res

    async def callSymPyDocsUrlResource(self) -> Union[Any, None]:
        """
        call the SymPy documentation URL resource.

        Return:
            the resource result.
        """
        res: Any = await self.callResource("sympy://{version}")

        # return the result.
        return res

    async def callSymPyDocsUrlVersionResource(self, version: str) -> Union[Any, None]:
        """
        call the SymPy documentation URL resource.

        Args:
            version: the version.

        Return:
            the resource result.
        """
        res: Any = await self.callResource(f"sympy://doc/{version}/num")

        # return the result.
        return res

SymPy Server

from sympy import *
from sympy import sympify

from typing import Optional, Any, List, Union, Callable, Awaitable

from mcp.types import ToolAnnotations
from mcp.server.fastmcp import FastMCP
from mcp.server.fastmcp.prompts.base import PromptArgument, Message, TextContent

from ..McpServerBase import McpServerBase
from ..McpTypes import McpPromptHelper

# SymPy Math Expression Evaluator.
class SymPyMath(McpServerBase):
    """
    SymPy math expression evaluator.
    """
    def __init__(self):
        super().__init__("SymPyMathExpression", "1.2.1", "SymPy math expression evaluator", 
                         dict( resources={}, tools={}, prompts={}))

    def registerTool_MathExpressionEvaluator(self) -> bool:
        """
        register tool math expression evaluator.

        Return:
            true if tool registered; else false.
        """
        result: bool = self.registerTool(
            "SymPy_MathExpressionEvaluator", 
            self.mathExpressionEvaluator,
            "Use SymPy to execute the mathematical expressions")

        # if added
        if (result):
            # set parameters
            self.setToolParameters("SymPy_MathExpressionEvaluator", {
                "type": "object",
                "properties": {
                    "expression": {
                        "type": "string",
                        "description": "the SymPy mathematical expression"
                    }
                },
                "required": ["expression"],
                "additionalProperties": False
            })
        return result

    def registerPrompt_MathExpressionEvaluator(self) -> bool:
        """
        register prompt math expression evaluator.

        Return:
            true if prompt registered; else false.
        """
        return self.registerPrompt(
            "MathExpressionEvaluator",
            self.mathExpressionEvaluatorPrompt,
            "Evaluate the mathematical expression",
            [ PromptArgument(name = "expression", description = "the SymPy mathematical expression", required = True) ]
        )

    def registerPrompt_MathExpressionResult(self) -> bool:
        """
        register prompt math expression result.

        Return:
            true if prompt registered; else false.
        """
        return self.registerPrompt(
            "MathExpressionResult",
            self.mathExpressionResultPrompt,
            "Describe the expression result",
            [ PromptArgument(name = "result", description = "the math evaluated result", required = True) ]
        )

    def registerResource_SymPyDocsUrl(self) -> bool:
        """
        register resource sympy documentation URL.

        Return:
            true if resource registered; else false.
        """
        return self.registerResource(
            "MathExpressionSymPyDocsUrl",
            "sympy://{version}",
            self.mathExpressionSymPyDocsUrlResource,
            "Get the SymPy documentation URL",
            "text/plain"
        )

    def registerResource_SymPyDocsUrl_Version(self) -> bool:
        """
        register resource sympy documentation URL version.

        Return:
            true if resource registered; else false.
        """
        return self.registerResourceTemplate(
            "MathExpressionSymPyDocsUrlVersion",
            "sympy://doc/{version}/num",
            self.mathExpressionSymPyDocsUrlVersionResource,
            "Get the SymPy documentation URL version",
            "text/plain"
        )

    def mathExpressionEvaluatorPrompt(self, expression: str) -> List[Message]:
        """
        prompt math expression evaluator.

        Args:
            expression:    expression to evaluate.

        Return:
            the prompt result.
        """
        return [ 
            Message(
                role = "user", 
                content = TextContent(
                    type = "text", 
                    text = f"evaluate the math expression: {expression}")
            )
        ]

    def mathExpressionResultPrompt(self, result: str) -> List[Message]:
        """
        prompt math expression result.

        Args:
            result:    expression to evaluate.

        Return:
            the prompt result.
        """
        return [ 
            Message(
                role = "user", 
                content = TextContent(
                    type = "text", 
                    text = f"describe the result: {result}, using latex")
            )
        ]

    def mathExpressionEvaluator(self, expression: str) -> str:
        """
        use SymPy to execute the mathematical expressions

        Args:
            expression:    the SymPy mathematical expression.

        Return:
            the expression result.
        """
        result = ""
        
        try:
            expr = sympify(expression)
            result = expr.evalf(15)
        except Exception as e:
            try:
                expr = sympify(expression)
                result = str(expr)
            except Exception as e:
                result = f"error: {e}"

        # return the result.
        return result

    def mathExpressionSymPyDocsUrlResource(self) -> str:
        """
        SymPy documentation URL resource.

        Return:
            the resource result.
        """
        return f"https://docs.sympy.org/latest/index.html"

    def mathExpressionSymPyDocsUrlVersionResource(self, version: str) -> str:
        """
        SymPy documentation URL resource version.

        Args:
            version: the version.

        Return:
            the resource result.
        """
        return f"The document version {version}"

    def register(self) -> bool:
        """
        register all tools, prompts, resources.

        Return:
            true if registered; else false.
        """
        registeredAll: bool = True

        # ternary conditional statement.
        # register tools.
        registeredAll = True if (self.registerTool_MathExpressionEvaluator() and registeredAll) else False
        registeredAll = True if (self.registerPrompt_MathExpressionEvaluator() and registeredAll) else False
        registeredAll = True if (self.registerPrompt_MathExpressionResult() and registeredAll) else False
        registeredAll = True if (self.registerResource_SymPyDocsUrl() and registeredAll) else False
        registeredAll = True if (self.registerResource_SymPyDocsUrl_Version() and registeredAll) else False

        # if all registered.
        return registeredAll

    def getPromptHelpers(self) -> List[McpPromptHelper]:
        """
        get the list of prompt helpers.

        Return:
            the list of prompt helpers.
        """
        prompts: List[McpPromptHelper] = []

        # add prompt.
        prompts.append(McpPromptHelper(
            "MathExpressionEvaluator",
            "evaluate the math expression: {expression}"
        ))

        prompts.append(McpPromptHelper(
            "MathExpressionResult",
            "describe the result: {result}, using latex"
        ))

        # return the helper list.
        return prompts

# if main.
def mainSymPyMathServer(useStreamableHttp: bool = False) -> SymPyMath | None:
    """
    start the SymPy math server.

    Args:
            useStreamableHttp:    use streamable HTTP to receiving messages.
    """
    # start server.
    sympymath_server = SymPyMath()

    # if registered
    if (sympymath_server.register()):
        # start server.
        if (useStreamableHttp):
            sympymath_server.startServerHttp()
        else:
            sympymath_server.startServerStdio()

        # return the server.
        return sympymath_server
    else:
        return None

Metadata

Release files for mcp-nequeo 2.7.27

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for mcp-nequeo 2.7.27
File Size Uploaded Provenance Actions
mcp_nequeo-2.7.27.tar.gz 13.2 kB Without provenance Details for mcp_nequeo-2.7.27.tar.gz

Built distribution (wheel)

Table of built distributions (wheels) for mcp-nequeo 2.7.27
File Interpreter ABI Platform Actions
mcp_nequeo-2.7.27-py3-none-any.whl Python 3 none any Details for mcp_nequeo-2.7.27-py3-none-any.whl

Total release size: 26.2 kB

Release files / mcp_nequeo-2.7.27.tar.gz

Download URL mcp_nequeo-2.7.27.tar.gz
Size 13.2 kB
Tags Source
SHA-256 checksum
How to use checksums
f193f1a58c86d69a53df4b05f130462f952dc3c6bf7bb389322791848d0c8f90
BLAKE2b-256 checksum
How to use checksums
6796cbcf4419a9ab4dcb7850cb73cda73361fbe397a0a06b23391a6aa15612d8
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.13.13

Release files / mcp_nequeo-2.7.27-py3-none-any.whl

Download URL mcp_nequeo-2.7.27-py3-none-any.whl
Size 13.0 kB
Tags Python 3
SHA-256 checksum
How to use checksums
beedd034e72b7e52833c5fe74266fa5f21f3a8b2cda1da83012d5bf65f402f3a
BLAKE2b-256 checksum
How to use checksums
11722bb062190f1979501fba20ff7c3a7aa1f7ac590098dc1c8446cc7350e09a
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.13.13

Security for mcp-nequeo 2.7.27

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

No provenance found

None of the files in this release were uploaded with provenance metadata.

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page