Mailcow Complete Email Server
Full-featured email server with Dovecot, Postfix, SOGo webmail, and rspamd spam filtering.
Overview
Mailcow is a complete, dockerized mail server solution that combines the most robust open-source email components into a unified platform. Originally developed as an alternative to complex manual email server setups, mailcow integrates Postfix for SMTP services, Dovecot for IMAP/POP3, SOGo for webmail and groupware functionality, and rspamd for advanced spam filtering and reputation management. This creates a production-ready email infrastructure that rivals commercial solutions while maintaining full control over your data. The architecture leverages Postfix as the mail transfer agent handling incoming and outgoing messages, while Dovecot manages mailbox storage and client connections through IMAP and POP3 protocols. SOGo provides a modern web interface for email, calendar, and contacts with ActiveSync support for mobile devices. Rspamd performs real-time spam analysis using machine learning algorithms, DKIM signing, and reputation scoring, with Redis caching frequently accessed data and MySQL storing user accounts, configurations, and message metadata. This combination addresses the critical challenge of running enterprise-grade email infrastructure without the complexity of manually configuring and maintaining individual components. Small to medium businesses, privacy-conscious organizations, and system administrators benefit from mailcow's integrated approach, which provides advanced features like two-factor authentication, alias management, automatic backup capabilities, and comprehensive logging while eliminating the traditional pain points of email server administration.
Key Features
- Rspamd advanced spam filtering with Bayes classification, neural networks, and real-time reputation scoring
- SOGo ActiveSync protocol support for native mobile device integration with push notifications
- Postfix multi-instance architecture with automatic DKIM key generation and DNS record management
- Dovecot full-text search with Solr backend integration and server-side mail filtering via Sieve
- Built-in quarantine management system with user self-service portal for reviewing blocked messages
- Automatic Let's Encrypt certificate provisioning and renewal with DANE TLSA record support
- Real-time monitoring dashboard with mail queue status, spam statistics, and system resource usage
- Multi-domain support with per-domain policies, quotas, and administrator delegation
Common Use Cases
- 1Small business email infrastructure replacing expensive hosted solutions like Microsoft 365
- 2Privacy-focused organizations requiring full control over email data and encryption keys
- 3Managed service providers offering white-label email hosting to multiple clients
- 4Educational institutions needing cost-effective email with calendar and contact synchronization
- 5Development teams requiring dedicated email services for application notifications and user communications
- 6Remote work environments needing reliable email with mobile device management capabilities
- 7Compliance-sensitive industries requiring email archiving, audit trails, and data residency control
Prerequisites
- Minimum 4GB RAM and 20GB storage space for production deployment with multiple domains
- Valid domain name with ability to configure MX, SPF, DKIM, and DMARC DNS records
- Clean IP address reputation (not blacklisted) with reverse DNS properly configured
- SSL certificate or ability to obtain Let's Encrypt certificates for mail.yourdomain.com
- Open firewall ports 25, 80, 110, 143, 443, 465, 587, 993, 995 for full functionality
- Basic understanding of email protocols (SMTP, IMAP, POP3) and DNS record management
For development & testing. Review security settings, change default credentials, and test thoroughly before production use. See Terms
docker-compose.yml
docker-compose.yml
1services: 2 unbound-mailcow: 3 image: mailcow/unbound:latest4 volumes: 5 - ./data/hooks/unbound:/hooks:Z6 - ./data/conf/unbound/unbound.conf:/etc/unbound/unbound.conf:ro,Z7 networks: 8 mailcow-network: 9 aliases: 10 - unbound1112 mysql-mailcow: 13 image: mariadb:10.1114 command: --innodb-buffer-pool-size=256M15 volumes: 16 - mysql-vol-1:/var/lib/mysql17 - mysql-socket-vol-1:/var/run/mysqld18 - ./data/conf/mysql/:/etc/mysql/conf.d/:ro,Z19 environment: 20 MYSQL_ROOT_PASSWORD: ${DBROOT}21 MYSQL_DATABASE: ${DBNAME}22 MYSQL_USER: ${DBUSER}23 MYSQL_PASSWORD: ${DBPASS}24 networks: 25 - mailcow-network26 restart: unless-stopped2728 redis-mailcow: 29 image: redis:alpine30 volumes: 31 - redis-vol-1:/data32 networks: 33 - mailcow-network34 restart: unless-stopped3536 rspamd-mailcow: 37 image: mailcow/rspamd:latest38 depends_on: 39 - redis-mailcow40 volumes: 41 - ./data/conf/rspamd/custom/:/etc/rspamd/custom:Z42 - ./data/conf/rspamd/override.d/:/etc/rspamd/override.d:Z43 - ./data/conf/rspamd/local.d/:/etc/rspamd/local.d:Z44 - rspamd-vol-1:/var/lib/rspamd45 networks: 46 - mailcow-network47 restart: unless-stopped4849 dovecot-mailcow: 50 image: mailcow/dovecot:latest51 depends_on: 52 - mysql-mailcow53 volumes: 54 - ./data/conf/dovecot:/etc/dovecot:Z55 - ./data/assets/ssl:/etc/ssl/mail:ro,Z56 - vmail-vol-1:/var/vmail57 environment: 58 DBNAME: ${DBNAME}59 DBUSER: ${DBUSER}60 DBPASS: ${DBPASS}61 networks: 62 - mailcow-network63 restart: unless-stopped6465 postfix-mailcow: 66 image: mailcow/postfix:latest67 depends_on: 68 - mysql-mailcow69 volumes: 70 - ./data/conf/postfix:/etc/postfix:Z71 - ./data/assets/ssl:/etc/ssl/mail:ro,Z72 - postfix-vol-1:/var/spool/postfix73 environment: 74 DBNAME: ${DBNAME}75 DBUSER: ${DBUSER}76 DBPASS: ${DBPASS}77 ports: 78 - "25:25"79 - "465:465"80 - "587:587"81 networks: 82 - mailcow-network83 restart: unless-stopped8485 sogo-mailcow: 86 image: mailcow/sogo:latest87 depends_on: 88 - mysql-mailcow89 - redis-mailcow90 environment: 91 DBNAME: ${DBNAME}92 DBUSER: ${DBUSER}93 DBPASS: ${DBPASS}94 MAILCOW_HOSTNAME: ${MAILCOW_HOSTNAME}95 networks: 96 - mailcow-network97 restart: unless-stopped9899 nginx-mailcow: 100 image: nginx:alpine101 depends_on: 102 - sogo-mailcow103 - rspamd-mailcow104 ports: 105 - "80:80"106 - "443:443"107 volumes: 108 - ./data/conf/nginx:/etc/nginx/conf.d:ro,Z109 - ./data/assets/ssl:/etc/ssl/mail:ro,Z110 networks: 111 - mailcow-network112 restart: unless-stopped113114volumes: 115 mysql-vol-1: 116 mysql-socket-vol-1: 117 redis-vol-1: 118 rspamd-vol-1: 119 vmail-vol-1: 120 postfix-vol-1: 121122networks: 123 mailcow-network: 124 driver: bridge.env Template
.env
1# Hostname2MAILCOW_HOSTNAME=mail.example.com34# Database5DBNAME=mailcow6DBUSER=mailcow7DBPASS=secure_db_password8DBROOT=secure_root_password910# Timezone11TZ=UTCUsage Notes
- 1Access admin at https://mail.example.com/admin
- 2SOGo webmail at https://mail.example.com/SOGo
- 3Configure DNS records (MX, SPF, DKIM, DMARC)
- 4Use mailcow generate_config.sh for initial setup
Individual Services(8 services)
Copy individual services to mix and match with your existing compose files.
unbound-mailcow
unbound-mailcow:
image: mailcow/unbound:latest
volumes:
- ./data/hooks/unbound:/hooks:Z
- ./data/conf/unbound/unbound.conf:/etc/unbound/unbound.conf:ro,Z
networks:
mailcow-network:
aliases:
- unbound
mysql-mailcow
mysql-mailcow:
image: mariadb:10.11
command: "--innodb-buffer-pool-size=256M"
volumes:
- mysql-vol-1:/var/lib/mysql
- mysql-socket-vol-1:/var/run/mysqld
- ./data/conf/mysql/:/etc/mysql/conf.d/:ro,Z
environment:
MYSQL_ROOT_PASSWORD: ${DBROOT}
MYSQL_DATABASE: ${DBNAME}
MYSQL_USER: ${DBUSER}
MYSQL_PASSWORD: ${DBPASS}
networks:
- mailcow-network
restart: unless-stopped
redis-mailcow
redis-mailcow:
image: redis:alpine
volumes:
- redis-vol-1:/data
networks:
- mailcow-network
restart: unless-stopped
rspamd-mailcow
rspamd-mailcow:
image: mailcow/rspamd:latest
depends_on:
- redis-mailcow
volumes:
- ./data/conf/rspamd/custom/:/etc/rspamd/custom:Z
- ./data/conf/rspamd/override.d/:/etc/rspamd/override.d:Z
- ./data/conf/rspamd/local.d/:/etc/rspamd/local.d:Z
- rspamd-vol-1:/var/lib/rspamd
networks:
- mailcow-network
restart: unless-stopped
dovecot-mailcow
dovecot-mailcow:
image: mailcow/dovecot:latest
depends_on:
- mysql-mailcow
volumes:
- ./data/conf/dovecot:/etc/dovecot:Z
- ./data/assets/ssl:/etc/ssl/mail:ro,Z
- vmail-vol-1:/var/vmail
environment:
DBNAME: ${DBNAME}
DBUSER: ${DBUSER}
DBPASS: ${DBPASS}
networks:
- mailcow-network
restart: unless-stopped
postfix-mailcow
postfix-mailcow:
image: mailcow/postfix:latest
depends_on:
- mysql-mailcow
volumes:
- ./data/conf/postfix:/etc/postfix:Z
- ./data/assets/ssl:/etc/ssl/mail:ro,Z
- postfix-vol-1:/var/spool/postfix
environment:
DBNAME: ${DBNAME}
DBUSER: ${DBUSER}
DBPASS: ${DBPASS}
ports:
- "25:25"
- "465:465"
- "587:587"
networks:
- mailcow-network
restart: unless-stopped
sogo-mailcow
sogo-mailcow:
image: mailcow/sogo:latest
depends_on:
- mysql-mailcow
- redis-mailcow
environment:
DBNAME: ${DBNAME}
DBUSER: ${DBUSER}
DBPASS: ${DBPASS}
MAILCOW_HOSTNAME: ${MAILCOW_HOSTNAME}
networks:
- mailcow-network
restart: unless-stopped
nginx-mailcow
nginx-mailcow:
image: nginx:alpine
depends_on:
- sogo-mailcow
- rspamd-mailcow
ports:
- "80:80"
- "443:443"
volumes:
- ./data/conf/nginx:/etc/nginx/conf.d:ro,Z
- ./data/assets/ssl:/etc/ssl/mail:ro,Z
networks:
- mailcow-network
restart: unless-stopped
Quick Start
terminal
1# 1. Create the compose file2cat > docker-compose.yml << 'EOF'3services:4 unbound-mailcow:5 image: mailcow/unbound:latest6 volumes:7 - ./data/hooks/unbound:/hooks:Z8 - ./data/conf/unbound/unbound.conf:/etc/unbound/unbound.conf:ro,Z9 networks:10 mailcow-network:11 aliases:12 - unbound1314 mysql-mailcow:15 image: mariadb:10.1116 command: --innodb-buffer-pool-size=256M17 volumes:18 - mysql-vol-1:/var/lib/mysql19 - mysql-socket-vol-1:/var/run/mysqld20 - ./data/conf/mysql/:/etc/mysql/conf.d/:ro,Z21 environment:22 MYSQL_ROOT_PASSWORD: ${DBROOT}23 MYSQL_DATABASE: ${DBNAME}24 MYSQL_USER: ${DBUSER}25 MYSQL_PASSWORD: ${DBPASS}26 networks:27 - mailcow-network28 restart: unless-stopped2930 redis-mailcow:31 image: redis:alpine32 volumes:33 - redis-vol-1:/data34 networks:35 - mailcow-network36 restart: unless-stopped3738 rspamd-mailcow:39 image: mailcow/rspamd:latest40 depends_on:41 - redis-mailcow42 volumes:43 - ./data/conf/rspamd/custom/:/etc/rspamd/custom:Z44 - ./data/conf/rspamd/override.d/:/etc/rspamd/override.d:Z45 - ./data/conf/rspamd/local.d/:/etc/rspamd/local.d:Z46 - rspamd-vol-1:/var/lib/rspamd47 networks:48 - mailcow-network49 restart: unless-stopped5051 dovecot-mailcow:52 image: mailcow/dovecot:latest53 depends_on:54 - mysql-mailcow55 volumes:56 - ./data/conf/dovecot:/etc/dovecot:Z57 - ./data/assets/ssl:/etc/ssl/mail:ro,Z58 - vmail-vol-1:/var/vmail59 environment:60 DBNAME: ${DBNAME}61 DBUSER: ${DBUSER}62 DBPASS: ${DBPASS}63 networks:64 - mailcow-network65 restart: unless-stopped6667 postfix-mailcow:68 image: mailcow/postfix:latest69 depends_on:70 - mysql-mailcow71 volumes:72 - ./data/conf/postfix:/etc/postfix:Z73 - ./data/assets/ssl:/etc/ssl/mail:ro,Z74 - postfix-vol-1:/var/spool/postfix75 environment:76 DBNAME: ${DBNAME}77 DBUSER: ${DBUSER}78 DBPASS: ${DBPASS}79 ports:80 - "25:25"81 - "465:465"82 - "587:587"83 networks:84 - mailcow-network85 restart: unless-stopped8687 sogo-mailcow:88 image: mailcow/sogo:latest89 depends_on:90 - mysql-mailcow91 - redis-mailcow92 environment:93 DBNAME: ${DBNAME}94 DBUSER: ${DBUSER}95 DBPASS: ${DBPASS}96 MAILCOW_HOSTNAME: ${MAILCOW_HOSTNAME}97 networks:98 - mailcow-network99 restart: unless-stopped100101 nginx-mailcow:102 image: nginx:alpine103 depends_on:104 - sogo-mailcow105 - rspamd-mailcow106 ports:107 - "80:80"108 - "443:443"109 volumes:110 - ./data/conf/nginx:/etc/nginx/conf.d:ro,Z111 - ./data/assets/ssl:/etc/ssl/mail:ro,Z112 networks:113 - mailcow-network114 restart: unless-stopped115116volumes:117 mysql-vol-1:118 mysql-socket-vol-1:119 redis-vol-1:120 rspamd-vol-1:121 vmail-vol-1:122 postfix-vol-1:123124networks:125 mailcow-network:126 driver: bridge127EOF128129# 2. Create the .env file130cat > .env << 'EOF'131# Hostname132MAILCOW_HOSTNAME=mail.example.com133134# Database135DBNAME=mailcow136DBUSER=mailcow137DBPASS=secure_db_password138DBROOT=secure_root_password139140# Timezone141TZ=UTC142EOF143144# 3. Start the services145docker compose up -d146147# 4. View logs148docker compose logs -fOne-Liner
Run this command to download and set up the recipe in one step:
terminal
1curl -fsSL https://docker.recipes/api/recipes/mailcow-full-stack/run | bashTroubleshooting
- Database connection errors in dovecot logs: Verify DBPASS environment variable matches MySQL password and mysql-mailcow container is running
- Redis connection timeouts in rspamd: Check redis-vol-1 volume permissions and ensure Redis container has sufficient memory allocation
- DKIM verification failures: Regenerate DKIM keys through mailcow admin interface and update DNS TXT records with new public key
- SOGo calendar sync issues with mobile devices: Verify MAILCOW_HOSTNAME environment variable matches certificate common name and ActiveSync is enabled
- Mail delivery delays or queue buildup: Check postfix logs for DNS resolution issues and verify sending IP reputation with major providers
Community Notes
Loading...
Loading notes...
Download Recipe Kit
Get all files in a ready-to-deploy package
Includes docker-compose.yml, .env template, README, and license
Components
mailcowdovecotpostfixsogorspamdredismysql
Tags
#email#mailcow#dovecot#postfix#sogo
Category
Productivity & CollaborationAd Space
Shortcuts: C CopyF FavoriteD Download