vmysql-mcp
A lightweight multi-environment MySQL MCP server providing controlled database access through two tools:
mysql_query(read-only): Execute a singleSELECT,SHOW,DESCRIBE,EXPLAIN, orWITH...SELECTCTE against a named environment. Returns rows, column metadata, row count, elapsed time, and truncation status.mysql_exec(write/DDL): Execute a singleINSERT,UPDATE,DELETE,REPLACE, or DDL statement (if policy permits) against a named environment. Returns affected rows, insert ID, warnings, and elapsed time. Automatically rejected for read-only environments.
Both tools support:
Multi-environment routing via an
envparameter (e.g.,dev,stg,prod_ro)Optional database override (if allowed by policy)
Optional timeout override (default 10s, hard max 30s)
Server-side policy enforcement per environment:
Read-only restrictions, write/DDL permissions, database allowlists
Row limits (default 200, hard max 1000) and timeouts
Multi-statement SQL rejection to prevent injection
DSN injection via environment variables (no secrets in config files)
Provides tools for interacting with MySQL databases across multiple environments, allowing for read-only queries and policy-gated write operations including data manipulation and DDL statements.
Click on "Deploy Server".
Wait a few minutes for the server to deploy. Once ready, it will show a "Started" state.
In the chat, type
@followed by the MCP server name and your instructions, e.g., "@vmysql-mcpfind the 5 most recent orders in the dev environment"
That's it! The server will respond to your query, and you can continue using it as needed.
Here is a step-by-step guide with screenshots.
vmysql-mcp
轻量级多环境 MySQL MCP Server。
A lightweight multi-environment MySQL MCP server.
简介 Overview
vmysql-mcp 是一个基于 stdio 的 MySQL MCP Server,目标不是做一个“大而全”的数据库平台,而是提供一个足够轻、足够稳、足够可控的数据库工具入口。
它当前只暴露两个工具:
mysql_query:只读查询工具 / read-only query toolmysql_exec:受策略约束的执行工具 / policy-gated execution tool
核心设计原则:
多环境通过
env路由,而不是为每个环境暴露一套工具。默认安全收口,尤其是生产环境建议只暴露只读别名。
配置文件只保存非敏感策略,连接串通过环境变量注入。
尽量减少 MCP tool surface,降低 Agent 加载 token 成本。
Related MCP server: MySQL MCP Server
功能特性 Features
使用
stdio传输 / uses stdio transport仅暴露两个工具:
mysql_query、mysql_exec通过环境别名访问多个 MySQL 环境,例如
dev、stg、prod_ro具备服务端策略控制:读写限制、DDL 限制、超时、行数限制、数据库白名单
返回简短文本摘要和结构化 JSON 结果 / short text + structured JSON output
mysql_query支持顶层WITH ... SELECTmysql_exec继续拒绝顶层WITH语句
运行要求 Requirements
Node.js 20+
推荐 MySQL 8.0+
如果你使用已发布 npm 包,不需要自己准备
dist目录如果你使用源码方式接入,需要先执行
npm run build
安装与使用 Installation and Usage
如果你只是使用这个 MCP 给 Agent 自动拉起,推荐走 npm 包模式,而不是先手动 npm run start。
If you only want an MCP client or agent to auto-start this server, prefer the npm package flow instead of manually running npm run start.
方式一:使用已发布 npm 包 Recommended for Agents
发布到 npm 后,推荐通过下面任一方式使用。
前提条件:
你的运行环境已经提供
VMYSQL_CONFIG_PATH你的运行环境已经提供对应环境的
MYSQL_*_DSN
否则,vmysql-mcp 会因为缺少配置文件或连接串而启动失败。
After publishing to npm, this is the recommended path for agent-managed auto-start.
Prerequisites:
VMYSQL_CONFIG_PATHmust point to a valid config file, or the current working directory must already containvmysql.config.jsonRequired
MYSQL_*_DSNenvironment variables must already be available
npx -y vmysql-mcp或者全局安装:
npm install -g vmysql-mcp
vmysql-mcp这类模式最适合 OpenCode、Codex、Claude Code 这类会自动拉起本地 stdio MCP 进程的 Agent。
方式二:本地源码开发 Local Source Development
npm install
npm run build服务端配置 Server Configuration
vmysql-mcp 的运行配置来自一个 JSON 文件,默认读取当前工作目录下的 vmysql.config.json。如果你想指定其他路径,可以通过环境变量 VMYSQL_CONFIG_PATH 覆盖。
vmysql-mcp reads runtime config from a JSON file. By default it uses vmysql.config.json in the current working directory. Override it with VMYSQL_CONFIG_PATH if needed.
示例 vmysql.config.json:
{
"server": {
"name": "vmysql-mcp",
"version": "0.1.0",
"defaultQueryLimit": 200,
"hardMaxRows": 1000,
"defaultTimeoutMs": 10000,
"hardTimeoutMs": 30000,
"maxConnectionsPerEnv": 2,
"logLevel": "info"
},
"environments": {
"dev": {
"dsnEnv": "MYSQL_DEV_DSN",
"defaultDatabase": "app_dev",
"allowedDatabases": ["app_dev"],
"readOnly": false,
"allowWrite": true,
"allowDDL": false,
"maxRows": 500,
"defaultTimeoutMs": 10000
},
"prod_ro": {
"dsnEnv": "MYSQL_PROD_RO_DSN",
"defaultDatabase": "app",
"allowedDatabases": ["app"],
"readOnly": true,
"allowWrite": false,
"allowDDL": false,
"maxRows": 200,
"defaultTimeoutMs": 8000
}
}
}示例环境变量:
export MYSQL_DEV_DSN='mysql://user:password@127.0.0.1:3306/app_dev'
export MYSQL_PROD_RO_DSN='mysql://readonly:password@127.0.0.1:3306/app'注意:
不要把密码直接提交到
vmysql.config.json。配置文件里应该只保留
dsnEnv这样的引用名。如果密码包含
@、:、/等字符,请先做 URL 编码再拼接 DSN。
Do not commit secrets into vmysql.config.json. Store only secret references such as dsnEnv names.
如果你是在本地开发这个项目,或者想手动调试进程启动行为,可以再执行:
If you are developing this project locally or want to debug the server process manually, you can then run:
本地手动启动 Run Locally
npm run start工具说明 Tools
mysql_query
执行单条只读 SQL。
Run one read-only SQL statement.
支持范围:
SELECTSHOWDESCRIBEEXPLAIN顶层
WITH ... SELECT
行为约束:
拒绝多语句 SQL / rejects multi-statement SQL
应用服务端行数限制和超时 / applies server-side row limits and timeout
按环境策略限制数据库访问范围 / enforces database allowlist per environment
mysql_exec
在环境策略允许的前提下执行单条写操作 SQL。
Run one write-capable SQL statement when environment policy allows it.
支持范围:
INSERTUPDATEDELETEREPLACE可选
DDL,前提是环境显式允许
行为约束:
拒绝顶层
WITH语句 / rejects top-levelWITH对只读环境直接拒绝写入 / rejects writes against read-only environments such as
prod_ro
主流 Agent 安装与配置 Agent Setup
下面分成两类:
已发布 npm 包接入方式 / published npm package flow
本地源码调试方式 / local source debugging flow
如果你是正常接入 Agent,优先用 npm 包方式;只有在本地开发或排障时,才需要用 node dist/index.js 这种源码路径方式。
For normal agent integration, prefer the npm package flow. Use direct node dist/index.js only for local development or debugging.
下面的例子统一假设:
项目目录 / project path:
/absolute/path/to/vmysql-mcp构建后 CLI 入口 / built CLI entry:
/absolute/path/to/vmysql-mcp/dist/cli.js配置文件路径 / config path:
/absolute/path/to/vmysql-mcp/vmysql.config.json
请使用绝对路径。相对路径是最容易制造“我这里能跑、别人那里不行”假象的坑。
Use absolute paths. Relative paths are a common source of fake “works on my machine” setups.
OpenCode
OpenCode 使用 opencode.json 或 opencode.jsonc。
推荐配置(npm 包方式)/ recommended package-based example:
{
"$schema": "https://opencode.ai/config.json",
"mcp": {
"vmysql": {
"type": "local",
"enabled": true,
"command": [
"npx",
"-y",
"vmysql-mcp"
],
"environment": {
"VMYSQL_CONFIG_PATH": "/absolute/path/to/vmysql-mcp/vmysql.config.json",
"MYSQL_DEV_DSN": "mysql://user:password@127.0.0.1:3306/app_dev",
"MYSQL_PROD_RO_DSN": "mysql://readonly:password@127.0.0.1:3306/app"
},
"timeout": 10000
}
}
}本地源码调试示例 / local source debugging example:
{
"$schema": "https://opencode.ai/config.json",
"mcp": {
"vmysql": {
"type": "local",
"enabled": true,
"command": [
"node",
"/absolute/path/to/vmysql-mcp/dist/cli.js"
],
"environment": {
"VMYSQL_CONFIG_PATH": "/absolute/path/to/vmysql-mcp/vmysql.config.json",
"MYSQL_DEV_DSN": "mysql://user:password@127.0.0.1:3306/app_dev",
"MYSQL_PROD_RO_DSN": "mysql://readonly:password@127.0.0.1:3306/app"
},
"timeout": 10000
}
}
}建议:
如果这是项目专用数据库工具,优先写项目配置。
如果 OpenCode 支持 secret reference,优先用 secret reference,不要把密码明文塞进去。
配好之后可用
opencode mcp list验证。
Codex
Codex CLI 使用 ~/.codex/config.toml。
推荐配置(npm 包方式):
[mcp_servers.vmysql]
command = "npx"
args = ["-y", "vmysql-mcp"]
[mcp_servers.vmysql.env]
VMYSQL_CONFIG_PATH = "/absolute/path/to/vmysql-mcp/vmysql.config.json"
MYSQL_DEV_DSN = "mysql://user:password@127.0.0.1:3306/app_dev"
MYSQL_PROD_RO_DSN = "mysql://readonly:password@127.0.0.1:3306/app"本地源码调试示例:
[mcp_servers.vmysql]
command = "node"
args = ["/absolute/path/to/vmysql-mcp/dist/cli.js"]
[mcp_servers.vmysql.env]
VMYSQL_CONFIG_PATH = "/absolute/path/to/vmysql-mcp/vmysql.config.json"
MYSQL_DEV_DSN = "mysql://user:password@127.0.0.1:3306/app_dev"
MYSQL_PROD_RO_DSN = "mysql://readonly:password@127.0.0.1:3306/app"如果包已经发布,也可以先用命令注册,再手动补环境变量:
codex mcp add vmysql --command npx --args -y vmysql-mcp建议:
修改
~/.codex/config.toml后重启 Codex。入口路径和配置路径都用绝对路径。
如果这是共享环境,不要把生产凭据写进共享 dotfile。
Claude Code
Claude Code 支持命令行注册,也支持配置文件方式。
CLI 示例(npm 包方式):
claude mcp add vmysql -- npx -y vmysql-mcp项目级 .mcp.json 示例(npm 包方式):
{
"mcpServers": {
"vmysql": {
"command": "npx",
"args": [
"-y",
"vmysql-mcp"
],
"env": {
"VMYSQL_CONFIG_PATH": "/absolute/path/to/vmysql-mcp/vmysql.config.json",
"MYSQL_DEV_DSN": "mysql://user:password@127.0.0.1:3306/app_dev",
"MYSQL_PROD_RO_DSN": "mysql://readonly:password@127.0.0.1:3306/app"
}
}
}
}本地源码调试 CLI 示例:
claude mcp add vmysql -- node /absolute/path/to/vmysql-mcp/dist/cli.js本地源码调试 .mcp.json 示例:
{
"mcpServers": {
"vmysql": {
"command": "node",
"args": [
"/absolute/path/to/vmysql-mcp/dist/cli.js"
],
"env": {
"VMYSQL_CONFIG_PATH": "/absolute/path/to/vmysql-mcp/vmysql.config.json",
"MYSQL_DEV_DSN": "mysql://user:password@127.0.0.1:3306/app_dev",
"MYSQL_PROD_RO_DSN": "mysql://readonly:password@127.0.0.1:3306/app"
}
}
}
}建议:
.mcp.json适合项目共享。~/.claude.json适合个人全局配置。.claude/settings.local.json适合本地私有配置,不应提交到 Git。手动改完配置后重启 Claude Code。
不要把 Claude Code 配置和 Claude Desktop 配置混为一谈,它们不是同一套东西。
安全建议 Recommended Security Practices
生产环境优先使用只读别名,例如
prod_ro不要把 DSN、密码、token 提交到仓库
写环境和读环境分开配置
除非确实需要,否则保持
allowDDL = false如果凭据曾经出现在聊天、日志、截图或错误配置里,请直接轮换,不要自我安慰说“应该没人看见”
自检与冒烟测试 Smoke Test
在 MCP 客户端接入完成后,建议先跑一条最简单的只读查询:
SELECT DATABASE() AS db, 1 AS ok再跑一条只读 CTE,确认 WITH ... SELECT 支持正常:
WITH cte AS (SELECT DATABASE() AS db, 1 AS ok)
SELECT * FROM cte如果你还想验证策略边界,可以尝试对只读环境发起写操作,确认它被拒绝。
发布流程 Release Flow
仓库现在已经带有两类 GitHub Actions:
CI:在push/pull_request时执行npm ci、npm run typecheck、npm run buildPublish:用于 npm 发布前 dry-run 校验,以及 tag 触发的正式发布
推荐发布流程:
先更新
package.json和package-lock.json中的版本号。提交并合并到
main。确保
Publishworkflow 的 dry-run 通过。在 npm 侧为该仓库配置 Trusted Publisher。
给对应提交打 tag,例如:
git tag v0.1.1
git push origin v0.1.1push这个 tag 后,GitHub Actions 会校验:tag 版本是否与
package.json一致该版本是否尚未发布
项目是否可以正常
typecheck、build、pack
校验通过后自动执行
npm publish --provenance --access public
注意:
如果你还没有在 npm 配置 Trusted Publisher,正式发布 job 会失败。
首次公开发布时,npm provenance 需要显式
--access public;当前 workflow 已经包含这个参数。当前 workflow 走的是无 secret 的 OIDC / Trusted Publishing 路线,不默认依赖
NPM_TOKEN。不要先打 tag 再回头改版本号,这种操作就是主动制造脏发布历史。
Available Tools
2 toolsmysql_execMySQL ExecADestructive
Run one write-capable SQL statement on a configured MySQL environment if policy allows.
| Name | Required | Description | Default |
|---|---|---|---|
| env | Yes | Environment alias such as dev or stg. | |
| database | No | Optional database override allowed by server policy. | |
| sql | Yes | One SQL statement allowed by server policy. | |
| timeoutMs | No | Requested execution timeout in milliseconds. |
Output Schema
| Name | Required | Description |
|---|---|---|
| ok | Yes | |
| env | Yes | |
| database | No | |
| insertId | No | |
| warnings | No | |
| elapsedMs | Yes | |
| affectedRows | Yes | |
| statementType | Yes |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
The description adds valuable context beyond annotations: it specifies 'one SQL statement' (limiting batch operations), 'if policy allows' (implying authorization checks), and 'write-capable' (clarifying operation type). Annotations already indicate destructiveHint=true and non-idempotent, but the description reinforces this with 'write-capable' and policy constraints, without contradiction.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The description is a single, well-structured sentence that front-loads the core action ('Run one write-capable SQL statement') and efficiently adds constraints ('on a configured MySQL environment if policy allows'). Every word contributes essential information without redundancy.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
Given the tool's complexity (destructive write operation with policy constraints), the description is complete: it clarifies purpose, usage context, and behavioral traits. With annotations covering safety aspects (destructiveHint=true) and an output schema existing, the description effectively supplements without needing to detail return values or repeat structured data.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, so parameters are fully documented in the schema. The description does not add specific meaning to individual parameters beyond implying 'env' and 'sql' are required (matching schema) and hinting at policy constraints for 'database' and 'sql'. Baseline score of 3 is appropriate as schema carries the burden.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description clearly states the specific action ('Run one write-capable SQL statement'), the resource ('on a configured MySQL environment'), and distinguishes from its sibling mysql_query by specifying 'write-capable' versus presumably read-only querying. It provides precise scope with 'one SQL statement' and policy constraints.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description explicitly states 'if policy allows' and specifies 'write-capable SQL statement,' which implies usage for write operations versus read queries handled by mysql_query. However, it does not explicitly name the sibling tool as an alternative or detail when not to use this tool beyond policy constraints.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
mysql_queryMySQL QueryARead-onlyIdempotent
Run one read-only SQL statement on a configured MySQL environment.
| Name | Required | Description | Default |
|---|---|---|---|
| env | Yes | Environment alias such as dev, stg, or prod_ro. | |
| database | No | Optional database override allowed by server policy. | |
| sql | Yes | One read-only SQL statement. | |
| limit | No | Requested row limit. The server may clamp it. | |
| timeoutMs | No | Requested execution timeout in milliseconds. |
Output Schema
| Name | Required | Description |
|---|---|---|
| ok | Yes | |
| env | Yes | |
| rows | Yes | |
| columns | Yes | |
| database | No | |
| rowCount | Yes | |
| elapsedMs | Yes | |
| truncated | Yes | |
| limitApplied | Yes | |
| statementType | Yes |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
The description adds valuable context beyond annotations by specifying 'one read-only SQL statement', which clarifies behavioral constraints not covered by annotations (e.g., single statement limitation). Annotations already cover safety (readOnlyHint=true, destructiveHint=false), so the description appropriately supplements with execution details without contradiction.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The description is a single, efficient sentence that front-loads the core purpose ('Run one read-only SQL statement') and includes essential context ('on a configured MySQL environment'). There is no wasted wording, making it highly concise and well-structured for quick comprehension.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
Given the tool's complexity (SQL querying), the description is complete enough when combined with annotations (which cover safety and idempotency) and the presence of an output schema (handling return values). It effectively sets expectations for read-only, single-statement execution without needing to detail outputs or advanced behaviors.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
With 100% schema description coverage, the input schema fully documents all parameters. The description does not add any parameter-specific details beyond what's in the schema, such as examples or usage tips. This meets the baseline for high schema coverage but doesn't enhance parameter understanding.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description clearly states the action ('Run'), the resource ('one read-only SQL statement'), and the context ('on a configured MySQL environment'). It specifically distinguishes from the sibling tool 'mysql_exec' by emphasizing 'read-only', which helps differentiate between query and execution operations.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description explicitly states when to use this tool: for 'read-only SQL statement[s]'. This implies that for write operations or multiple statements, the sibling tool 'mysql_exec' should be used instead, providing clear alternatives and context for tool selection.
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.
2 tool updates
v0.1.0- First observed
mysql_exec - First observed
mysql_query
TDQS
Scored across 2 tools
The two tools are clearly distinct: mysql_exec handles write-capable SQL statements, while mysql_query handles read-only statements. There is no ambiguity in purpose or overlap, making it easy for an agent to select the correct tool based on the operation type.
Both tools follow a consistent verb_noun pattern with 'mysql_' as a prefix and descriptive suffixes ('exec' and 'query'). This predictable naming scheme enhances readability and reduces confusion for agents.
With only 2 tools, the server feels thin for a MySQL database interaction domain. While it covers basic read and write operations, typical database workflows might require more granular tools (e.g., for transactions, schema management, or bulk operations), making this set potentially incomplete for complex tasks.
The toolset is severely incomplete for a MySQL server. It lacks essential operations such as managing connections, handling transactions, executing multiple statements, or performing schema-related tasks (e.g., create/drop tables). This minimal coverage could lead to agent failures when attempting common database workflows beyond simple queries.
Maintenance
Related MCP Connectors
- dataOAuthco.thinair
PostgreSQL, MySQL, and SQL Server in one session. 26 read-only MCP tools for AI agents.
MCP server for building and testing AI agents with multi-model experimentation and insights.
Draxlr's remote MCP server connects AI assistants to your SQL databases and dashboards. Explore schemas, run read-only queries, manage saved queries and dashboards, and export results, all with row-level security so each user sees only their own data.
MCP server for secureFlows: token-free URL builders and integration-linting tools for AI agents.
Related MCP Servers
- FlicenseNot gradedqualityDmaintenanceA high-performance MCP server that enables AI assistants to safely interact with MySQL databases through secure CRUD operations, schema inspection, and parameterized queries with built-in SQL injection prevention.1-
- AlicenseAqualityBmaintenanceA lightweight MySQL MCP server that enables LLMs to interact with databases through tools for schema inspection and query execution. It features LLM-friendly formatting, SSL support, and a secure read-only mode with query timeout protections.7344 npmMIT
- FlicenseNot gradedqualityBmaintenanceAn MCP server that enables AI agents to safely explore and interact with MySQL databases through dynamic tool generation from stored procedures. It provides database discovery capabilities and intelligent procedure categorization while enforcing security restrictions to prevent data modification.-
- AlicenseNot gradedqualityDmaintenanceA MySQL MCP server for secure database interaction, enabling schema inspection, query execution, and RBAC via AI coding assistants.392 npm5MIT