Skip to main content
Glama
ClickHouse

mcp-clickhouse

Official
by ClickHouse

ClickHouse MCP Server

PyPI - Version

An MCP server for ClickHouse.

Features

ClickHouse Tools

  • run_query

    • Execute SQL queries on your ClickHouse cluster.

    • Input: query (string): The SQL query to execute.

    • Queries run in read-only mode by default (CLICKHOUSE_ALLOW_WRITE_ACCESS=false), but writes can be enabled explicitly if needed.

  • list_databases

    • List all databases on your ClickHouse cluster.

  • list_tables

    • List tables in a database with pagination.

    • Required input: database (string).

    • Optional inputs:

      • like / not_like (string): Apply LIKE or NOT LIKE filters to table names.

      • page_token (string): Token returned by a previous call for fetching the next page.

      • page_size (int, default 50): Number of tables returned per page.

      • include_detailed_columns (bool, default true): When false, omits column metadata for lighter responses while keeping the full create_table_query.

    • Response shape:

      • tables: Array of table objects for the current page.

      • next_page_token: Pass this value back to fetch the next page, or null when there are no more tables.

      • total_tables: Total count of tables that match the supplied filters.

chDB Tools

  • run_chdb_select_query

    • Execute SQL queries using chDB's embedded ClickHouse engine.

    • Input: query (string): The SQL query to execute.

    • Query data directly from various sources (files, URLs, databases) without ETL processes.

    • Requires the optional chdb extra: pip install 'mcp-clickhouse[chdb]'

Health Check Endpoint

When running with HTTP or SSE transport, a health check endpoint is available at /health. This endpoint:

  • Returns 200 OK with the ClickHouse version if the server is healthy and can connect to ClickHouse

  • Returns 503 Service Unavailable if the server cannot connect to ClickHouse

Example:

curl http://localhost:8000/health
# Response: OK - Connected to ClickHouse 24.3.1

Related MCP server: ClickHouse MCP Server

Security

Authentication for HTTP/SSE Transports

When using HTTP or SSE transport, authentication is required by default. The stdio transport (default) does not require authentication as it only communicates via standard input/output.

Setting Up Authentication

  1. Generate a secure token (can be any random string):

    # Using uuidgen (macOS/Linux)
    uuidgen
    
    # Using openssl
    openssl rand -hex 32
  2. Configure the server with the token:

    export CLICKHOUSE_MCP_AUTH_TOKEN="your-generated-token"
  3. Configure your MCP client to include the token in requests:

    For Claude Desktop with HTTP/SSE transport:

    {
      "mcpServers": {
        "mcp-clickhouse": {
          "url": "http://127.0.0.1:8000",
          "headers": {
            "Authorization": "Bearer your-generated-token"
          }
        }
      }
    }

    For command-line tools:

    curl -H "Authorization: Bearer your-generated-token" http://localhost:8000/health

Development Mode (Disabling Authentication)

For local development and testing only, you can disable authentication by setting:

export CLICKHOUSE_MCP_AUTH_DISABLED=true

WARNING: Only use this for local development. Do not disable authentication when the server is exposed to any network.

Configuration

This MCP server supports both ClickHouse and chDB. You can enable either or both depending on your needs.

  1. Open the Claude Desktop configuration file located at:

    • On macOS: ~/Library/Application Support/Claude/claude_desktop_config.json

    • On Windows: %APPDATA%/Claude/claude_desktop_config.json

  2. Add the following:

{
  "mcpServers": {
    "mcp-clickhouse": {
      "command": "uv",
      "args": [
        "run",
        "--with",
        "mcp-clickhouse",
        "--python",
        "3.10",
        "mcp-clickhouse"
      ],
      "env": {
        "CLICKHOUSE_HOST": "<clickhouse-host>",
        "CLICKHOUSE_PORT": "<clickhouse-port>",
        "CLICKHOUSE_USER": "<clickhouse-user>",
        "CLICKHOUSE_PASSWORD": "<clickhouse-password>",
        "CLICKHOUSE_ROLE": "<clickhouse-role>",
        "CLICKHOUSE_SECURE": "true",
        "CLICKHOUSE_VERIFY": "true",
        "CLICKHOUSE_CONNECT_TIMEOUT": "30",
        "CLICKHOUSE_SEND_RECEIVE_TIMEOUT": "30"
      }
    }
  }
}

