Skip to main content
Recommended Reading: For practical implementation details, see the MCP Integration Guide.
💻 Code Examples

What is MCP?

The Model Context Protocol (MCP) is an open standard that enables seamless communication between AI applications and external tools. Slide’s Tyler package includes first-class MCP support, allowing your agents to:
  • Connect to any MCP-compatible server
  • Use tools from external services
  • Share context across applications
  • Build interoperable AI systems

MCP Architecture in Slide

Tyler uses the official MCP SDK’s ClientSessionGroup to manage connections to multiple MCP servers simultaneously. This provides:
  • Automatic session lifecycle management
  • Tool discovery and aggregation across servers
  • Tool execution routing to the correct server
  • Support for all SDK transport types (stdio, SSE, StreamableHTTP)

Quick Start

import asyncio
from tyler import Agent, Thread, Message

async def main():
    # Create agent with MCP config (validates schema immediately)
    agent = Agent(
        name="Tyler",
        model_name="gpt-4.1",
        tools=["web"],
        mcp={
            "servers": [{
                "name": "docs",
                "transport": "streamablehttp",  # Use for Mintlify and hosted servers
                "url": "https://slide.mintlify.app/mcp"
            }]
        }
    )

    # Connect to MCP servers (fail fast!)
    await agent.connect_mcp()
    
    # Use the agent - MCP tools are now available
    thread = Thread()
    thread.add_message(Message(
        role="user",
        content="How do I create a Tyler agent?"
    ))
    
    result = await agent.run(thread)
    print(result.content)
    
    # Cleanup MCP connections
    await agent.cleanup()

if __name__ == "__main__":
    asyncio.run(main())

Using MCP Tools

Once connected, MCP tools are automatically available to your agent with namespaced names:
# Tools from server "docs" become available as:
# - docs_SearchSlideFramework
# - docs_GetDocument
# etc.

# The agent automatically selects and uses appropriate tools
thread = Thread()
thread.add_message(Message(
    role="user",
    content="Search the Slide documentation for information about streaming"
))

result = await agent.run(thread)

MCP Server Types

1. Stdio Servers

Local processes that communicate via standard input/output. Great for local tools and development:
mcp={
    "servers": [{
        "name": "filesystem",
        "transport": "stdio",
        "command": "npx",
        "args": ["-y", "@modelcontextprotocol/server-filesystem", "/tmp"],
        "env": {"NODE_ENV": "production"}  # Optional environment
    }]
}

2. StreamableHTTP Servers

HTTP-based servers using the newer streaming protocol. Recommended for hosted MCP servers:
mcp={
    "servers": [{
        "name": "docs",
        "transport": "streamablehttp",
        "url": "https://slide.mintlify.app/mcp",
        "headers": {"X-API-Key": "${API_KEY}"}  # Optional auth
    }]
}

3. SSE (Server-Sent Events) Servers

Legacy HTTP transport for streaming connections:
mcp={
    "servers": [{
        "name": "legacy",
        "transport": "sse",
        "url": "https://legacy.example.com/mcp"
    }]
}

Creating MCP Servers

Using FastMCP (Python)

Create an MCP server that exposes tools to Slide:
from fastmcp import FastMCP

# Create MCP server
mcp = FastMCP()

@mcp.tool()
async def search_knowledge_base(query: str) -> str:
    """Search internal knowledge base."""
    results = await db.search(query)
    return format_results(results)

@mcp.tool()
async def execute_sql(query: str, database: str = "main") -> dict:
    """Execute SQL query safely."""
    if not is_safe_query(query):
        return {"error": "Unsafe query"}
    
    conn = get_connection(database)
    results = await conn.execute(query)
    return {"data": results}

# Run the server
if __name__ == "__main__":
    mcp.run()

Advanced MCP Usage

Multiple Server Connections

Connect to multiple MCP servers simultaneously:
agent = Agent(
    name="multi-server-agent",
    model_name="gpt-4.1",
    mcp={
        "servers": [
            {
                "name": "docs",
                "transport": "streamablehttp",
                "url": "https://slide.mintlify.app/mcp",
                "prefix": "slide"  # Custom prefix
            },
            {
                "name": "github",
                "transport": "stdio",
                "command": "npx",
                "args": ["-y", "@modelcontextprotocol/server-github"],
                "env": {"GITHUB_PERSONAL_ACCESS_TOKEN": "${GITHUB_TOKEN}"},
                "prefix": "gh",
                "fail_silent": True  # Continue if GitHub unavailable
            },
            {
                "name": "filesystem",
                "transport": "stdio",
                "command": "npx",
                "args": ["-y", "@modelcontextprotocol/server-filesystem", "/tmp"],
                "exclude_tools": ["write_file", "delete_file"]  # Read-only
            }
        ]
    }
)

await agent.connect_mcp()

# Agent now has tools from all servers:
# - slide_SearchSlideFramework
# - gh_search_repos
# - filesystem_read_file, filesystem_list_directory

Tool Filtering

Control which tools are available:
{
    "name": "filesystem",
    "transport": "stdio",
    "command": "mcp-server-filesystem",
    "include_tools": ["read_file", "list_directory"],  # Whitelist
    "exclude_tools": ["delete_file"]  # Blacklist (applied after include)
}

Custom Prefixes

Override the default namespace prefix for cleaner tool names:
{
    "name": "wandb_documentation_server",  # Long server name
    "prefix": "docs",  # Short, clean prefix
    "transport": "streamablehttp",
    "url": "https://docs.wandb.ai/mcp"
}
# Tools become: docs_search, docs_query (not wandb_documentation_server_search)

Environment Variable Substitution

Use environment variables for secrets (recommended!):
mcp={
    "servers": [{
        "name": "api",
        "transport": "streamablehttp",
        "url": "https://api.example.com/mcp",
        "headers": {
            "Authorization": "Bearer ${API_TOKEN}",  # Substituted from env
            "X-API-Key": "${API_KEY}"
        }
    }]
}

Graceful Degradation

Control failure behavior per server:
{
    "servers": [
        {
            "name": "critical",
            "url": "...",
            "fail_silent": False  # Fail startup if unavailable
        },
        {
            "name": "optional",
            "url": "...",
            "fail_silent": True  # Continue if unavailable (default)
        }
    ]
}

Best Practices

Always cleanup MCP connections in long-running applications:
agent = Agent(mcp={...})
try:
    await agent.connect_mcp()
    # Use agent
finally:
    await agent.cleanup()
For short scripts with streamablehttp transport, cleanup is required:
async def main():
    agent = Agent(mcp={"servers": [{"transport": "streamablehttp", ...}]})
    await agent.connect_mcp()
    result = await agent.run(thread)
    await agent.cleanup()  # Required for streamablehttp
Never hardcode secrets:
# Good
"headers": {"Authorization": "Bearer ${API_TOKEN}"}

# Bad
"headers": {"Authorization": "Bearer sk-1234567890"}
Only connect to trusted MCP servers - they execute with your agent’s permissions.
Use custom prefixes for cleaner tool names:
{
    "name": "long_server_name",
    "prefix": "short",  # Tools become short_toolname
    ...
}
Use fail_silent: True for optional servers:
{
    "name": "optional_feature",
    "fail_silent": True,  # Won't break startup
    ...
}

Troubleshooting

Common MCP issues and solutions:
  • Connection refused: Check if MCP server is running and URL is correct
  • Tool not found: Verify tool is exposed by server, check include_tools/exclude_tools
  • Timeout errors: Increase timeout or check network connectivity
  • Permission denied: Verify authentication credentials
  • Environment variable not substituted: Ensure variable is set before running

Next Steps