Universal Db Mcp

io.github.Fashad-Ahmed由 GitHub 账号 Fashad-Ahmed 发布v1.1.2更新于 Oct 24, 2026

Security-first MCP server for PostgreSQL, SQLite, MySQL, DuckDB with SQL injection prevention.

已验证STDIO仅桌面数据库数据与分析

概览

AI 生成的概览

本地运行的 MCP 服务器,默认只读,让助手查看表结构并对 PostgreSQL、MySQL、SQLite 和 DuckDB 执行受防护的 SQL。

可以做什么
对已配置的数据库执行 SQL 查询,默认只读,带注入检测和行数限制,也可选择仅试运行或查看执行计划而不实际执行。查看表和列结构,列出已配置的数据库并检查连接状态与版本。查看最近 100 条已执行查询,并保存表结构快照以比对结构变化。查询本地 SQLite 文件与进程内 DuckDB,包括内存中的分析。
适用场景
适合让助手用自然语言探索或查询关系型与分析型数据库,尤其是无需搭建服务器的本地 SQLite 或 DuckDB 文件,同时默认阻止写入。
运行要求
以 Python 包在本地运行(uvx 或 pip)。至少需要一项连接配置:POSTGRES_URI、MYSQL_URI、SQLITE_PATH 或 DUCKDB_PATH。可选配置包括 ALLOW_DESTRUCTIVE、MAX_RESULT_ROWS 和只读开关。仅连接远程 PostgreSQL 或 MySQL 时需要网络访问。
安装前请注意
POSTGRES_URI 和 MYSQL_URI 含数据库凭据,应使用专用只读账号。将 ALLOW_DESTRUCTIVE 设为 true 会允许 INSERT、UPDATE、DELETE 和 DDL,从而可能写入或删除数据。查询结果和表结构信息会发送给模型提供方。DuckDB 的文件读取函数已被拦截,但指向敏感数据前请先阅读安全文档。

安装

在 SourceWeft 中

  1. 打开 控制台中的 Universal Db Mcp,将其添加到工作区。
  2. 为需要使用其工具的对话启用该服务。

Desktop only,通过 STDIO。 STDIO 服务会启动本地进程,因此需要 SourceWeft 桌面宿主。

其他 MCP 客户端

参照 仓库 中的启动说明。

README

Universal Database MCP Server

The security-first, Python-native MCP server for database access from AI agents.

[CI] [PyPI] [Python 3.10+] [FastMCP] [License: MIT]

[Demo: schema discovery, a real query, a blocked DROP, and dry-run mode]


Why This Exists

Most database MCP servers give AI agents raw SQL access and hope for the best. This server assumes the LLM is untrusted input and applies 8 layers of injection prevention before any query reaches your database — including blocking UNION attacks, stacked statements, time-based injection, and comment bypasses.

Supports: PostgreSQL · SQLite · MySQL · DuckDB (columnar analytics)


Zero Setup: Works on Your Laptop Right Now

No Docker. No cloud account. No database server to install. DuckDB and SQLite run in-process:

bash
# Query a local SQLite database — one command, zero infraSQLITE_PATH=./myapp.db uvx universal-db-mcp
# Query a local DuckDB file or parquet filesDUCKDB_PATH=./analytics.duckdb uvx universal-db-mcp
# In-memory DuckDB for throwaway analysisDUCKDB_PATH=:memory: uvx universal-db-mcp

Add to Claude Code in ~/.claude/mcp_servers.json, or to Claude Desktop in ~/Library/Application Support/Claude/claude_desktop_config.json (macOS) / %APPDATA%\Claude\claude_desktop_config.json (Windows):

json
{  "mcpServers": {    "mydb": {      "command": "uvx",      "args": ["universal-db-mcp"],      "env": {        "SQLITE_PATH": "/Users/you/projects/myapp/db.sqlite3",        "ALLOW_DESTRUCTIVE": "false"      }    }  }}

Restart Claude Desktop / Claude Code after saving — that's it.

That's it. Claude Code discovers the tools automatically.

More client configs (Claude Desktop, Cursor, Windsurf, Docker) in examples/.


