Skip to main content

mcp-ui Server SDK for Python

Project description

MCP UI Server SDK for Python

A Python SDK for creating MCP UI resources on the server side, enabling rich interactive experiences in MCP applications.

Installation

pip install mcp-ui-server

Quick Start

from mcp_ui_server import create_ui_resource

# Create an HTML resource
resource = create_ui_resource({
    "uri": "ui://my-component",
    "content": {
        "type": "rawHtml",
        "htmlString": "<h1>Hello MCP UI!</h1>"
    },
    "encoding": "text"
})

# Use in MCP tool result
tool_result = {
    "content": [resource.to_dict()]
}

Features

Resource Types

The SDK supports three main content types:

1. Raw HTML

Direct HTML content for embedding in the UI:

html_resource = create_ui_resource({
    "uri": "ui://html-example",
    "content": {
        "type": "rawHtml", 
        "htmlString": "<div><h1>Dynamic Content</h1><p>Generated server-side</p></div>"
    },
    "encoding": "text"  # or "blob" for base64 encoding
})

2. External URLs

Embed external websites via iframe:

url_resource = create_ui_resource({
    "uri": "ui://external-site",
    "content": {
        "type": "externalUrl",
        "iframeUrl": "https://example.com"
    },
    "encoding": "text"
})

3. Remote DOM Components

Interactive components using React or Web Components:

# React component
react_resource = create_ui_resource({
    "uri": "ui://react-component",
    "content": {
        "type": "remoteDom",
        "script": """
            function WeatherWidget({ location }) {
                return (
                    <div>
                        <h3>Weather for {location}</h3>
                        <p>Temperature: 72°F</p>
                    </div>
                );
            }
        """,
        "framework": "react"
    },
    "encoding": "text"
})

# Web Components
wc_resource = create_ui_resource({
    "uri": "ui://web-component", 
    "content": {
        "type": "remoteDom",
        "script": """
            class StatusIndicator extends HTMLElement {
                connectedCallback() {
                    this.innerHTML = `
                        <div style="color: green;">
                            ✅ System Online
                        </div>
                    `;
                }
            }
            customElements.define('status-indicator', StatusIndicator);
        """,
        "framework": "webcomponents"
    },
    "encoding": "blob"
})

Encoding Options

Choose between text and blob encoding:

  • text: Direct string content (recommended for development)
  • blob: Base64-encoded content (recommended for production)
# Text encoding - content stored as plain text
text_resource = create_ui_resource({
    "uri": "ui://text-example",
    "content": {"type": "rawHtml", "htmlString": "<p>Text content</p>"},
    "encoding": "text"
})

# Blob encoding - content base64 encoded
blob_resource = create_ui_resource({
    "uri": "ui://blob-example", 
    "content": {"type": "rawHtml", "htmlString": "<p>Blob content</p>"},
    "encoding": "blob"
})

UI Metadata

Enhance resources with metadata for client-side handling. The SDK automatically prefixes UI-specific metadata with mcpui.dev/ui- to distinguish it from custom metadata.

Preferred Frame Size

Specify preferred dimensions for UI rendering:

resource = create_ui_resource({
    "uri": "ui://chart",
    "content": {
        "type": "externalUrl",
        "iframeUrl": "https://charts.example.com/widget"
    },
    "encoding": "text",
    "uiMetadata": {
        "preferred-frame-size": [800, 600]  # width, height in pixels or css units
    }
})

Initial Render Data

Provide data to components at initialization:

resource = create_ui_resource({
    "uri": "ui://dashboard",
    "content": {
        "type": "remoteDom",
        "script": """
            function Dashboard({ theme, userId }) {
                // Component receives initial data
                return <div>Dashboard for user {userId}</div>;
            }
        """,
        "framework": "react"
    },
    "encoding": "text",
    "uiMetadata": {
        "initial-render-data": {
            "theme": "dark",
            "userId": "123"
        }
    }
})

Multiple Metadata Fields

Combine multiple metadata fields:

resource = create_ui_resource({
    "uri": "ui://data-viz",
    "content": {
        "type": "rawHtml",
        "htmlString": "<canvas id='chart'></canvas>"
    },
    "encoding": "text",
    "uiMetadata": {
        "preferred-frame-size": ["800px", "600px"],
        "initial-render-data": {
            "chartType": "bar",
            "dataSet": "quarterly-sales"
        }
    }
})

Custom Metadata

Add custom metadata alongside UI metadata:

resource = create_ui_resource({
    "uri": "ui://custom-widget",
    "content": {
        "type": "rawHtml",
        "htmlString": "<div>Widget</div>"
    },
    "encoding": "text",
    "uiMetadata": {
        "preferred-frame-size": [640, 480]
    },
    "metadata": {
        "customKey": "customValue",
        "version": "1.0.0"
    }
})

# Result includes both prefixed UI metadata and custom metadata:
# {
#   "resource": {
#     "meta": {
#       "mcpui.dev/ui-preferred-frame-size": [640, 480],
#       "customKey": "customValue",
#       "version": "1.0.0"
#     }
#   }
# }

UI Actions

Create action results for user interactions:

from mcp_ui_server import (
    ui_action_result_tool_call,
    ui_action_result_prompt,
    ui_action_result_link,
    ui_action_result_intent,
    ui_action_result_notification
)

# Tool execution
tool_action = ui_action_result_tool_call("search_database", {
    "query": "user input",
    "limit": 10
})

# User prompt
prompt_action = ui_action_result_prompt("Enter search query:")

