Postfix + Dovecot на Debian 12: корпоративная почта с нуля
Семёнов Евгений Сергеевич, директор АйТи Фреш. 15+ лет опыта в корпоративных почтовых системах. С уходом Microsoft из России и ограничениями в Яндекс 360 для крупных компаний всё больше клиентов возвращаются к собственным почтовым серверам. И это правильный выбор — свой Postfix+Dovecot даёт независимость, неограниченные ящики и полный контроль над данными. В статье — полная установка от нуля, с виртуальными доменами, антиспамом, TLS и Sieve-фильтрами.
Когда стоит поднимать свою почту
Не всем нужен self-hosted mail. Если у вас 15 сотрудников и стандартные требования — Яндекс 360 или российский Hoster.ru будут дешевле и проще в поддержке. Свой сервер оправдан, когда:
- Сотрудников 50+ и хочется платить один раз за железо, а не за каждый ящик ежемесячно.
- Есть требования к хранению данных в своей инфраструктуре (152-ФЗ, коммерческая тайна).
- Нужна интеграция с AD, CRM, ERP через SMTP и IMAP API.
- Много технической почты (алерты мониторинга, логи) с объёмом, не влезающим в стандартные тарифы.
- Нужен контроль над DKIM-ключами, DMARC-политиками, чёрными списками.
Подготовка сервера
Базовая конфигурация: Debian 12 Bookworm, 4 vCPU, 8 ГБ RAM, 500 ГБ SSD под почту + 2 ТБ HDD под архивы. Статический белый IP с PTR, указывающим на mx.example.ru. У нас на стенде в дата-центре МТС почтовики работают на виртуалках с Dell Xeon Platinum 8280, storage — на кластере с 40G Mellanox.
apt update && apt upgrade -y
apt install -y postfix postfix-mysql \
dovecot-core dovecot-imapd dovecot-pop3d dovecot-lmtpd \
dovecot-mysql dovecot-sieve dovecot-managesieved \
mariadb-server nginx certbot python3-certbot-nginx \
opendkim opendkim-tools rspamd redis-server clamav-daemon
# Отключаем Exim (Debian ставит по умолчанию)
systemctl disable --now exim4 2>/dev/null
apt purge -y exim4*
Во время установки Postfix выбираем «Internet Site» и указываем mail.example.ru как mail name.
База данных для ящиков
Создаём БД для виртуальных доменов и ящиков:
mysql_secure_installation
mysql -uroot -p << 'EOF'
CREATE DATABASE mailserver;
CREATE USER 'mailuser'@'127.0.0.1' IDENTIFIED BY 'StrongPass2025';
GRANT SELECT ON mailserver.* TO 'mailuser'@'127.0.0.1';
FLUSH PRIVILEGES;
USE mailserver;
CREATE TABLE virtual_domains (
id INT AUTO_INCREMENT PRIMARY KEY,
name VARCHAR(50) NOT NULL UNIQUE
);
CREATE TABLE virtual_users (
id INT AUTO_INCREMENT PRIMARY KEY,
domain_id INT NOT NULL,
email VARCHAR(100) NOT NULL UNIQUE,
password VARCHAR(106) NOT NULL,
quota BIGINT DEFAULT 5368709120,
FOREIGN KEY (domain_id) REFERENCES virtual_domains(id) ON DELETE CASCADE
);
CREATE TABLE virtual_aliases (
id INT AUTO_INCREMENT PRIMARY KEY,
domain_id INT NOT NULL,
source VARCHAR(100) NOT NULL,
destination VARCHAR(100) NOT NULL,
FOREIGN KEY (domain_id) REFERENCES virtual_domains(id) ON DELETE CASCADE
);
INSERT INTO virtual_domains (name) VALUES ('example.ru');
INSERT INTO virtual_users (domain_id, email, password) VALUES (1, 'admin@example.ru',
ENCRYPT('AdminPass2025', CONCAT('$6$', SUBSTRING(SHA(RAND()), -16))));
EOF
Получение TLS-сертификата
Без TLS современный mail не работает — большинство MTA отклоняет plaintext. Получаем Let's Encrypt:
# nginx для certbot
cat > /etc/nginx/sites-available/mail << 'EOF'
server {
listen 80;
server_name mail.example.ru autodiscover.example.ru mta-sts.example.ru;
root /var/www/html;
}
EOF
ln -s /etc/nginx/sites-available/mail /etc/nginx/sites-enabled/
systemctl restart nginx
certbot --nginx -d mail.example.ru -d autodiscover.example.ru -d mta-sts.example.ru \
--non-interactive --agree-tos -m admin@example.ru
Конфигурация Postfix
Главный файл — /etc/postfix/main.cf:
myhostname = mail.example.ru
mydomain = example.ru
myorigin = $mydomain
inet_interfaces = all
inet_protocols = ipv4
mydestination = localhost
mynetworks = 127.0.0.0/8 [::1]/128
message_size_limit = 52428800
mailbox_size_limit = 0
recipient_delimiter = +
biff = no
append_dot_mydomain = no
# TLS
smtpd_tls_cert_file = /etc/letsencrypt/live/mail.example.ru/fullchain.pem
smtpd_tls_key_file = /etc/letsencrypt/live/mail.example.ru/privkey.pem
smtpd_use_tls = yes
smtpd_tls_security_level = may
smtp_tls_security_level = may
smtpd_tls_auth_only = yes
smtpd_tls_protocols = !SSLv2, !SSLv3, !TLSv1, !TLSv1.1
smtp_tls_protocols = !SSLv2, !SSLv3, !TLSv1, !TLSv1.1
# SASL через Dovecot
smtpd_sasl_type = dovecot
smtpd_sasl_path = private/auth
smtpd_sasl_auth_enable = yes
smtpd_tls_auth_only = yes
smtpd_relay_restrictions = permit_sasl_authenticated permit_mynetworks reject_unauth_destination
# Виртуальные домены
virtual_transport = lmtp:unix:private/dovecot-lmtp
virtual_mailbox_domains = mysql:/etc/postfix/mysql-virtual-mailbox-domains.cf
virtual_mailbox_maps = mysql:/etc/postfix/mysql-virtual-mailbox-maps.cf
virtual_alias_maps = mysql:/etc/postfix/mysql-virtual-alias-maps.cf
# Milter для DKIM и rspamd
milter_default_action = accept
smtpd_milters = inet:localhost:11332, inet:localhost:8891
non_smtpd_milters = inet:localhost:11332, inet:localhost:8891
# /etc/postfix/mysql-virtual-mailbox-domains.cf
user = mailuser
password = StrongPass2025
hosts = 127.0.0.1
dbname = mailserver
query = SELECT 1 FROM virtual_domains WHERE name='%s'
# /etc/postfix/mysql-virtual-mailbox-maps.cf
user = mailuser
password = StrongPass2025
hosts = 127.0.0.1
dbname = mailserver
query = SELECT 1 FROM virtual_users WHERE email='%s'
# /etc/postfix/mysql-virtual-alias-maps.cf
user = mailuser
password = StrongPass2025
hosts = 127.0.0.1
dbname = mailserver
query = SELECT destination FROM virtual_aliases WHERE source='%s'
Включаем submission (587) и smtps (465) в /etc/postfix/master.cf — стандартные разделы раскомментируем.
Конфигурация Dovecot
Dovecot отвечает за IMAP/POP3, LMTP-доставку в ящики и SASL для Postfix:
# /etc/dovecot/dovecot.conf
protocols = imap pop3 lmtp sieve
listen = *
# /etc/dovecot/conf.d/10-mail.conf
mail_location = maildir:/var/vmail/%d/%n/Maildir
mail_privileged_group = mail
first_valid_uid = 5000
mail_uid = vmail
mail_gid = vmail
# /etc/dovecot/conf.d/10-auth.conf
disable_plaintext_auth = yes
auth_mechanisms = plain login
!include auth-sql.conf.ext
# /etc/dovecot/conf.d/auth-sql.conf.ext
passdb {
driver = sql
args = /etc/dovecot/dovecot-sql.conf.ext
}
userdb {
driver = static
args = uid=vmail gid=vmail home=/var/vmail/%d/%n allow_all_users=yes
}
# /etc/dovecot/dovecot-sql.conf.ext
driver = mysql
connect = host=127.0.0.1 dbname=mailserver user=mailuser password=StrongPass2025
default_pass_scheme = SHA512-CRYPT
password_query = SELECT email AS user, password FROM virtual_users WHERE email='%u'
# /etc/dovecot/conf.d/10-master.conf — SASL для Postfix
service auth {
unix_listener /var/spool/postfix/private/auth {
mode = 0660
user = postfix
group = postfix
}
}
service lmtp {
unix_listener /var/spool/postfix/private/dovecot-lmtp {
mode = 0600
user = postfix
group = postfix
}
}
# /etc/dovecot/conf.d/10-ssl.conf
ssl = required
ssl_cert = </etc/letsencrypt/live/mail.example.ru/fullchain.pem
ssl_key = </etc/letsencrypt/live/mail.example.ru/privkey.pem
ssl_min_protocol = TLSv1.2
groupadd -g 5000 vmail
useradd -r -g 5000 -u 5000 -d /var/vmail -m vmail
chown -R vmail:vmail /var/vmail
chmod -R 770 /var/vmail
systemctl restart postfix dovecot
DKIM, антиспам, антивирус
OpenDKIM — отдельная тема, подробно в статье про SPF/DKIM/DMARC. Rspamd ставится одной командой и подключается как milter:
# /etc/rspamd/local.d/redis.conf
servers = "127.0.0.1:6379";
# /etc/rspamd/local.d/classifier-bayes.conf
backend = "redis";
# /etc/rspamd/local.d/antivirus.conf
clamav {
type = "clamav";
servers = "/var/run/clamav/clamd.ctl";
scan_mime_parts = true;
}
systemctl restart rspamd clamav-daemon
Sieve-фильтры
Sieve — стандарт IMAP для server-side фильтрации. Пользователи через Roundcube могут писать свои правила:
// Пример .sieve файла
require ["fileinto", "mailbox"];
if header :contains "X-Spam-Flag" "YES" {
fileinto :create "Junk";
stop;
}
if address :contains "From" "crm@example.ru" {
fileinto :create "CRM";
}
if allof (header :contains "Subject" "Отчёт", header :contains "From" "reports@") {
fileinto :create "Отчёты";
}
Мини-кейс: миграция с Exchange на Postfix
В феврале 2026 года к нам пришёл клиент — дистрибутор электроники, 220 сотрудников, 12 лет работы на Microsoft Exchange 2016. После окончания поддержки и проблем с лицензированием решено было мигрировать на open-source. Требования: сохранить все 220 ящиков, ~350 ГБ исторической переписки, интеграция с AD, поддержка ActiveSync для iPhone/Android.
Решение:
- Postfix + Dovecot на двух виртуалках (active-passive failover через DNS MX с приоритетами).
- LDAP-бэкенд вместо MySQL — привязали к корпоративному AD для единых учёток.
- SOGo поверх Dovecot — даёт веб-интерфейс, CalDAV, CardDAV, ActiveSync.
- Миграция данных через imapsync — заняла 14 часов на 350 ГБ, после чего переключили MX.
- Rspamd + ClamAV + DKIM/DMARC настроены с первого дня.
- Бэкап ежедневный на стороннюю СХД Synology RS3621RPxs в дата-центре МТС.
Итог: миграция прошла за 6 часов ночью, downtime почты — 2 часа. За 3 месяца — 0 инцидентов с доступом, объём почты 420 ГБ, ежемесячная нагрузка стабильная. Экономия на лицензиях Exchange — 1,8 млн руб./год. Стоимость проекта — 520 000 руб. + 15 000 руб./мес сопровождение.
Бэкап и мониторинг
| Компонент | Что бэкапим | Частота |
|---|---|---|
| MySQL | Полный дамп mailserver | Ежедневно |
| Maildir | /var/vmail целиком через rsync | Ежедневно инкремент, еженедельно полный |
| Конфиги | /etc/postfix, /etc/dovecot, /etc/opendkim | При каждом изменении в git |
| Сертификаты | /etc/letsencrypt | Ежемесячно |
Мониторинг через Prometheus + Grafana с postfix_exporter, dovecot_exporter: очередь почты, количество доставленных, отказы, время обработки. Алерты на очередь >100, на %-fail>5%, на отсутствие дисков.
Типовые ошибки при поднятии сервера
- Без SPF/DKIM/DMARC. Сервер работает, но письма в спам у всех. Настраивайте заранее.
- Без TLS. Большие провайдеры отклоняют plaintext.
- Отсутствие PTR. Без обратной записи IP->FQDN 50% MTA отклонит.
- Mailbox_size_limit = 51200000. Дефолт Debian 50 МБ — маленькая почта быстро падает. Ставьте 0 (без лимита) + квоту в БД.
- Open relay. Неправильный
smtpd_relay_restrictions— через вас шлют спам. - Логирование pwd в истории MySQL. Никогда не вбивайте пароли через --password=, только через
-pинтерактивно или mysql_config_editor.
Поднимем корпоративную почту под ключ
Миграция с Exchange/Яндекс 360/любых почтовых сервисов на свой Postfix+Dovecot. Полный набор: виртуальные домены, DKIM/SPF/DMARC, антиспам, антивирус, веб-интерфейс, ActiveSync, бэкап, мониторинг. 15+ лет опыта с почтовыми серверами от 20 до 500 пользователей.
Телефон: +7 903 729-62-41
Telegram: @ITfresh_Boss
Семёнов Евгений Сергеевич, директор АйТи Фреш
FAQ — частые вопросы про Postfix+Dovecot
- Зачем свой почтовый сервер вместо Яндекс 360?
- Причин несколько: полный контроль над данными (152-ФЗ, коммерческая тайна), отсутствие лимитов на количество ящиков и объём, возможность интеграции со своими системами (CRM, ERP, 1С), независимость от сторонних провайдеров и их тарифов.
- Какое железо нужно на почтовый сервер для 100 пользователей?
- Вполне достаточно 4 vCPU, 8 ГБ RAM, 500 ГБ SSD под хранилище и 2 ТБ HDD под архивы. Нагрузка на почтовый сервер 100-пользователей обычно невысокая. Критично — хороший канал и стабильный IP с PTR.
- Какую базу использовать для users?
- Для небольших инсталляций — обычный текстовый файл (passwd-file). Для 50+ пользователей — MySQL или PostgreSQL с веб-админкой (PostfixAdmin, iRedMail). Для интеграции с AD — LDAP-бэкенд.
- Что с веб-интерфейсом?
- Roundcube — популярный выбор, ставится за 15 минут. SOGo — более функциональный с календарями и контактами ActiveSync. Для корпоратива я обычно ставлю Roundcube + отдельно Radicale для CardDAV/CalDAV.
- Нужен ли антивирус?
- Обязательно. Rspamd или SpamAssassin + ClamAV проверяют входящие письма на спам и вредоносные вложения. Без этого сервер быстро становится магнитом для фишинга и трояна от имени ваших клиентов.