docker-compose 中的 Postfix“name=dovecot 的名称服务错误”

docker-compose 中的 Postfix“name=dovecot 的名称服务错误”

语境

我的docker-compose --version是2.13.0

我已经创建了一个复制器https://github.com/Losmoges/postfix-dovecot-lmtp-reproducer

我的试用版在 Compose 文件中有三个 docker 服务:postfix、dovecot 和 client。它们通过 bridge 驱动程序共享一个网络。

  • Postfix 配置为通过virtual_transport = lmtp:dovecot:24main.cf 配置中的设置将传入的电子邮件转发到 dovecot。
  • Dovecot 配置为通过dovecot.conf 配置中的//service lmtp设置接收连接。inet_listener lmtpport = 24
  • 我可以通过在客户端容器中执行 Postfix 来发送电子邮件。其 msmtp 配置为通过配置文件进行连接。echo test | msmtp [email protected]host postfixmsmtprc

这会在 Postfix 队列中产生以下结果,我可以通过postqueue -p在 Postfix 容器中运行来检查它。

错误

-Queue ID-  --Size-- ----Arrival Time---- -Sender/Recipient-------
DEC4F3DCBE      245 Fri Dec 16 19:41:17  [email protected]
(Host or domain name not found. Name service error for name=dovecot type=A: Host not found, try again)
                                         [email protected]

解决方法

当我通过找到 Dovecot 容器的 IP 地址docker inspect并将其输入到 Postfix 配置中时,例如virtual_transport = lmtp:172.18.0.4:24,一切都按预期工作。在这种情况下,命令postqueue -p给出Mail queue is empty(通过 msmtp 发送电子邮件后)

问题

为什么不起作用virtual_transport = lmtp:dovecot:24?我配置错误了吗?任何形式的名称查找(例如nslookup dovecot在 Postfix 容器中安装 dnsutils 后)都可以正常工作并返回 Dovecot 容器的 IP 地址。Postfix 是否执行其自己的单独域名解析?如果是,我如何强制它使用默认域名解析?

编辑:答案中的解决方案

我在 Postfix 镜像的 Dockerfile 中添加了以下行

RUN sed -i'' -e 's/^lmtp .*/lmtp      unix  -       -       n       -       -       lmtp/g' /etc/postfix/master.cf

答案1

为什么 virtual_transport = lmtp:dovecot:24 不起作用?

在您的 中master.cf,您已lmtp配置为在环境中运行chroot

# ==========================================================================
# service type  private unpriv  chroot  wakeup  maxproc command + args
#               (yes)   (yes)   (no)    (never) (100)
lmtp      unix  -       -       n       -       -       lmtp

环境chroot无法访问容器的/etc/resolv.conf,因此它不知道如何解析主机名。lmtp 配置默认在 chrooted 环境中运行,因为典型配置使用 unix 套接字进行通信,因此主机名解析不是问题。

最简单的修复方法是配置lmtp为不在chroot环境中运行:

lmtp      unix  -       -       y       -       -       lmtp

经过此更改,邮件可以正确传递:

postfix_1  | Dec 16 21:47:15 8d74be7a5951 postfix/smtpd[598]: connect from unknown[172.28.0.1]
postfix_1  | Dec 16 21:47:15 8d74be7a5951 postfix/smtpd[598]: 9131638672DA: client=unknown[172.28.0.1]
postfix_1  | Dec 16 21:47:15 8d74be7a5951 postfix/qmgr[582]: 9131638672DA: from=<[email protected]>, size=434, nrcpt=1 (queue active)
postfix_1  | Dec 16 21:47:15 8d74be7a5951 postfix/smtpd[598]: disconnect from unknown[172.28.0.1] ehlo=1 mail=1 rcpt=1 data=1 quit=1 commands=5
dovecot_1  | Dec 16 21:47:15 lmtp(16): Info: Connect from 172.28.0.3
dovecot_1  | Dec 16 21:47:15 lmtp([email protected])<16><+A19J2PnnGMQAAAAqj6rOA>: Info: msgid=<20221216164715.079491@rocket>: saved mail to INBOX
postfix_1  | Dec 16 21:47:15 8d74be7a5951 postfix/lmtp[597]: 9131638672DA: to=<[email protected]>, relay=dovecot[172.28.0.2]:24, delay=0.09, delays=0.07/0/0/0.01, dsn=2.0.0, status=sent (250 2.0.0 <[email protected]> +A19J2PnnGMQAAAAqj6rOA Saved)
dovecot_1  | Dec 16 21:47:15 lmtp(16): Info: Disconnect from 172.28.0.3: Logged out (state=READY)
postfix_1  | Dec 16 21:47:15 8d74be7a5951 postfix/qmgr[582]: 9131638672DA: removed

一种替代方法是在dovecotpostfix容器之间配置一个共享的 unix 套接字,并使用它进行通信而不是 inet 连接。

第二种选择是在与 postfix 容器相同的网络命名空间中运行 lmtp 容器,在这种情况下您可以更简单地使用主机名localhost

相关内容