Security Model: 8 Layers

Read-only by default. Defense-in-depth. Every query validated before it touches the driver.

LayerWhat it does
1Driver-level read-only — PostgreSQL session flag, SQLite mode=ro URI, DuckDB read_only=True. Write rejected before SQL parsing.
2Keyword blocking — DROP, DELETE, TRUNCATE, ALTER, INSERT, UPDATE, GRANT, EXEC blocked in read-only mode
3Injection pattern detection — UNION SELECT, stacked statements, SQL comments (--, /*), xp_, SLEEP(), WAITFOR, BENCHMARK()
4Multiple statement rejection — ; separating statements always blocked
5Parameter type enforcement — only str, int, float, bool, null accepted as parameters
6Result size limits — truncated at MAX_RESULT_ROWS (default 1000) to prevent memory exhaustion
7Identifier sanitization — table/column names stripped of metacharacters in internally-generated SQL
8DuckDB filesystem blocklist — read_csv(), read_parquet(), glob(), LOAD, INSTALL, httpfs, COPY blocked at adapter level; read_only=True only blocks writes, not file reads

Full threat model: docs/SECURITY.md


DuckDB: Analytics Without Infrastructure

DuckDB runs in-process (no server) and reads Parquet, CSV, JSON natively. Connect AI agents to your analytics data without spinning up a warehouse:

bash
# Query parquet files directlyDUCKDB_PATH=:memory: uvx universal-db-mcp

Then in Claude Code:

You: "Load sales.parquet and show me monthly revenue by region"Claude: [uses query tool → SELECT region, strftime('%Y-%m', date) AS month, SUM(revenue) ...]

Natural Language → SQL

No separate NL-to-SQL tool needed — Claude already does this. Give it the schema tool and ask in plain English:

You: "Which customers placed more than 5 orders last month?"Claude: [calls schema() to see table structure, then query() with the         generated SQL — every query still passes through all 8 security         layers before touching your database]

Pair with dry_run: true (DRYRUN=true) while prototyping — Claude gets the query plan back without anything executing.


Docker

bash
docker build -t universal-db-mcp .docker run -i --rm \  -e POSTGRES_URI=postgresql://readonly:[email protected]:5432/mydb \  -e ALLOW_DESTRUCTIVE=false \  universal-db-mcp

See examples/docker_mcp_config.json for wiring this into an MCP client.


All Databases

bash
# PostgreSQLPOSTGRES_URI=postgresql://readonly:pass@localhost/mydb uvx universal-db-mcp
# SQLite (local file, zero infra)SQLITE_PATH=./db.sqlite3 uvx universal-db-mcp
# MySQLMYSQL_URI=mysql://readonly:pass@localhost/mydb uvx universal-db-mcp
# DuckDB (columnar, in-process analytics)DUCKDB_PATH=./analytics.duckdb uvx universal-db-mcp
# Multiple databases simultaneouslyPOSTGRES_URI=... SQLITE_PATH=... uvx universal-db-mcp

MCP Tools

ToolDescription
queryExecute SQL — read-only by default, all 8 security layers apply
schemaInspect tables and columns — no config needed
explainGet query execution plan without running the query
healthCheck connection status, DB version, and pool metrics
list_databasesShow all configured databases and connection state
query_historyInspect the last 100 executed queries
snapshot_schemaCapture current schema for drift detection
schema_diffCompare current schema against the last snapshot

v1.1.0: dry-run mode (DRYRUN=true), table allowlists (WHITELISTED_TABLES), query complexity warnings, structured audit logs, and a --check CLI flag for connectivity validation. See CHANGELOG.md.


Configuration

bash
# ── PostgreSQL ─────────────────────────────────────POSTGRES_URI=postgresql://user:pass@host:5432/dbPOSTGRES_READONLY=true          # default: true
# ── SQLite ─────────────────────────────────────────SQLITE_PATH=/path/to/database.dbSQLITE_READONLY=true            # default: true
# ── MySQL ──────────────────────────────────────────MYSQL_URI=mysql://user:pass@host:3306/dbMYSQL_READONLY=true             # default: true
# ── DuckDB ─────────────────────────────────────────DUCKDB_PATH=/path/to/analytics.duckdb   # or :memory:DUCKDB_READONLY=true            # default: true
# ── Security ───────────────────────────────────────ALLOW_DESTRUCTIVE=false         # default: false — blocks INSERT/UPDATE/DELETE/DROPMAX_RESULT_ROWS=1000            # truncate large resultsENABLE_LOGGING=true             # log queries to stderrQUERY_TIMEOUT=30                # secondsRATE_LIMIT_RPM=60               # requests per minute

Secure Database Users

Always use a dedicated read-only account. Never give the MCP server credentials that can modify data.

PostgreSQL:

sql
CREATE USER mcp_agent WITH PASSWORD 'strong_random_password';GRANT CONNECT ON DATABASE mydb TO mcp_agent;GRANT USAGE ON SCHEMA public TO mcp_agent;GRANT SELECT ON ALL TABLES IN SCHEMA public TO mcp_agent;

MySQL:

sql
CREATE USER 'mcp_agent'@'localhost' IDENTIFIED BY 'strong_random_password';GRANT SELECT ON mydb.* TO 'mcp_agent'@'localhost';FLUSH PRIVILEGES;

Development

bash
git clone <repo-url>cd universal-db-mcppython -m venv .venv && source .venv/bin/activatepip install -e ".[dev]"
# Run tests (67+ passing, no external DB required for SQLite + DuckDB)pytest
# Security tests onlypytest tests/test_security.py -v
# With coveragepytest --cov=src/universal_db_mcp --cov-report=term-missing

Architecture

src/universal_db_mcp/├── server.py          # FastMCP server — 5 tools├── config.py          # Env-var config via Pydantic├── adapters/│   ├── base.py        # Abstract adapter + result dataclasses│   ├── postgresql.py  # asyncpg, connection pool, read-only via init callback│   ├── sqlite.py      # aiosqlite, read-only via file URI mode=ro│   ├── mysql.py       # aiomysql, DictCursor│   └── duckdb.py      # duckdb, thread-pool executor, lock-guarded└── security/    └── sanitizer.py   # SQLSanitizer — 8-layer injection prevention
docs/└── SECURITY.md        # Full security architecture and threat model

vs. Google MCP Toolbox

This projectGoogle MCP Toolbox
RuntimePython — pip install / uvxGo binary / Docker
Local DBsSQLite + DuckDB zero-infraNo SQLite
AnalyticsDuckDB in-processNo columnar adapter
Auth modelRead-only by default + env varsIAM / GCP-native
SQL injection8-layer sanitizer + parameterizedAuth-focused
ExtendPython ecosystem, any pip packageGo plugins
VendorNeutralGoogle Cloud funnel

Different tools for different jobs. Use this when you want Python-native, local-first, security-hardened access without cloud dependencies.


License

MIT — LICENSE


Security Notice: This server provides AI agents with database access. Always use read-only credentials, review docs/SECURITY.md before production deployment, and never commit .env files.

来源:README.md,提交 7581347

工具

0
SourceWeft 尚未在沙箱中启动过该软件包,因此其工具未知。

版本历史

1
  1. v1.1.2最新Sep 16, 2026

评分

已满足适用检查项的 40%

该评分衡量此收录条目的完整程度,依据注册中心条目、端点与公开来源计算得出。它不是对服务器本身的评价,也不表示服务器安全或当前可用:可连通性是带日期的检查结果,评分也不包含安装量或用户评价。

  • 近 30 天内可连通25 分

    请保持端点能够响应 MCP 握手;SourceWeft 每 30 天探测一次。

  • 已声明认证方式10 分

    请在注册中心条目中声明凭据请求头,或保持端点能够响应探测,以便判定其认证方式。

  • 已列出工具15 分

    请让服务器在无凭据时响应 tools/list,或发布可在沙箱中无凭据启动的软件包。

  • 描述必需15 分
  • 图标10 分
  • 文档15 分
  • 许可证10 分

    请在仓库或注册中心条目中声明许可证。