# External link
link_action = ui_action_result_link("https://docs.example.com")

# Intent trigger
intent_action = ui_action_result_intent("show_details", {
    "item_id": "123"
})

# Notification
notify_action = ui_action_result_notification("Search completed!")

Advanced Usage

MCP Integration

Convert UI resources for MCP tool results:

from mcp_ui_server.utils import create_mcp_tool_result_content

# Create resource
resource = create_ui_resource({...})

# Convert to MCP format
mcp_content = create_mcp_tool_result_content(resource)

# Use in tool result
return {
    "content": [mcp_content],
    "isError": False
}

HTML Enhancement

Automatically enhance HTML with communication capabilities:

from mcp_ui_server.utils import wrap_html_with_communication

# Basic HTML
html = "<div>My content</div>"

# Enhanced with MCP UI communication
enhanced_html = wrap_html_with_communication(html)

# Use in resource
resource = create_ui_resource({
    "uri": "ui://enhanced-html",
    "content": {"type": "rawHtml", "htmlString": enhanced_html},
    "encoding": "text"
})

Error Handling

The SDK provides specific exception types:

from mcp_ui_server.exceptions import (
    MCPUIServerError,
    InvalidURIError,
    InvalidContentError,
    EncodingError
)

try:
    resource = create_ui_resource({
        "uri": "invalid://test",  # Must start with ui://
        "content": {"type": "rawHtml", "htmlString": "<p>Test</p>"},
        "encoding": "text"
    })
except InvalidURIError as e:
    print(f"URI validation failed: {e}")
except InvalidContentError as e:
    print(f"Content validation failed: {e}")
except MCPUIServerError as e:
    print(f"General SDK error: {e}")

API Reference

Core Functions

create_ui_resource(options: CreateUIResourceOptions) -> UIResource

Creates a UI resource from the given options.

Parameters:

  • options: Configuration dictionary with uri, content, and encoding

Returns:

  • UIResource instance ready for use in MCP tool results

Action Result Functions

  • ui_action_result_tool_call(tool_name: str, params: dict) -> UIActionResultToolCall
  • ui_action_result_prompt(prompt: str) -> UIActionResultPrompt
  • ui_action_result_link(url: str) -> UIActionResultLink
  • ui_action_result_intent(intent: str, params: dict) -> UIActionResultIntent
  • ui_action_result_notification(message: str) -> UIActionResultNotification

Types

CreateUIResourceOptions

{
    "uri": str,  # Must start with "ui://"
    "content": Union[RawHtmlPayload, ExternalUrlPayload, RemoteDomPayload],
    "encoding": Literal["text", "blob"],
    "uiMetadata": Optional[dict[str, Any]],  # UI-specific metadata (auto-prefixed)
    "metadata": Optional[dict[str, Any]]     # Custom metadata
}

Content Payloads

# Raw HTML
{
    "type": "rawHtml",
    "htmlString": str
}

# External URL
{
    "type": "externalUrl", 
    "iframeUrl": str
}

# Remote DOM
{
    "type": "remoteDom",
    "script": str,
    "framework": Literal["react", "webcomponents"]
}

Examples

See the examples/ directory for complete usage examples:

  • basic_server_usage.py: Basic resource creation and action results
  • advanced_features.py: Advanced patterns and integrations
  • mcp_tool_integration.py: Complete MCP tool implementation

Development

Setup

# Install development dependencies
pip install -e ".[dev]"

# Run tests
pytest

# Run linting
ruff check .
black .

# Type checking
mypy src/

Project Structure

src/mcp_ui_server/
├── __init__.py          # Main exports
├── types.py             # Type definitions
├── core.py              # Core functionality
├── utils.py             # Utility functions
└── exceptions.py        # Custom exceptions

License

Apache 2.0

Contributing

See CONTRIBUTING.md for contribution guidelines.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

mcp_ui_server-1.0.0.tar.gz (78.4 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

mcp_ui_server-1.0.0-py3-none-any.whl (11.5 kB view details)

Uploaded Python 3

File details

Details for the file mcp_ui_server-1.0.0.tar.gz.

File metadata

  • Download URL: mcp_ui_server-1.0.0.tar.gz
  • Upload date:
  • Size: 78.4 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.2.0 CPython/3.11.14

File hashes

Hashes for mcp_ui_server-1.0.0.tar.gz
Algorithm Hash digest
SHA256 5ab8f17b93bf794966af7c35e9a575e4f21a9ba2bab3d316cfc107a15f88a3c9
MD5 c29f1251c3bcefd905b91a0117d4e8c9
BLAKE2b-256 f7ed80b21fb515be72baa7fbb55326ee36bad55aa3080519827431599b003989

See more details on using hashes here.

File details

Details for the file mcp_ui_server-1.0.0-py3-none-any.whl.

File metadata

  • Download URL: mcp_ui_server-1.0.0-py3-none-any.whl
  • Upload date:
  • Size: 11.5 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.2.0 CPython/3.11.14

File hashes

Hashes for mcp_ui_server-1.0.0-py3-none-any.whl
Algorithm Hash digest
SHA256 85f53b2e4300fbd175f1fbb7c40f2566b1f4a4ad03a1f33647867c82a3159dcc
MD5 cadaa0309c9477f6b237751c420cc003
BLAKE2b-256 4b8a4c1b2b5708e2f8bf3f3d2ebc130f5bb2a1805cd648b6eda8e5e4bdc039bc

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page