Skip to main content
Glama
liwenqikeep

postgres-mcp-server

by liwenqikeep
README.md
# PostgreSQL MCP 服务器

一个基于 [Model Context Protocol (MCP)](https://modelcontextprotocol.io/) 的 PostgreSQL 数据库查询服务器,让 AI 助手能够安全地访问和查询您的数据库。

## 📋 目录

- [功能特性](#功能特性)
- [快速开始](#快速开始)
- [项目结构](#项目结构)
- [配置说明](#配置说明)
- [使用方法](#使用方法)
- [MCP 客户端配置](#mcp-客户端配置)
- [安全建议](#安全建议)
- [故障排除](#故障排除)

## ✨ 功能特性

- ✅ **SQL 查询** - 执行 SELECT 查询语句
- ✅ **数据修改** - 执行 INSERT、UPDATE、DELETE 操作
- ✅ **表管理** - 列出数据库中的所有表
- ✅ **表结构查询** - 查看表的列信息、数据类型等
- ✅ **表统计信息** - 获取表的行数、大小等详细信息
- ✅ **参数化查询** - 支持参数化查询,防止 SQL 注入
- ✅ **自动连接管理** - 自动管理数据库连接池

## 🚀 快速开始

### 前置要求

- Python 3.10 或更高版本
- PostgreSQL 数据库(本地或远程)
- pip 包管理器

### 安装步骤

#### 1. 克隆或下载项目

```bash
git clone <repository_url>
cd ai-mcp
```

#### 2. 创建虚拟环境

```bash
python -m venv venv
```

#### 3. 激活虚拟环境

**Windows (PowerShell):**
```powershell
.\venv\Scripts\Activate.ps1
```

**Windows (CMD):**
```cmd
venv\Scripts\activate.bat
```

**Linux/Mac:**
```bash
source venv/bin/activate
```

#### 4. 安装依赖

```bash
pip install -r requirements.txt
```

#### 5. 配置数据库连接

复制环境变量模板并编辑:

**Windows:**
```cmd
copy env_template.txt .env
```

**Linux/Mac:**
```bash
cp env_template.txt .env
```

编辑 `.env` 文件,填入您的数据库连接信息:

```env
DB_HOST=localhost
DB_PORT=5432
DB_NAME=postgres
DB_USER=postgres
DB_PASSWORD=your_password_here
```

#### 6. 测试运行(可选)

```bash
python postgres_mcp_server.py
```

如果看到 "数据库连接成功" 的日志,说明配置正确。

## 📁 项目结构

```
ai-mcp/
├── postgres_mcp_server.py  # MCP 服务器主程序
├── requirements.txt         # Python 依赖包列表
├── env_template.txt         # 环境变量配置模板
├── README.md               # 项目说明文档(本文件)
├── .env                    # 数据库连接配置(需自行创建)
└── venv/                   # Python 虚拟环境目录
```

## ⚙️ 配置说明

### 环境变量

在 `.env` 文件中配置以下变量:

| 变量名 | 说明 | 默认值 | 示例 |
|--------|------|--------|------|
| `DB_HOST` | 数据库主机地址 | `localhost` | `192.168.1.100` |
| `DB_PORT` | 数据库端口 | `5432` | `5432` |
| `DB_NAME` | 数据库名称 | `postgres` | `my_database` |
| `DB_USER` | 数据库用户名 | `postgres` | `db_user` |
| `DB_PASSWORD` | 数据库密码 | (空) | `your_secure_password` |

### 依赖包

项目依赖以下 Python 包(已在 `requirements.txt` 中定义):

- `mcp>=1.0.0` - Model Context Protocol SDK
- `psycopg2-binary>=2.9.0` - PostgreSQL 数据库驱动
- `python-dotenv>=1.0.0` - 环境变量管理

## 📖 使用方法

### 直接运行(测试用)

```bash
python postgres_mcp_server.py
```

### 作为 MCP 服务器运行

MCP 服务器设计为通过 **stdio** 协议运行,需要配合 MCP 客户端使用(如 Claude Desktop、Cursor 等)。

### 可用工具(Tools)

服务器提供以下 5 个工具:

#### 1. `query` - 执行查询

执行 SQL 查询语句并返回结果。

**参数:**
- `sql` (string, 必需) - SQL 查询语句
- `params` (array, 可选) - 查询参数列表

**示例:**
```json
{
  "sql": "SELECT * FROM users WHERE age > %s LIMIT 10",
  "params": [18]
}
```

#### 2. `execute` - 执行修改

执行 INSERT、UPDATE、DELETE 等数据修改操作。

**参数:**
- `sql` (string, 必需) - SQL 修改语句
- `params` (array, 可选) - 查询参数列表

**示例:**
```json
{
  "sql": "INSERT INTO users (name, email) VALUES (%s, %s)",
  "params": ["张三", "zhangsan@example.com"]
}
```

#### 3. `list_tables` - 列出所有表

列出指定模式中的所有表和视图。

**参数:**
- `schema` (string, 可选) - 模式名称,默认为 `"public"`

**示例:**
```json
{
  "schema": "public"
}
```

#### 4. `describe_table` - 查看表结构

获取表的列信息(列名、数据类型、是否可空、默认值等)。

**参数:**
- `table_name` (string, 必需) - 表名
- `schema` (string, 可选) - 模式名称,默认为 `"public"`

**示例:**
```json
{
  "table_name": "users",
  "schema": "public"
}
```

#### 5. `get_table_info` - 获取表详细信息

获取表的统计信息(行数、表大小、索引大小等)。

**参数:**
- `table_name` (string, 必需) - 表名
- `schema` (string, 可选) - 模式名称,默认为 `"public"`

**示例:**
```json
{
  "table_name": "users",
  "schema": "public"
}
```

## 🔌 MCP 客户端配置

### Claude Desktop

#### 配置文件位置

- **Windows:** `%APPDATA%\Claude\claude_desktop_config.json`
- **Mac:** `~/Library/Application Support/Claude/claude_desktop_config.json`

#### 配置示例

```json
{
  "mcpServers": {
    "postgres": {
      "command": "python",
      "args": ["D:\\desk\\code\\python\\ai-mcp\\postgres_mcp_server.py"],
      "env": {
        "DB_HOST": "localhost",
        "DB_PORT": "5432",
        "DB_NAME": "your_database",
        "DB_USER": "your_username",
        "DB_PASSWORD": "your_password"
      }
    }
  }
}
```

**注意:** 
- Windows 路径需要使用双反斜杠 `\\` 或单正斜杠 `/`
- 确保 Python 在系统 PATH 中,或使用完整路径(如 `C:\\Python312\\python.exe`)

### Cursor

#### 配置文件位置

- **Windows:** `%USERPROFILE%\.cursor\mcp.json`
- **Mac/Linux:** `~/.cursor/mcp.json`

#### 配置示例

```json
{
  "mcpServers": {
    "postgres": {
      "command": "python",
      "args": ["D:\\desk\\code\\python\\ai-mcp\\postgres_mcp_server.py"],
      "env": {
        "DB_HOST": "localhost",
        "DB_PORT": "5432",
        "DB_NAME": "your_database",
        "DB_USER": "your_username",
        "DB_PASSWORD": "your_password"
      }
    }
  }
}
```

### 配置后的使用

配置完成后,重启 Claude Desktop 或 Cursor,您就可以在对话中直接使用自然语言查询数据库了:

**示例对话:**
```
用户:列出数据库中的所有表
AI:[调用 list_tables 工具]

用户:查询 china_highway_wgs84 表中有多少条数据
AI:[调用 query 工具执行 SELECT COUNT(*)]

用户:显示 users 表的结构
AI:[调用 describe_table 工具]
```

## 🔒 安全建议

### 1. 数据库权限控制

**强烈建议**为 MCP 服务器创建一个专用的数据库用户,并只授予必要的权限:

```sql
-- 创建只读用户(推荐用于查询)
CREATE USER mcp_readonly WITH PASSWORD 'secure_password';
GRANT CONNECT ON DATABASE your_database TO mcp_readonly;
GRANT USAGE ON SCHEMA public TO mcp_readonly;
GRANT SELECT ON ALL TABLES IN SCHEMA public TO mcp_readonly;

-- 如果需要修改权限(谨慎授予)
GRANT INSERT, UPDATE, DELETE ON ALL TABLES IN SCHEMA public TO mcp_readonly;
```

### 2. 环境变量安全

- ❌ **不要**将 `.env` 文件提交到版本控制系统
- ✅ 将 `.env` 添加到 `.gitignore`
- ✅ 使用强密码
- ✅ 定期更换数据库密码

### 3. 网络安全

- 如果数据库在远程服务器,使用 SSL/TLS 加密连接
- 限制数据库的网络访问(使用防火墙规则)
- 考虑使用 VPN 或 SSH 隧道

### 4. 查询限制

考虑在数据库层面设置:
- 查询超时时间
- 结果集大小限制
- 连接数限制

## 🐛 故障排除

### 问题 1: 无法连接到数据库

**错误信息:** `could not connect to server` 或 `connection refused`

**解决方案:**
1. 确认 PostgreSQL 服务正在运行
   ```bash
   # Windows
   services.msc  # 查找 PostgreSQL 服务
   
   # Linux
   sudo systemctl status postgresql
   ```

2. 检查 `.env` 文件中的连接信息是否正确
3. 确认数据库允许来自客户端的连接(检查 `pg_hba.conf`)
4. 检查防火墙是否阻止了连接

### 问题 2: 认证失败

**错误信息:** `password authentication failed`

**解决方案:**
1. 确认用户名和密码正确
2. 检查用户是否有访问该数据库的权限
3. 查看 PostgreSQL 的 `pg_hba.conf` 配置

### 问题 3: 模块导入错误

**错误信息:** `ModuleNotFoundError: No module named 'xxx'`

**解决方案:**
1. 确认虚拟环境已激活
2. 重新安装依赖:
   ```bash
   pip install -r requirements.txt
   ```

### 问题 4: MCP 客户端无法找到服务器

**解决方案:**
1. 确认配置文件路径正确
2. 检查 JSON 格式是否正确(使用 JSON 验证器)
3. 确认 Python 可执行文件路径正确
4. 查看客户端的日志文件(通常在配置文件同目录)
5. 重启 MCP 客户端应用

### 问题 5: 中文显示乱码

**解决方案:**
确保数据库使用 UTF-8 编码:
```sql
-- 查看数据库编码
SHOW SERVER_ENCODING;

-- 创建新数据库时指定编码
CREATE DATABASE mydb WITH ENCODING 'UTF8';
```

## 📝 开发说明

### 日志配置

服务器使用 Python 的 `logging` 模块记录日志。修改日志级别:

```python
# 在 postgres_mcp_server.py 中修改
logging.basicConfig(
    level=logging.DEBUG,  # 改为 DEBUG 查看详细日志
    format='%(asctime)s - %(name)s - %(levelname)s - %(message)s'
)
```

### 扩展功能

如需添加新的工具,参考现有工具的实现:

1. 在 `list_tools()` 中添加工具定义
2. 在 `call_tool()` 中添加工具调用
3. 实现具体的处理函数

## 📄 许可证

MIT License

## 🤝 贡献

欢迎提交 Issue 和 Pull Request!

## 📚 相关资源

- [Model Context Protocol 官方文档](https://modelcontextprotocol.io/)
- [PostgreSQL 官方文档](https://www.postgresql.org/docs/)
- [psycopg2 文档](https://www.psycopg.org/docs/)

## ❓ 常见问题

**Q: 这个服务器安全吗?**  
A: 服务器本身不暴露网络端口,只通过 stdio 与 MCP 客户端通信。但请务必遵循安全建议,使用专用数据库用户并限制权限。

**Q: 可以连接多个数据库吗?**  
A: 当前版本只支持连接一个数据库。如需连接多个数据库,可以配置多个 MCP 服务器实例。

**Q: 支持其他数据库吗(如 MySQL、SQLite)?**  
A: 当前只支持 PostgreSQL。如需支持其他数据库,需要修改代码并使用相应的数据库驱动。

**Q: 查询结果有大小限制吗?**  
A: 没有硬性限制,但返回大量数据可能会影响性能。建议在查询中使用 `LIMIT` 子句限制结果数量。

---

**项目版本:** 1.0.0  
**最后更新:** 2025年10月