Update the environment variables to point to your own ClickHouse service.

Or, if you'd like to try it out with the ClickHouse SQL Playground, you can use the following config:

{
  "mcpServers": {
    "mcp-clickhouse": {
      "command": "uv",
      "args": [
        "run",
        "--with",
        "mcp-clickhouse",
        "--python",
        "3.10",
        "mcp-clickhouse"
      ],
      "env": {
        "CLICKHOUSE_HOST": "sql-clickhouse.clickhouse.com",
        "CLICKHOUSE_PORT": "8443",
        "CLICKHOUSE_USER": "demo",
        "CLICKHOUSE_PASSWORD": "",
        "CLICKHOUSE_SECURE": "true",
        "CLICKHOUSE_VERIFY": "true",
        "CLICKHOUSE_CONNECT_TIMEOUT": "30",
        "CLICKHOUSE_SEND_RECEIVE_TIMEOUT": "30"
      }
    }
  }
}

For chDB (embedded ClickHouse engine), add the following configuration:

{
  "mcpServers": {
    "mcp-clickhouse": {
      "command": "uv",
      "args": [
        "run",
        "--with",
        "mcp-clickhouse[chdb]",
        "--python",
        "3.10",
        "mcp-clickhouse"
      ],
      "env": {
        "CHDB_ENABLED": "true",
        "CLICKHOUSE_ENABLED": "false",
        "CHDB_DATA_PATH": "/path/to/chdb/data"
      }
    }
  }
}

You can also enable both ClickHouse and chDB simultaneously:

{
  "mcpServers": {
    "mcp-clickhouse": {
      "command": "uv",
      "args": [
        "run",
        "--with",
        "mcp-clickhouse[chdb]",
        "--python",
        "3.10",
        "mcp-clickhouse"
      ],
      "env": {
        "CLICKHOUSE_HOST": "<clickhouse-host>",
        "CLICKHOUSE_PORT": "<clickhouse-port>",
        "CLICKHOUSE_USER": "<clickhouse-user>",
        "CLICKHOUSE_PASSWORD": "<clickhouse-password>",
        "CLICKHOUSE_SECURE": "true",
        "CLICKHOUSE_VERIFY": "true",
        "CLICKHOUSE_CONNECT_TIMEOUT": "30",
        "CLICKHOUSE_SEND_RECEIVE_TIMEOUT": "30",
        "CHDB_ENABLED": "true",
        "CHDB_DATA_PATH": "/path/to/chdb/data"
      }
    }
  }
}
  1. Locate the command entry for uv and replace it with the absolute path to the uv executable. This ensures that the correct version of uv is used when starting the server. On a mac, you can find this path using which uv.

  2. Restart Claude Desktop to apply the changes.

Optional Write Access

By default, this MCP enforces read-only queries so that accidental mutations cannot happen during exploration. To allow DDL or INSERT/UPDATE statements, set the CLICKHOUSE_ALLOW_WRITE_ACCESS environment variable to true. The server keeps enforcing read-only mode if the ClickHouse instance itself disallows writes.

Destructive Operation Protection

Even when write access is enabled (CLICKHOUSE_ALLOW_WRITE_ACCESS=true), destructive operations (DROP TABLE, DROP DATABASE, DROP VIEW, DROP DICTIONARY, TRUNCATE TABLE) require an additional opt-in flag for safety. This prevents accidental data deletion during AI exploration.

To enable destructive operations, set both flags:

"env": {
  "CLICKHOUSE_ALLOW_WRITE_ACCESS": "true",
  "CLICKHOUSE_ALLOW_DROP": "true"
}

This two-tier approach ensures that accidental drops are very difficult:

  • Write operations (INSERT, UPDATE, CREATE) require CLICKHOUSE_ALLOW_WRITE_ACCESS=true

  • Destructive operations (DROP, TRUNCATE) additionally require CLICKHOUSE_ALLOW_DROP=true

Running Without uv (Using System Python)

If you prefer to use the system Python installation instead of uv, you can install the package from PyPI and run it directly:

  1. Install the package using pip:

    python3 -m pip install mcp-clickhouse

    To install chDB support as well:

    python3 -m pip install 'mcp-clickhouse[chdb]'

    To upgrade to the latest version:

    python3 -m pip install --upgrade mcp-clickhouse
  2. Update your Claude Desktop configuration to use Python directly:

{
  "mcpServers": {
    "mcp-clickhouse": {
      "command": "python3",
      "args": [
        "-m",
        "mcp_clickhouse.main"
      ],
      "env": {
        "CLICKHOUSE_HOST": "<clickhouse-host>",
        "CLICKHOUSE_PORT": "<clickhouse-port>",
        "CLICKHOUSE_USER": "<clickhouse-user>",
        "CLICKHOUSE_PASSWORD": "<clickhouse-password>",
        "CLICKHOUSE_SECURE": "true",
        "CLICKHOUSE_VERIFY": "true",
        "CLICKHOUSE_CONNECT_TIMEOUT": "30",
        "CLICKHOUSE_SEND_RECEIVE_TIMEOUT": "30"
      }
    }
  }
}

Alternatively, you can use the installed script directly:

{
  "mcpServers": {
    "mcp-clickhouse": {
      "command": "mcp-clickhouse",
      "env": {
        "CLICKHOUSE_HOST": "<clickhouse-host>",
        "CLICKHOUSE_PORT": "<clickhouse-port>",
        "CLICKHOUSE_USER": "<clickhouse-user>",
        "CLICKHOUSE_PASSWORD": "<clickhouse-password>",
        "CLICKHOUSE_SECURE": "true",
        "CLICKHOUSE_VERIFY": "true",
        "CLICKHOUSE_CONNECT_TIMEOUT": "30",
        "CLICKHOUSE_SEND_RECEIVE_TIMEOUT": "30"
      }
    }
  }
}

Note: Make sure to use the full path to the Python executable or the mcp-clickhouse script if they are not in your system PATH. You can find the paths using:

  • which python3 for the Python executable

  • which mcp-clickhouse for the installed script

Custom Middleware

You can add custom middleware to the MCP server without modifying the source code. FastMCP provides a middleware system that allows you to intercept and process MCP protocol messages (tool calls, resource reads, prompts, etc.).

How to Use

  1. Create a Python module with middleware classes extending Middleware and a setup_middleware(mcp) function:

# my_middleware.py
import logging
from fastmcp.server.middleware import Middleware, MiddlewareContext, CallNext

logger = logging.getLogger("my-middleware")

class LoggingMiddleware(Middleware):
    """Log all tool calls."""
    
    async def on_call_tool(self, context: MiddlewareContext, call_next: CallNext):
        tool_name = context.message.name if hasattr(context.message, 'name') else 'unknown'
        logger.info(f"Calling tool: {tool_name}")
        result = await call_next(context)
        logger.info(f"Tool {tool_name} completed")
        return result

def setup_middleware(mcp):
    """Register middleware with the MCP server."""
    mcp.add_middleware(LoggingMiddleware())
  1. Set the MCP_MIDDLEWARE_MODULE environment variable to the module name (without .py extension):

{
  "mcpServers": {
    "mcp-clickhouse": {
      "command": "uv",
      "args": ["run", "--with", "mcp-clickhouse", "--python", "3.10", "mcp-clickhouse"],
      "env": {
        "CLICKHOUSE_HOST": "<clickhouse-host>",
        "CLICKHOUSE_USER": "<clickhouse-user>",
        "CLICKHOUSE_PASSWORD": "<clickhouse-password>",
        "MCP_MIDDLEWARE_MODULE": "my_middleware"
      }
    }
  }
}
  1. Ensure your middleware module is in Python's import path (e.g., in the same directory where the MCP server runs, or installed as a package).

Example Middleware

An example middleware module is provided in example_middleware.py showing common patterns:

  • Logging all MCP requests

  • Logging tool calls specifically

  • Measuring request processing time

To use the example:

"env": {
  "MCP_MIDDLEWARE_MODULE": "example_middleware"
}

Middleware Capabilities

The Middleware base class provides hooks for different MCP operations:

  • on_message(context, call_next) - Called for all messages

  • on_request(context, call_next) - Called for all requests

  • on_notification(context, call_next) - Called for all notifications

  • on_call_tool(context, call_next) - Called when a tool is executed

  • on_read_resource(context, call_next) - Called when a resource is read

  • on_get_prompt(context, call_next) - Called when a prompt is retrieved

  • on_list_tools(context, call_next) - Called when listing tools

  • on_list_resources(context, call_next) - Called when listing resources

  • on_list_resource_templates(context, call_next) - Called when listing resource templates

  • on_list_prompts(context, call_next) - Called when listing prompts

