27 KiB
| title | date | draft | description | tags | categories | series | series_order | ||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| Почтовый сервер на Debian 12: полное руководство от установки до production. Часть 2 - Postfix и Dovecot | 2026-03-10 | false | Установка и настройка Postfix и Dovecot. SMTP/IMAP, виртуальные ящики, авторизация через SASL. Первые тесты отправки и получения почты. |
|
|
|
2 |
Postfix + Dovecot: установка и базовая настройка
Сейчас поставим два ключевых компонента почтового сервера: Postfix (прием/отправка) и Dovecot (доступ к ящикам). На выходе получишь работающую систему, через которую можно отправлять и получать почту.
Без антивируса, без антиспама, без веб-морды - голый функционал. Но работающий.
Перед началом
Эта инструкция подразумевает, что у тебя:
- Debian 12 с базовой настройкой безопасности
- Настроены SSH, firewall, fail2ban
- Система обновлена
Если еще не настроил - сделай это сейчас:
{{< article link="/posts/tips-debian-12-hardening/">}}
Дальше считаем, что база готова.
Подготовка для почтового сервера
Открываем порты в firewall
Почтовому серверу нужны специфичные порты:
sudo ufw allow 25/tcp comment 'SMTP'
sudo ufw allow 587/tcp comment 'SMTP Submission'
sudo ufw allow 143/tcp comment 'IMAP'
sudo ufw allow 993/tcp comment 'IMAPS'
Проверь:
sudo ufw status
Должны появиться:
- 25/tcp (SMTP)
- 587/tcp (Submission)
- 143/tcp (IMAP)
- 993/tcp (IMAPS)
Проверяем DNS
Для почтового сервера DNS - критично. Без правильных записей письма не пойдут или улетят в спам.
MX-запись:
dig +short MX example.com
Должно вернуть:
10 mail.example.com.
A-запись:
dig +short mail.example.com
Должен вернуть твой IP.
PTR (обратная зона):
host твой-IP
Должно вернуть:
твой-IP.in-addr.arpa domain name pointer mail.example.com.
Если PTR не настроен - письма будут улетать в спам. Пиши в поддержку хостера, это делается с их стороны.
Установка Postfix
Ставим пакет
sudo apt install -y postfix
Установщик запустит конфигуратор. Отменяй его - настроим вручную.
Выбери:
- General type of mail configuration: No configuration
- Нажми OK
Создаем структуру для хранения почты
Проверяем где реальная директория
ls -ld /var/spool/mail
Если это симлинк (обычно в Debian) - работаем с /var/mail:
sudo mkdir -p /var/mail/example.com
Замени example.com на свой домен.
Создай системную группу и пользователя для виртуальных ящиков:
sudo groupadd -g 5000 vmail
sudo useradd -g vmail -u 5000 -d /var/spool/mail -s /usr/sbin/nologin vmail
Что сделали:
- Создали группу
vmailс GID 5000 - Создали пользователя
vmailс UID 5000 - Домашняя директория
/var/spool/mail - Запрет на логин (
/usr/sbin/nologin)
Назначь владельца:
sudo chown -R vmail:vmail /var/mail
sudo chmod -R 770 /var/mail
Базовая конфигурация Postfix
Создай главный конфиг:
sudo nano /etc/postfix/main.cf
Вставь:
# Общие параметры
smtpd_banner = $myhostname ESMTP
biff = no
append_dot_mydomain = no
readme_directory = no
compatibility_level = 3.6
# Имя хоста и домен
myhostname = mail.example.com
mydomain = example.com
myorigin = $mydomain
# Сеть
inet_interfaces = all
inet_protocols = ipv4
# Доверенные сети
mynetworks = 127.0.0.0/8
# Локальная доставка отключена
mydestination = localhost
local_recipient_maps =
# Виртуальные домены
virtual_mailbox_domains = example.com
virtual_mailbox_base = /var/spool/mail
virtual_mailbox_maps = hash:/etc/postfix/vmailbox
virtual_alias_maps = hash:/etc/postfix/virtual
virtual_minimum_uid = 100
virtual_uid_maps = static:5000
virtual_gid_maps = static:5000
# Размер сообщений
message_size_limit = 52428800
mailbox_size_limit = 0
# Очереди
queue_directory = /var/spool/postfix
Замени mail.example.com и example.com на свои значения.
Что настроили:
Общие параметры:
smtpd_banner- приветствие сервераbiff = no- отключили уведомления comsatappend_dot_mydomain = no- не добавлять домен автоматическиcompatibility_level = 3.6- уровень совместимости
Имя и домен:
myhostname- полное имя сервераmydomain- основной доменmyorigin- от какого домена идут письма
Сеть:
inet_interfaces = all- слушаем на всех интерфейсахinet_protocols = ipv4- только IPv4 (если есть IPv6 - используйall)
Доверенные сети:
mynetworks- только localhost (расширим позже)
Локальная доставка:
mydestination = localhost- только для локалхоста- Остальное через виртуальные домены
Виртуальные домены:
virtual_mailbox_domains- список доменов (пока один)virtual_mailbox_base- корневая директория почтыvirtual_mailbox_maps- файл с ящикамиvirtual_alias_maps- файл с псевдонимамиvirtual_uid_maps / virtual_gid_maps- от имени кого хранить файлы
Лимиты:
message_size_limit- максимальный размер письма (50 MB)mailbox_size_limit = 0- без лимита на ящик
Создаем файлы для виртуальных ящиков
Файл vmailbox - список почтовых ящиков:
sudo nano /etc/postfix/vmailbox
Добавь:
admin@example.com example.com/admin/
user@example.com example.com/user/
Формат: email путь_относительно_virtual_mailbox_base/
Файл virtual - псевдонимы:
sudo nano /etc/postfix/virtual
Добавь:
postmaster@example.com admin@example.com
abuse@example.com admin@example.com
Формат: псевдоним куда_перенаправлять
Создай hash-таблицы:
sudo postmap /etc/postfix/vmailbox
sudo postmap /etc/postfix/virtual
Это создаст файлы .db - бинарные индексы для быстрого поиска.
Проверь конфиг:
sudo postfix check
Если ошибок нет - молчит. Если есть - исправляй.
Запускаем Postfix
sudo systemctl enable postfix
sudo systemctl start postfix
sudo systemctl status postfix
Должен быть active (running).
Проверяем порты
sudo ss -tulnp | grep master
Должно быть:
tcp LISTEN 0 100 0.0.0.0:25 0.0.0.0:* users:(("master",pid=...))
Postfix слушает порт 25.
Установка Dovecot
Ставим пакеты
sudo apt install -y \
dovecot-core \
dovecot-imapd \
dovecot-lmtpd
Что установили:
dovecot-core- ядроdovecot-imapd- IMAP серверdovecot-lmtpd- LMTP для приема почты от Postfix
Основной конфиг Dovecot
Открой:
sudo nano /etc/dovecot/dovecot.conf
Приведи к виду:
# Протоколы
protocols = imap lmtp
# Слушаем на всех интерфейсах IPv4
listen = *
# Рабочая директория
base_dir = /var/run/dovecot/
# Привет от сервера
login_greeting = Dovecot ready.
# Отключать клиентов при перезапуске
shutdown_clients = yes
# Подключаем конфиги из conf.d/
!include conf.d/*.conf
Настройка аутентификации
Открой:
sudo nano /etc/dovecot/conf.d/10-auth.conf
Найди и измени:
# Разрешаем plaintext auth (потом включим TLS)
disable_plaintext_auth = no
# Механизмы аутентификации
auth_mechanisms = plain login
В конце файла закомментируй:
#!include auth-system.conf.ext
И раскомментируй:
!include auth-passwdfile.conf.ext
Что сделали:
- Отключили системную аутентификацию (через /etc/passwd)
- Включили аутентификацию через файл паролей
Настройка файла паролей
Открой:
sudo nano /etc/dovecot/conf.d/auth-passwdfile.conf.ext
Приведи к виду:
passdb {
driver = passwd-file
args = scheme=CRYPT username_format=%u /etc/dovecot/users
}
userdb {
driver = static
args = uid=vmail gid=vmail home=/var/spool/mail/%d/%n
}
Что настроили:
passdb - база паролей:
driver = passwd-file- из файлаscheme=CRYPT- хеширование CRYPTusername_format=%u- формат логина (email)/etc/dovecot/users- путь к файлу
userdb - база пользователей:
driver = static- статические значения для всехuid=vmail gid=vmail- от имени кого работаемhome=/var/spool/mail/%d/%n- путь к ящику
Переменные:
%u- полный email (user@example.com)%d- домен (example.com)%n- локальная часть (user)
Настройка почтовых ящиков
Открой:
sudo nano /etc/dovecot/conf.d/10-mail.conf
Найди и измени:
# Формат и расположение почты
mail_location = maildir:/var/spool/mail/%d/%n
# От имени кого работаем
mail_uid = vmail
mail_gid = vmail
# Привилегированная группа
mail_privileged_group = vmail
# Разрешенные chroot-директории
valid_chroot_dirs = /var/spool/mail
Что настроили:
mail_location- формат Maildir, путь к ящикамmail_uid / mail_gid- UID/GID для работы с файламиvalid_chroot_dirs- где можно работать
Настройка LMTP
Открой:
sudo nano /etc/dovecot/conf.d/10-master.conf
Найди блок service lmtp и измени:
service lmtp {
unix_listener /var/spool/postfix/private/dovecot-lmtp {
mode = 0600
user = postfix
group = postfix
}
}
Найди блок service auth и добавь:
service auth {
# Postfix SMTP AUTH
unix_listener /var/spool/postfix/private/auth {
mode = 0666
user = postfix
group = postfix
}
# Для самого Dovecot
unix_listener auth-userdb {
mode = 0600
user = vmail
}
}
Что настроили:
service lmtp:
- Создали UNIX-сокет для Postfix
- Postfix будет передавать письма через него
service auth:
- Сокет для SMTP AUTH (авторизация в Postfix)
- Сокет для внутренних нужд Dovecot
Отключаем SSL (пока)
Открой:
sudo nano /etc/dovecot/conf.d/10-ssl.conf
Измени:
ssl = no
Потом включим с Let's Encrypt. Пока отключаем.
Создаем файл пользователей
sudo nano /etc/dovecot/users
Формат файла:
email:password_hash:5000:5000::
Создадим пользователя admin@example.com с паролем SecurePass123:
Генерируем хеш:
sudo doveadm pw -s CRYPT -p SecurePass123
Вернет что-то вроде:
{CRYPT}$6$random_salt$hash_here
Копируй только часть после {CRYPT}, т.е. $6$random_salt$hash_here.
Запиши в /etc/dovecot/users:
admin@example.com:$6$random_salt$hash_here:5000:5000::
Создай еще пользователя user@example.com с паролем UserPass456:
sudo doveadm pw -s CRYPT -p UserPass456
Добавь в файл:
admin@example.com:$6$hash1:5000:5000::
user@example.com:$6$hash2:5000:5000::
Формат строки:
email:hash:uid:gid:gecos:home:shell
У нас home и shell пустые, т.к. используем static userdb.
Права на файл
sudo chmod 640 /etc/dovecot/users
sudo chown root:dovecot /etc/dovecot/users
Запускаем Dovecot
sudo systemctl enable dovecot
sudo systemctl start dovecot
sudo systemctl status dovecot
Должен быть active (running).
Проверяем порты
sudo ss -tulnp | grep dovecot
Должно быть:
tcp LISTEN 0 100 0.0.0.0:143 0.0.0.0:* users:(("dovecot",pid=...))
Dovecot слушает порт 143 (IMAP).
Интеграция Postfix и Dovecot
Сейчас свяжем Postfix и Dovecot, чтобы:
- Postfix передавал письма в Dovecot через LMTP
- Postfix использовал Dovecot для SMTP AUTH
Настраиваем Postfix на LMTP
Открой:
sudo nano /etc/postfix/main.cf
Добавь в конец:
# Доставка через Dovecot LMTP
virtual_transport = lmtp:unix:private/dovecot-lmtp
# SMTP AUTH через Dovecot
smtpd_sasl_type = dovecot
smtpd_sasl_path = private/auth
smtpd_sasl_auth_enable = yes
smtpd_sasl_security_options = noanonymous
broken_sasl_auth_clients = yes
Что добавили:
virtual_transport:
- Письма для виртуальных доменов отправляем в Dovecot через LMTP
SMTP AUTH:
- Используем Dovecot для проверки логинов/паролей
noanonymous- запрет анонимного доступаbroken_sasl_auth_clients- поддержка старых клиентов
Настраиваем правила приема/отправки
Добавь туда же:
# Требовать HELO/EHLO
smtpd_helo_required = yes
# Правила HELO
smtpd_helo_restrictions =
permit_mynetworks,
permit_sasl_authenticated,
reject_invalid_helo_hostname,
reject_non_fqdn_helo_hostname,
reject_unknown_helo_hostname
# Правила получателя
smtpd_recipient_restrictions =
permit_mynetworks,
permit_sasl_authenticated,
reject_unauth_destination,
reject_non_fqdn_recipient,
reject_unknown_recipient_domain
# Правила отправителя
smtpd_sender_restrictions =
permit_mynetworks,
permit_sasl_authenticated,
reject_non_fqdn_sender,
reject_unknown_sender_domain
Что добавили:
smtpd_helo_required:
- Требуем команду HELO при подключении
smtpd_helo_restrictions:
permit_mynetworks- свои пропускаемpermit_sasl_authenticated- авторизованных пропускаемreject_invalid_helo_hostname- отклоняем невалидные именаreject_non_fqdn_helo_hostname- отклоняем неполные именаreject_unknown_helo_hostname- отклоняем неизвестные имена
smtpd_recipient_restrictions:
- Свои и авторизованных пропускаем
reject_unauth_destination- отклоняем для чужих доменов (защита от relay)reject_non_fqdn_recipient- отклоняем неполные адреса получателейreject_unknown_recipient_domain- отклоняем неизвестные домены
smtpd_sender_restrictions:
- Проверяем адреса отправителей
Настраиваем порт submission (587)
Открой:
sudo nano /etc/postfix/master.cf
Найди строку submission (должна быть закомментирована) и раскомментируй/измени:
submission inet n - y - - smtpd
-o syslog_name=postfix/submission
-o smtpd_tls_security_level=may
-o smtpd_sasl_auth_enable=yes
-o smtpd_reject_unlisted_recipient=no
-o smtpd_recipient_restrictions=permit_sasl_authenticated,reject
-o smtpd_relay_restrictions=permit_sasl_authenticated,reject
Что настроили:
- Порт 587 для отправки от клиентов
- Требуется авторизация
- TLS опционален (пока, потом сделаем обязательным)
Перезагружаем Postfix
sudo postfix reload
Проверь статус:
sudo systemctl status postfix
Проверь порты:
sudo ss -tulnp | grep master
Должно быть:
tcp LISTEN 0 100 0.0.0.0:25 ...
tcp LISTEN 0 100 0.0.0.0:587 ...
Первый тест
Сейчас проверим, работает ли базовая функциональность.
Тест 1: Отправка письма через telnet
Подключись к SMTP:
telnet localhost 25
Увидишь:
220 mail.example.com ESMTP
Выполни команды:
EHLO test.local
MAIL FROM:<admin@example.com>
RCPT TO:<user@example.com>
DATA
Subject: Test mail
This is a test message.
.
QUIT
Пояснение:
EHLO test.local- представляемсяMAIL FROM- от кого письмоRCPT TO- кому письмоDATA- начало тела письма.(точка на отдельной строке) - конец письмаQUIT- завершение сессии
Если все ОК, увидишь:
250 2.0.0 Ok: queued as 2CAB723BB4
Тест 2: Проверка доставки
Проверь логи Postfix:
sudo tail -f /var/log/mail.log
Ищи строки вроде этой:
Mar 16 19:54:34 mail postfix/lmtp[24548]: 634D423BB4: to=<user@example.com>, relay=mail.example.com[private/dovecot-lmtp], delay=21, delays=21/0.02/0.02/0.01, dsn=2.0.0, status=sent (250 2.0.0 <user@example.com> mPzKDMo1uGnlXwAAt3BTQQ Saved)
Проверь файловую систему:
sudo ls -la /var/spool/mail/example.com/user/new/
Должен появиться файл письма.
drwx--S--- 2 vmail vmail 4096 Mar 16 19:57 .
drwx--S--- 5 vmail vmail 4096 Mar 16 19:57 ..
-rw------- 1 vmail vmail 537 Mar 16 19:52 '1773679952.M948512P24098.mail.example.com,S=537,W=554'
-rw------- 1 vmail vmail 537 Mar 16 19:54 '1773680074.M217408P24549.mail.example.com,S=537,W=554'
-rw------- 1 vmail vmail 537 Mar 16 19:57 '1773680252.M311184P24696.mail.example.com,S=537,W=554'
Посмотри содержимое:
cat /var/spool/mail/example.com/user/new/*
Должен быть текст письма. Например:
Return-Path: <admin@example.com>
Delivered-To: user@example.com
Received: from mail.example.com
by mail.example.com with LMTP
id /8HxEHw2uGl4YAAAt3BTQQ
(envelope-from <admin@example.com>)
for <user@example.com>; Mon, 16 Mar 2026 19:57:32 +0300
Received: from test.local (localhost [127.0.0.1])
by mail.example.com (Postfix) with ESMTP id 06AAD23BBA
for <user@example.com>; Mon, 16 Mar 2026 18:37:51 +0300 (MSK)
Subject: Test mail
Message-Id: <20260316153757.06AAD23BBA@mail.example.com>
Date: Mon, 16 Mar 2026 18:37:51 +0300 (MSK)
From: admin@example.com
This is a test message.
Тест 3: Проверка IMAP
Подключись к Dovecot:
telnet localhost 143
Увидишь:
* OK [CAPABILITY IMAP4rev1 SASL-IR LOGIN-REFERRALS ID ENABLE IDLE LITERAL+ AUTH=PLAIN AUTH=LOGIN] Dovecot ready.
Выполни:
a1 LOGIN user@example.com UserPass456
a2 SELECT INBOX
a3 FETCH 1 BODY[]
a4 LOGOUT
Пояснение:
a1 LOGIN- авторизация (логин пароль)a2 SELECT INBOX- открыть папку INBOXa3 FETCH 1 BODY[]- получить тело первого письмаa4 LOGOUT- выход
Если авторизация прошла:
a1 OK [CAPABILITY IMAP4rev1 SASL-IR LOGIN-REFERRALS ID ENABLE IDLE SORT SORT=DISPLAY THREAD=REFERENCES THREAD=REFS THREAD=ORDEREDSUBJECT MULTIAPPEND URL-PARTIAL CATENATE UNSELECT CHILDREN NAMESPACE UIDPLUS LIST-EXTENDED I18NLEVEL=1 CONDSTORE QRESYNC ESEARCH ESORT SEARCHRES WITHIN CONTEXT=SEARCH LIST-STATUS BINARY MOVE SNIPPET=FUZZY PREVIEW=FUZZY STATUS=SIZE SAVEDATE LITERAL+ NOTIFY SPECIAL-USE] Logged in
Если письмо есть:
* 1 FETCH (FLAGS (\Seen \Recent) BODY[] {554}
Return-Path: <admin@example.com>
Delivered-To: user@example.com
Received: from mail.example.com
by mail.example.com with LMTP
id jdVeOFA1uGkiXgAAt3BTQQ
(envelope-from <admin@example.com>)
for <user@example.com>; Mon, 16 Mar 2026 19:52:32 +0300
Received: from test.local (localhost [127.0.0.1])
by mail.example.com (Postfix) with ESMTP id 2CAB723BB4
for <user@example.com>; Mon, 16 Mar 2026 18:33:46 +0300 (MSK)
Subject: Test mail
Message-Id: <20260316153352.2CAB723BB4@mail.example.com>
Date: Mon, 16 Mar 2026 18:33:46 +0300 (MSK)
From: admin@example.com
This is a test message.
)
Тест 4: Отправка с авторизацией
Для теста SMTP AUTH нужен base64 логина и пароля.
Генерируем:
echo -ne '\000admin@example.com\000SecurePass123' | base64
Где:
\000- нулевой байт (NULL, символ с кодом 0)username- логин (admin@example.com)\000- еще один NULLpassword- пароль (SecurePass123)
Вернет что-то вроде:
AGFkbWluQGV4YW1wbGUuY29tAFNlY3VyZVBhc3MxMjM=
Подключись к порту 587:
telnet localhost 587
Выполни:
EHLO test.local
AUTH PLAIN AGFkbWluQGV4YW1wbGUuY29tAFNlY3VyZVBhc3MxMjM=
MAIL FROM:<admin@example.com>
RCPT TO:<user@example.com>
DATA
Subject: Auth test
Test with auth.
.
QUIT
Если авторизация прошла:
235 2.7.0 Authentication successful
Письмо должно быть доставлено.
Что получилось
Сейчас у тебя:
Работает:
- Прием почты на порт 25
- Отправка почты через порт 587 с авторизацией
- Доступ к ящикам через IMAP на порту 143
- Виртуальные домены и ящики
- Псевдонимы
Не работает:
- Шифрование (все по открытому каналу)
- Проверка на вирусы
- Проверка на спам
- Защита от брутфорса
- Веб-интерфейс
- DKIM подписи
Это рабочий прототип, но не production-ready решение.
Типичные проблемы
Postfix не стартует
Проверь логи:
journalctl -u postfix -n 50
Частые причины:
- Опечатка в
main.cf - Порт 25 занят другим процессом
- Нет прав на директории
Проверь конфиг:
postfix check
Dovecot не стартует
Проверь логи:
journalctl -u dovecot -n 50
Частые причины:
- Опечатка в конфигах
- Неправильные права на
/etc/dovecot/users - Порт 143 занят
Проверь конфиг:
doveconf -n
Письма не доставляются
Проверь очередь Postfix:
postqueue -p
Если письма застряли - смотри причину:
tail -f /var/log/mail.log
Частые причины:
- Неправильный путь в
vmailbox - Нет прав на
/var/spool/mail - LMTP сокет не создан
Проверь сокет:
ls -la /var/spool/postfix/private/dovecot-lmtp
Должен быть.
Письма не доставляются: Permission denied
Ошибка в логах:
# Permission denied (euid=5000(vmail) missing +x perm: /var/spool/mail)
Проверь владельца реальной директории
ls -ld /var/spool/mail # Может быть симлинк
ls -ld /var/mail # Реальная директория
Исправь права
sudo chown -R vmail:vmail /var/mail
sudo chmod 755 /var/mail
Проверь вложенные директории
ls -la /var/mail/
IMAP не работает
Проверь авторизацию вручную:
doveadm auth test user@example.com UserPass456
Должно вернуть:
passdb: user@example.com auth succeeded
userdb: user@example.com
Если не работает:
- Проверь хеш пароля в
/etc/dovecot/users - Проверь права на файл
- Проверь логи Dovecot
SMTP AUTH не работает
Проверь сокет:
ls -la /var/spool/postfix/private/auth
Должен быть с правами 666 и владельцем postfix:postfix.
Проверь логи:
grep "sasl" /var/log/mail.log
Следующий шаг
В следующей части настроим защиту:
- Антивирус Amavis + ClamAV
- Антиспам SpamAssassin
- GreyListing через Postgrey
- Fail2ban против брутфорса
После этого сервер станет безопаснее и перестанет пропускать вирусы и спам.