MCP Server for MySQL
Run SQL against a MySQL database from an AI client, read-only unless writes are switched on
Connects an MCP client to a MySQL database to browse schemas, sample tables and run SQL
By Dana K. Williams (individual) Python Local · stdio Databases
74 popularity score ★ 1.4k ↓ 30k/mo
Opens the app, which asks before it adds the server. Then replace each <NAME> in its settings with your value.
It needs MYSQL_USER, MYSQL_PASSWORD. Replace each <NAME> with your value.
claude mcp add mysql -e MYSQL_USER=<MYSQL_USER> -e MYSQL_PASSWORD=<MYSQL_PASSWORD> -- uvx --from mysql-mcp-server mysql_mcp_server{
"mcpServers": {
"mysql": {
"command": "uvx",
"args": [
"--from",
"mysql-mcp-server",
"mysql_mcp_server"
],
"env": {
"MYSQL_USER": "<MYSQL_USER>",
"MYSQL_PASSWORD": "<MYSQL_PASSWORD>"
}
}
}
}{
"mcpServers": {
"mysql": {
"command": "uvx",
"args": [
"--from",
"mysql-mcp-server",
"mysql_mcp_server"
],
"env": {
"MYSQL_USER": "<MYSQL_USER>",
"MYSQL_PASSWORD": "<MYSQL_PASSWORD>"
}
}
}
}{
"servers": {
"mysql": {
"type": "stdio",
"command": "uvx",
"args": [
"--from",
"mysql-mcp-server",
"mysql_mcp_server"
],
"env": {
"MYSQL_USER": "<MYSQL_USER>",
"MYSQL_PASSWORD": "<MYSQL_PASSWORD>"
}
}
}
}[mcp_servers.mysql]
command = "uvx"
args = ["--from", "mysql-mcp-server", "mysql_mcp_server"]
[mcp_servers.mysql.env]
MYSQL_USER = "<MYSQL_USER>"
MYSQL_PASSWORD = "<MYSQL_PASSWORD>"gemini mcp add --scope user -e MYSQL_USER=<MYSQL_USER> -e MYSQL_PASSWORD=<MYSQL_PASSWORD> mysql uvx -- --from mysql-mcp-server mysql_mcp_serverMYSQL_USER |
Required: MySQL user name; the server refuses to connect without it. |
|---|---|
MYSQL_PASSWORD secret |
Required: Password for that user; must be set, may be an empty string. |
MYSQL_HOST |
Optional: Database host. |
MYSQL_PORT |
Optional: Database port. |
MYSQL_DATABASE |
Optional: Database to work in; leave unset for multi-database mode. |
MYSQL_CONNECT_TIMEOUT |
Optional: Connection timeout in seconds. |
MCP_TRANSPORT |
Optional: stdio, or sse for an HTTP server. |
MYSQL_SQL_MODE |
Optional: SQL mode for the connection. |
| Set together: ssl | |
MYSQL_SSL_MODE |
Optional: DISABLED, REQUIRED, VERIFY_CA or VERIFY_IDENTITY. |
MYSQL_SSL_CA |
Optional: CA certificate path used with VERIFY_CA or VERIFY_IDENTITY. |
| Set together: sse | |
MCP_SSE_HOST |
Optional: Address the SSE server listens on. |
| Set together: ssh | |
MYSQL_SSH_ENABLE |
Optional: Set to true to connect through an SSH tunnel set up with MYSQL_SSH_HOST, MYSQL_SSH_USER and MYSQL_SSH_KEY_PATH. |
MySQL MCP Server is a Python server that sits between an MCP client and a MySQL database you point it at with environment variables. It has three tools. One runs a single SQL statement and hands back the rows as comma-separated text, one describes the columns of a table or of the whole configured database, and one pulls a few sample rows. Tables are also served as MCP resources, and two prompts, explore_database and analyze_table, walk the client through a survey of the schema or of one table.
With MYSQL_DATABASE set it works inside that database. Leave it out and it lists every non-system database instead, and you write database.table names. It can reach a remote server through an SSH tunnel (the MYSQL_SSH_* settings) and supports SSL modes from DISABLED to VERIFY_IDENTITY. It speaks stdio by default, and MCP_TRANSPORT=sse starts an HTTP server.
The code of version 0.4.5 (server.py) is looser than the README suggests. execute_sql has no statement filter: the README names SELECT, SHOW, DESCRIBE and INSERT/UPDATE/DELETE, but DROP, ALTER or GRANT go through just the same, on a connection with autocommit on. What it can change depends only on the grants of the MySQL user you give it. The single-statement rule is a plain check for a semicolon anywhere but the end of the query, so a semicolon inside a string literal gets the query refused too. The code also reads MYSQL_SSL_CA for the VERIFY_CA and VERIFY_IDENTITY modes, a setting the README never lists.
| Runtime | Python |
|---|---|
| Runs on | macOS, Windows, Linux |
| MySQL | Your own instanceA reachable MySQL server and a MySQL user for the server to sign in as |
| Also |
|
Install uv for the uvx command, or use pip install mysql-mcp-server. MYSQL_USER and MYSQL_PASSWORD go in the client's env block (the password may be an empty string). SSE mode needs the extra packages from pip install mysql-mcp-server[sse]. SSH tunnelling needs a jump host and a private key file.
Single statements only: multi-statement input such as USE db; SELECT ... is not supported. get_table_sample returns 5 rows by default and at most 20; reading a table resource returns its first 100 rows; execute_sql has no row cap and fetches the whole result. Table names passed to the schema and sample tools may contain only letters, digits, underscores, $ and one dot. A .env file is only found when the server runs from the project folder: Claude Desktop and Claude Code start it elsewhere, so settings must go in the client config. SSE mode has no authentication of its own and listens on 0.0.0.0 by default.
Suits developers who want an assistant to explore and query a MySQL database they control, locally or over SSH, and who can create a dedicated MySQL user with only the privileges they want it to have. Since execute_sql passes any statement through, anyone who wants the server itself to refuse writes should look at read-only-local-mysql-mcp-server, which we also list: it accepts only SELECT, WITH, SHOW, DESCRIBE and EXPLAIN and runs them in a read-only transaction. With this one, read-only access has to come from the MySQL user's grants.
2 only read, 1 can delete or overwrite. A ? marks an optional parameter.
execute_sql deletesquery: stringget_schema_infotable_name?: stringget_table_sampletable_name: stringlimit?: integermysql://{table}/datamysql://database/{database}explore_databaseanalyze_table