Each hook receives a MiddlewareContext object containing the message and metadata, and a call_next function to continue the pipeline.

Dynamic Client Configuration via Context State

Middleware can override ClickHouse client configuration on a per-request basis using the CLIENT_CONFIG_OVERRIDES_KEY context state key. The server merges these overrides with the base configuration from environment variables.

from fastmcp.server.dependencies import get_context
from mcp_clickhouse.mcp_server import CLIENT_CONFIG_OVERRIDES_KEY

ctx = get_context()
ctx.set_state(CLIENT_CONFIG_OVERRIDES_KEY, {
    "connect_timeout": 60,
    "send_receive_timeout": 120
})

This enables advanced use cases like dynamic timeout adjustments, tenant-specific routing, or per-user connection settings.

Development

  1. In test-services directory run docker compose up -d to start the ClickHouse cluster.

  2. Add the following variables to a .env file in the root of the repository.

Note: The use of the default user in this context is intended solely for local development purposes.

CLICKHOUSE_HOST=localhost
CLICKHOUSE_PORT=8123
CLICKHOUSE_USER=default
CLICKHOUSE_PASSWORD=clickhouse
  1. Run uv sync to install the dependencies. To install uv follow the instructions here. Then do source .venv/bin/activate.

  2. For easy testing with the MCP Inspector, run fastmcp dev mcp_clickhouse/mcp_server.py to start the MCP server.

  3. To test with HTTP transport and the health check endpoint:

    # For development, disable authentication
    CLICKHOUSE_MCP_SERVER_TRANSPORT=http CLICKHOUSE_MCP_AUTH_DISABLED=true python -m mcp_clickhouse.main
    
    # Or with authentication (generate a token first)
    CLICKHOUSE_MCP_SERVER_TRANSPORT=http CLICKHOUSE_MCP_AUTH_TOKEN="your-token" python -m mcp_clickhouse.main
    
    # Then in another terminal:
    # Without auth (if disabled):
    curl http://localhost:8000/health
    
    # With auth:
    curl -H "Authorization: Bearer your-token" http://localhost:8000/health

Environment Variables

The following environment variables are used to configure the ClickHouse and chDB connections:

ClickHouse Variables

Required Variables
  • CLICKHOUSE_HOST: The hostname of your ClickHouse server

  • CLICKHOUSE_USER: The username for authentication

  • CLICKHOUSE_PASSWORD: The password for authentication

CAUTION

It is important to treat your MCP database user as you would any external client connecting to your database, granting only the minimum necessary privileges required for its operation. The use of default or administrative users should be strictly avoided at all times.

