Model Context Protocol server for PostgreSQL with HTTP/SSE transport for remote deployment. Built with Python, FastAPI, and Docker for Elestio or any cloud platform.
- HTTP/SSE Transport: Remote access via HTTPS
- API Key Authentication: Secure access control
- Query Execution: Execute SELECT queries with natural language
- Schema Management: Create, alter, and drop tables and indexes
- Data Manipulation: Insert, update, and delete data
- User Management: Create users and manage permissions
- Database Maintenance: VACUUM, backups, and connection management
- Secure: Read-only mode, connection pooling, and query timeouts
docker build -t postgresql-mcp-server .Generate API key:
python3 -c "import secrets; print(secrets.token_urlsafe(32))"Copy .env.example to .env and update:
cp .env.example .env
# Edit .env with your PostgreSQL and API keydocker-compose up -dServer will be available at http://localhost:3000
Add to Cursor MCP settings:
{
"mcpServers": {
"postgresql": {
"url": "https://your-server.com:3000",
"headers": {
"Authorization": "Bearer your_api_key"
}
}
}
}See ELESTIO_DEPLOY.md for deployment guide.
execute_query- Run SELECT queriesexecute_explain- Get query execution planslist_databases- List all databaseslist_tables- List tables in schemalist_columns- Show column informationget_table_info- Get detailed table metadataget_database_size- Get database and table sizes
create_table- Create new tablesdrop_table- Remove tablesalter_table- Modify table structurecreate_index- Create indexesdrop_index- Remove indexesget_table_ddl- Generate CREATE TABLE statements
insert_data- Insert single rowbulk_insert- Insert multiple rowsupdate_data- Update rowsdelete_data- Delete rows
list_users- List database userscreate_user- Create new usersgrant_permissions- Grant privilegesrevoke_permissions- Revoke privilegeslist_permissions- Show user permissions
vacuum_analyze- Run VACUUM ANALYZEbackup_database- Create pg_dump backuprestore_database- Restore from backupkill_connections- Terminate connectionsget_active_connections- Show active connectionstest_connection- Test database connection
Once configured in Cursor, interact with your database naturally:
"Show me all tables in the database"
"What's the structure of the users table?"
"Find the top 10 customers by order count"
"Create a products table with id, name, and price columns"
"Insert a new user with email test@example.com"
"Show me all database users and their permissions"
Environment variables:
POSTGRES_HOST- Database host (default: localhost)POSTGRES_PORT- Database port (default: 5432)POSTGRES_DB- Database namePOSTGRES_USER- Database userPOSTGRES_PASSWORD- Database passwordPOSTGRES_READONLY- Read-only mode (default: false)POSTGRES_SSLMODE- SSL mode (default: prefer)POSTGRES_POOL_MIN- Min connections (default: 1)POSTGRES_POOL_MAX- Max connections (default: 10)QUERY_TIMEOUT- Query timeout in seconds (default: 30)
- Use environment variables for credentials, never hardcode
- Enable read-only mode for exploration:
POSTGRES_READONLY=true - Create dedicated users with minimal required privileges
- Use SSL connections for production:
POSTGRES_SSLMODE=require - Set query timeouts to prevent long-running queries
- Limit connection pools based on your database capacity
Edit .env with your PostgreSQL credentials:
docker-compose up -ddocker run -i --rm \
-e POSTGRES_HOST=your_host \
-e POSTGRES_PORT=5432 \
-e POSTGRES_DB=your_db \
-e POSTGRES_USER=your_user \
-e POSTGRES_PASSWORD=your_password \
postgresql-mcp-servermcpg/
├── src/postgresql_mcp_server/
│ ├── __init__.py
│ ├── server.py # Main MCP server
│ ├── db_manager.py # Connection management
│ ├── query_executor.py # Query execution
│ ├── schema_manager.py # DDL operations
│ ├── data_manager.py # DML operations
│ ├── user_manager.py # User management
│ └── maintenance_manager.py # Maintenance tools
├── Dockerfile
├── docker-compose.yml
├── requirements.txt
├── .env.example
├── cursor-mcp-config.json
├── CURSOR_SETUP.md
└── README.md
-
Verify PostgreSQL is accessible:
docker run -it --rm postgres:16-alpine psql -h host.docker.internal -U user -d db
-
Check Docker network settings for container-to-container communication
-
Review Cursor logs for MCP errors
- Verify database user has required privileges
- Check PostgreSQL pg_hba.conf for access rules
- Use
test_connectiontool to diagnose
- Ensure Docker daemon is running
- Check for port conflicts (5432)
- Verify image is built:
docker images | grep postgresql-mcp-server
- Python 3.11+
- PostgreSQL 12+
- Docker 20.10+
# Install dependencies
pip install -r requirements.txt
# Set environment variables
export POSTGRES_HOST=localhost
export POSTGRES_PORT=5432
# ... other vars
# Run directly
python -m src.postgresql_mcp_server.serverMIT License - see LICENSE file for details
Contributions welcome! Please open an issue or PR.
For issues and questions:
- Check CURSOR_SETUP.md for setup help
- Review Troubleshooting section
- Open a GitHub issue
- Cursor Setup Guide - Detailed Cursor IDE integration
- MCP Protocol - MCP specification
- PostgreSQL Docs - PostgreSQL documentation