Optional Variables
  • CLICKHOUSE_PORT: The port number of your ClickHouse server

    • Default: 8443 if HTTPS is enabled, 8123 if disabled

    • Usually doesn't need to be set unless using a non-standard port

  • CLICKHOUSE_ROLE: The role to use for authentication

    • Default: None

    • Set this if your user requires a specific role

  • CLICKHOUSE_SECURE: Enable/disable HTTPS connection

    • Default: "true"

    • Set to "false" for non-secure connections

  • CLICKHOUSE_VERIFY: Enable/disable SSL certificate verification

    • Default: "true"

    • Set to "false" to disable certificate verification (not recommended for production)

    • TLS certificates: The package uses your operating system trust store for TLS certificate verification via truststore. We call truststore.inject_into_ssl() at startup to ensure proper certificate handling. Python’s default SSL behavior is used as a fallback only if an unexpected error occurs.

  • CLICKHOUSE_SERVER_HOST_NAME: Server hostname for SNI override and certificate validation

    • Default: None (uses the connection hostname)

    • This is useful when connecting through proxies or load balancers where the certificate hostname differs from the connection hostname. When set, this hostname will be used for both SNI (Server Name Indication) during the TLS handshake and for certificate hostname validation.

  • CLICKHOUSE_CONNECT_TIMEOUT: Connection timeout in seconds

    • Default: "30"

    • Increase this value if you experience connection timeouts

  • CLICKHOUSE_SEND_RECEIVE_TIMEOUT: Send/receive timeout in seconds

    • Default: "300"

    • Increase this value for long-running queries

  • CLICKHOUSE_DATABASE: Default database to use

    • Default: None (uses server default)

    • Set this to automatically connect to a specific database

  • CLICKHOUSE_MCP_SERVER_TRANSPORT: Sets the transport method for the MCP server.

    • Default: "stdio"

    • Valid options: "stdio", "http", "sse". This is useful for local development with tools like MCP Inspector.

  • CLICKHOUSE_MCP_BIND_HOST: Host to bind the MCP server to when using HTTP or SSE transport

    • Default: "127.0.0.1"

    • Set to "0.0.0.0" to bind to all network interfaces (useful for Docker or remote access)

    • Only used when transport is "http" or "sse"

  • CLICKHOUSE_MCP_BIND_PORT: Port to bind the MCP server to when using HTTP or SSE transport

    • Default: "8000"

    • Only used when transport is "http" or "sse"

  • CLICKHOUSE_MCP_QUERY_TIMEOUT: Timeout in seconds for SELECT tools

    • Default: "30"

    • Increase this if you see Query timed out after ... errors for heavy queries

  • CLICKHOUSE_MCP_AUTH_TOKEN: Authentication token for HTTP/SSE transports

    • Default: None

    • Required when using HTTP or SSE transport (unless CLICKHOUSE_MCP_AUTH_DISABLED=true)

    • Generate using uuidgen or openssl rand -hex 32

    • Clients must send this token in the Authorization: Bearer <token> header

  • CLICKHOUSE_MCP_AUTH_DISABLED: Disable authentication for HTTP/SSE transports

    • Default: "false" (authentication is enabled)

    • Set to "true" to disable authentication for local development/testing only

    • WARNING: Only use for local development. Do not disable when exposed to networks

  • CLICKHOUSE_ENABLED: Enable/disable ClickHouse functionality

    • Default: "true"

    • Set to "false" to disable ClickHouse tools when using chDB only

  • CLICKHOUSE_ALLOW_WRITE_ACCESS: Allow write operations (DDL and DML)

    • Default: "false"

    • Set to "true" to allow DDL (CREATE, ALTER, DROP) and DML (INSERT, UPDATE, DELETE) operations

    • When disabled (default), queries run with readonly=1 setting to prevent data modifications

  • CLICKHOUSE_ALLOW_DROP: Allow destructive operations (DROP TABLE, DROP DATABASE, DROP VIEW, DROP DICTIONARY, TRUNCATE TABLE)

    • Default: "false"

    • Only takes effect when CLICKHOUSE_ALLOW_WRITE_ACCESS=true is also set

    • Set to "true" to explicitly allow destructive DROP and TRUNCATE operations

    • This is a safety feature to prevent accidental data deletion during AI exploration

Middleware Variables

  • MCP_MIDDLEWARE_MODULE: Python module name containing custom middleware to inject into the MCP server

    • Default: None (no middleware loaded)

    • Set to the module name (without .py extension) of your middleware module

    • The module must provide a setup_middleware(mcp) function

    • See Custom Middleware for details and examples

chDB Variables

  • CHDB_ENABLED: Enable/disable chDB functionality

    • Default: "false"

    • Set to "true" to enable chDB tools

    • Requires installing the optional extra: mcp-clickhouse[chdb]

  • CHDB_DATA_PATH: The path to the chDB data directory

    • Default: ":memory:" (in-memory database)

    • Use :memory: for in-memory database

    • Use a file path for persistent storage (e.g., /path/to/chdb/data)

Example Configurations

For local development with Docker:

# Required variables
CLICKHOUSE_HOST=localhost
CLICKHOUSE_USER=default
CLICKHOUSE_PASSWORD=clickhouse

# Optional: Override defaults for local development
CLICKHOUSE_SECURE=false  # Uses port 8123 automatically
CLICKHOUSE_VERIFY=false

For ClickHouse Cloud:

# Required variables
CLICKHOUSE_HOST=your-instance.clickhouse.cloud
CLICKHOUSE_USER=default
CLICKHOUSE_PASSWORD=your-password

# Optional: These use secure defaults
# CLICKHOUSE_SECURE=true  # Uses port 8443 automatically
# CLICKHOUSE_DATABASE=your_database

For ClickHouse SQL Playground:

CLICKHOUSE_HOST=sql-clickhouse.clickhouse.com
CLICKHOUSE_USER=demo
CLICKHOUSE_PASSWORD=
# Uses secure defaults (HTTPS on port 8443)

For chDB only (in-memory):

# chDB configuration
CHDB_ENABLED=true
CLICKHOUSE_ENABLED=false
# CHDB_DATA_PATH defaults to :memory:

For chDB with persistent storage:

# chDB configuration
CHDB_ENABLED=true
CLICKHOUSE_ENABLED=false
CHDB_DATA_PATH=/path/to/chdb/data

For MCP Inspector or remote access with HTTP transport:

CLICKHOUSE_HOST=localhost
CLICKHOUSE_USER=default
CLICKHOUSE_PASSWORD=clickhouse
CLICKHOUSE_MCP_SERVER_TRANSPORT=http
CLICKHOUSE_MCP_BIND_HOST=0.0.0.0  # Bind to all interfaces
CLICKHOUSE_MCP_BIND_PORT=4200  # Custom port (default: 8000)
CLICKHOUSE_MCP_AUTH_TOKEN=your-generated-token  # Required for HTTP/SSE

For local development with HTTP transport (authentication disabled):

CLICKHOUSE_HOST=localhost
CLICKHOUSE_USER=default
CLICKHOUSE_PASSWORD=clickhouse
CLICKHOUSE_MCP_SERVER_TRANSPORT=http
CLICKHOUSE_MCP_AUTH_DISABLED=true  # Only for local development!

When using HTTP transport, the server will run on the configured port (default 8000). For example, with the above configuration:

  • MCP endpoint: http://localhost:4200/mcp

  • Health check: http://localhost:4200/health

You can set these variables in your environment, in a .env file, or in the Claude Desktop configuration:

{
  "mcpServers": {
    "mcp-clickhouse": {
      "command": "uv",
      "args": [
        "run",
        "--with",
        "mcp-clickhouse",
        "--python",
        "3.10",
        "mcp-clickhouse"
      ],
      "env": {
        "CLICKHOUSE_HOST": "<clickhouse-host>",
        "CLICKHOUSE_USER": "<clickhouse-user>",
        "CLICKHOUSE_PASSWORD": "<clickhouse-password>",
        "CLICKHOUSE_DATABASE": "<optional-database>",
        "CLICKHOUSE_MCP_SERVER_TRANSPORT": "stdio",
        "CLICKHOUSE_MCP_BIND_HOST": "127.0.0.1",
        "CLICKHOUSE_MCP_BIND_PORT": "8000"
      }
    }
  }
}

Note: The bind host and port settings are only used when transport is set to "http" or "sse".

Running tests

uv sync --all-extras --dev # install dev dependencies
uv run ruff check . # run linting

docker compose up -d test_services # start ClickHouse
uv run pytest -v tests
uv run pytest -v tests/test_tool.py # ClickHouse only
CHDB_ENABLED=true uv run --extra chdb pytest -v tests/test_chdb_tool.py # chDB only

YouTube Overview

YouTube

Available Tools

3 tools
list_databasesList DatabasesA

List available ClickHouse databases

NameRequiredDescriptionDefault

No parameters

Output Schema

NameRequiredDescription
resultYes

TDQS

A3.6/5.0
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

No annotations are provided, so the description carries the full burden of disclosing behavior. It merely says 'list available ClickHouse databases' without indicating that it is a read-only operation, whether it requires specific permissions, or what the return structure looks like (though an output schema exists). The description adds no behavioral context beyond the obvious intent.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is a single, concise sentence that directly states the function with no filler or redundancy. It is appropriately sized for a simple tool with no parameters.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's simplicity, zero parameters, and presence of an output schema, the description is sufficient for an agent to understand its core function. The lack of explicit usage alternatives is a minor gap, but for a basic listing tool, the description covers the essentials.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The tool has zero parameters, and the schema is empty, so there is nothing for the description to explain about parameters. According to the rubric, a baseline of 4 is appropriate when no parameters exist, and the description does not need to add anything.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the verb 'list' and the resource 'available ClickHouse databases', making the tool's purpose unambiguous. It distinguishes itself from siblings like list_tables (tables) and run_query (queries) by explicitly targeting databases.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives no explicit guidance on when to use this tool versus the sibling tools. While the purpose is self-evident, there is no mention of scenarios where listing databases is preferred or when a different tool (e.g., list_tables) would be more appropriate. This leaves the agent to infer usage context.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

list_tablesList TablesA

List available ClickHouse tables in a database, including schema, comment, row count, and column count.

Integers outside [-9007199254740991, 9007199254740991] in table metadata are returned as decimal strings. Pagination tokens are single-use and retained for up to one hour.

NameRequiredDescriptionDefault
likeNoOptional LIKE pattern to filter table names
databaseYesThe database to list tables from
not_likeNoOptional NOT LIKE pattern to exclude table names
page_sizeNoNumber of tables to return per page (default: 50, must be greater than 0)
page_tokenNoSingle-use token from a previous call, retained for up to one hour
include_detailed_columnsNoWhether to include detailed column metadata (default: True). When False, the columns array will be empty but create_table_query still contains all column information. This reduces payload size for large schemas.

Output Schema

NameRequiredDescription
resultYes

TDQS

A4/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

No annotations are provided, so the description carries the burden of behavioral disclosure. It does disclose two non-obvious behaviors: large integers become decimal strings, and pagination tokens are single-use and retained for one hour. This is meaningful transparency, though it does not address all potential behaviors such as sorting or default pagination size.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is three sentences with no filler. The first sentence states the core purpose and output, and the following two sentences provide essential behavioral quirks. Every sentence earns its place.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool has an output schema made available and 100% parameter coverage, the description does not need to restate return structures or parameter details. It adequately covers the non-obvious behaviors around large integers and pagination tokenshare tokens, making it largely complete for an agent to invoke correctly. It falls short of 5 because it lacks any guidance on when to prefer this over list_databases or run_query.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Parameter descriptions in the schema already cover 100% of parameters, including defaults and semantics. The description adds minor context around pagination token behavior and output metadata, but does not need to compensate for schema gaps. Baseline 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool lists ClickHouse tables in a database and includes specific metadata fields (schema, comment, row count, column count). This distinguishes it from sibling tools list_databases and run_query based on the resource being operated on and the nature of the operation.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies the tool is for discovering table metadata, which contrasts with list_databases and run_query, but it never explicitly states when to use this tool over its siblings. There is no direct mention of alternatives or exclusion conditions.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

run_queryRun QueryA

Execute SQL queries in ClickHouse. Queries run in read-only mode by default. Bind optional params by name with {name:Type} placeholders, such as {name:String} or {vector:Array(Float32)}. Values may be JSON scalars, nulls, or arrays. Pass exact large integers as decimal strings. JSON lists and objects cannot bind to Tuple and Map types. Python percent formatting and $name$ raw binary parameters are not supported. Parameter values stay out of the MCP server's normal SQL log lines, but may appear in errors and backend logs. Set CLICKHOUSE_ALLOW_WRITE_ACCESS=true to allow DDL and DML operations. Set CLICKHOUSE_ALLOW_DROP=true to additionally allow destructive operations (DROP, TRUNCATE, DELETE, UPDATE, REPLACE TABLE/PARTITION, CREATE OR REPLACE, CLEAR COLUMN/INDEX/PROJECTION, DETACH PERMANENTLY). That gate is a best-effort accident guard, not a security boundary. Integers outside [-9007199254740991, 9007199254740991] are returned as decimal strings. Two optional checks also run through this tool. Use DESCRIBE () when you need a query's output columns and types; it inspects the result schema and surfaces analysis errors such as an unknown column, but a query that describes cleanly can still fail at runtime. Consider EXPLAIN ESTIMATE before a SELECT that could be expensive; it returns the estimated parts, rows and marks read from MergeTree family tables, which is not run time and not result size. Neither runs the query body, though analysis can execute scalar subqueries.

NameRequiredDescriptionDefault
queryYes
paramsNo

Output Schema

NameRequiredDescription
resultYes

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

With no annotations provided, the description fully discloses behavioral traits: read-only by default, write/drop gated by environment variables, parameter binding constraints, integer handling as decimal strings, and the best-effort nature of the accident guard (not a security boundary). It even warns about parameter visibility in logs. This is exceptionally transparent.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but every sentence delivers necessary behavioral or usage information. It's logically structured: main purpose, read-only default, parameter details, write-access gates, integer handling, and optional checks. While it could be trimmed slightly, the density of information justifies the length for a complex tool.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity and the presence of an output schema, the description covers all essential aspects: query execution, parameter binding, access control, integer representation, and optional DESCRIBE/EXPLAIN usage. It does not need to detail the return format since an output schema exists. Nothing an agent needs to correctly invoke this tool is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters5/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The schema only defines 'query' and 'params' with no descriptions, so the description carries the entire burden. It thoroughly explains parameter binding syntax ({name:Type}), acceptable value types (scalars, nulls, arrays), limitations (no Tuple/Map binding, no Python formatting), and how to pass large integers as decimal strings. This adds critical meaning far beyond the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Clearly states it executes SQL queries in ClickHouse with a specific verb and resource. It differentiates itself from sibling tools (list_databases, list_tables) by being the general-purpose query executor, and even mentions read-only default and optional write access, making its role unambiguous.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Provides explicit guidance on when to use the tool for general queries, and details when to use DESCRIBE and EXPLAIN ESTIMATE for schema inspection and cost estimation. It does not explicitly say 'use list_databases for listing databases', but that's implied by sibling names and the description's scope. The read-only default and access flags also clarify permissible usage contexts.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Tool Schema Changelog

Recent tool additions, removals, and schema changes observed during successful MCP inspections.

  1. 3 tool updatesv0.7.0
    • Addedlist_databases
    • Addedlist_tables
    • Changedrun_query3 fields changed
      • addedInput schema / additionalProperties
        Added value: +false
      • addedInput schema / properties / params
        Added value: +{
        +  "anyOf": [
        +    {
        +      "additionalProperties": true,
        +      "type": "object"
        +    },
        +    {
        +      "type": "null"
        +    }
        +  ],
        +  "default": null
        +}
      • removedOutput schema / description
        Removed value: -"Generic wrapper for non-object return types."
  2. 2 tool updatesv0.4.1
    • Removedlist_databases
    • Removedlist_tables
  3. 4 tool updatesv0.2.0
    • Changedlist_databases1 field changed
      • changedOutput schema / (root)
        Previous value: -nullNew value: +{
        +  "description": "Generic wrapper for non-object return types.",
        +  "properties": {
        +    "result": {
        +      "type": "string"
        +    }
        +  },
        +  "required": [
        +    "result"
        +  ],
        +  "type": "object",
        +  "x-fastmcp-wrap-result": true
        +}
    • Changedlist_tables5 fields changed
      • removedOutput schema / additionalProperties
        Removed value: -true
      • addedOutput schema / description
        Added value: +"Generic wrapper for non-object return types."
      • addedOutput schema / properties
        Added value: +{
        +  "result": {
        +    "type": "string"
        +  }
        +}
      • addedOutput schema / required
        Added value: +[
        +  "result"
        +]
      • addedOutput schema / x-fastmcp-wrap-result
        Added value: +true
    • Addedrun_query
    • Removedrun_select_query
  4. 3 tool updatesv1.0.0
    • First observedlist_databases
    • First observedlist_tables
    • First observedrun_select_query

TDQS

A4.2/5.0

Scored across 3 tools

Disambiguation5/5

The three tools have clearly distinct purposes: listing databases, listing tables with metadata, and executing SQL queries. There is no realistic ambiguity about which tool an agent should choose for a given operation.

Naming Consistency5/5

All tool names follow a consistent verb_noun snake_case pattern: list_databases, list_tables, and run_query. This makes the tool surface predictable and easy to navigate.

Tool Count5/5

Three tools is a compact but well-scoped set for a database MCP server: discovery of databases, discovery of tables, and execution of SQL. Each tool earns its place and there is no redundancy.

Completeness5/5

The set covers the full workflow of exploring and querying a ClickHouse instance: list databases, inspect table schemas, then run queries. Advanced operations such as EXPLAIN and DESCRIBE are accessible through run_query, with write operations config-gated, so there are no obvious dead ends.

Maintenance

ActivityActive
ResponsivenessSlow

Related MCP Connectors

Related MCP Servers

  • A
    license
    Not graded
    quality
    D
    maintenance
    A Model Context Protocol server that enables Large Language Models to seamlessly interact with ClickHouse databases, supporting resource listing, schema retrieval, and query execution.
    2
    MIT
  • A
    license
    B
    quality
    D
    maintenance
    An MCP server implementation that enables Claude AI to interact with Clickhouse databases. Features include secure database connections, query execution, read-only mode support, and multi-query capabilities.
    2
    34 PyPI
    2
    MIT
  • A
    license
    Not graded
    quality
    C
    maintenance
    Enables interaction with ClickHouse databases via MCP, providing tools to list databases and tables and execute safe SELECT, SHOW, and DESCRIBE queries.
    46 npm
    MIT