14.3. smtpd — smtp 服务器 | 邮件模块 |《python 3 标准库实例教程》| python 技术论坛-380玩彩网官网入口
目的:包括用于实现smtp服务器的类。
smtpd
模块包括用于构建简单邮件传输协议服务器的类。它是[smtplib
](“ smtplib:简单邮件传输协议客户端”使用的协议的服务器端。 )。
邮件服务器基类
所有提供的示例服务器的基类是smtpserver
。它处理与客户端的通信,接收传入的数据,并提供了一个方便的钩子,可以在消息完全可用后进行覆盖以对其进行处理。
构造函数参数是用于侦听连接的本地地址,也是应将代理消息传递到的远程地址。提供方法process_message()
作为挂钩,以被派生类覆盖。当完全接收到消息并给出以下参数时,将调用它:
peer
客户地址,一个包含ip和传入端口的元组。
mailfrom
邮件信封中的“发件人”信息,在邮件传递时由客户端提供给服务器。不一定在所有情况下都匹配
from
标题。
rcpttos
邮件信封中的收件人列表。同样,这并不总是与
to
标头匹配,尤其是在收件人被盲目抄写的情况下。
data
完整的rfc 5322消息正文
process_message()
的默认实现会引起notimplementederror
。下一个示例定义一个子类,该子类重写用于打印有关接收到的消息的信息的方法。
smtpd_custom.py
import smtpd
import asyncore
class customsmtpserver(smtpd.smtpserver):
def process_message(self, peer, mailfrom, rcpttos, data):
print('receiving message from:', peer)
print('message addressed from:', mailfrom)
print('message addressed to :', rcpttos)
print('message length :', len(data))
server = customsmtpserver(('127.0.0.1', 1025), none)
asyncore.loop()
smtpserver
使用asyncore
,因此要运行服务器调用asyncore.loop()
。
需要一个客户端来演示服务器。可以是[smtplib
](“ smtplib:简单邮件传输协议客户端。”)中的示例之一。适用于创建客户端以将数据发送到在端口1025上本地运行的测试服务器。
smtpd_senddata.py
import smtplib
import email.utils
from email.mime.text import mimetext
# 创建消息
msg = mimetext('this is the body of the message.')
msg['to'] = email.utils.formataddr(('recipient',
'[email protected]'))
msg['from'] = email.utils.formataddr(('author',
'[email protected]'))
msg['subject'] = 'simple test message'
server = smtplib.smtp('127.0.0.1', 1025)
server.set_debuglevel(true) # 显示与服务器的通信
try:
server.sendmail('[email protected]',
['[email protected]'],
msg.as_string())
finally:
server.quit()
要测试程序,请在一个终端中运行smtpd_custom.py
,在另一终端中运行smtpd_senddata.py
。
$ python3 smtpd_custom.py
receiving message from: ('127.0.0.1', 58541)
message addressed from: [email protected]
message addressed to : ['[email protected]']
message length : 229
smtpd_senddata.py
的调试输出显示了与服务器的所有通信。
$ python3 smtpd_senddata.py
send: 'ehlo 1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.
0.0.0.0.0.0.ip6.arpa..'
reply: b'250-1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0
.0.0.0.0.0.0.ip6.arpa..'
reply: b'250-size 33554432..'
reply: b'250 help..'
reply: retcode (250); msg: b'1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0
.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa.size 33554432.help'
send: 'mail from:<[email protected]> size=236..'
reply: b'250 ok..'
reply: retcode (250); msg: b'ok'
send: 'rcpt to:<[email protected]>..'
reply: b'250 ok..'
reply: retcode (250); msg: b'ok'
send: 'data..'
reply: b'354 end data with ...'
reply: retcode (354); msg: b'end data with .'
data: (354, b'end data with .')
send: b'content-type: text/plain; charset="us-ascii"..mime-ver
sion: 1.0..content-transfer-encoding: 7bit..to: recipient [email protected]>..from: author <[email protected]>..su
bject: simple test message....this is the body of the messag
e......'
reply: b'250 ok..'
reply: retcode (250); msg: b'ok'
data: (250, b'ok')
send: 'quit..'
reply: b'221 bye..'
reply: retcode (221); msg: b'bye'
要停止服务器,请按ctrl-c
。
调试服务器
上一个示例显示了process_message()
的参数,但是smtpd
还包括专门为更完整的调试而设计的服务器,称为debuggingserver
。它将整个传入消息打印到控制台,然后停止处理(它不会将消息代理到真实的邮件服务器)。
smtpd_debug.py
import smtpd
import asyncore
server = smtpd.debuggingserver(('127.0.0.1', 1025), none)
asyncore.loop()
使用以前的smtpd_senddata.py
客户端程序,debuggingserver
的输出为:
---------- message follows ----------
content-type: text/plain; charset="us-ascii"
mime-version: 1.0
content-transfer-encoding: 7bit
to: recipient <[email protected]>
from: author <[email protected]>
subject: simple test message
x-peer: 127.0.0.1
this is the body of the message.
------------ end message ------------
## 代理服务器
pureproxy
类实现了一个简单的代理服务器。传入的消息将作为构造函数的参数提供给上游,转发给服务器。
警告
smtpd
的标准库文档说:“运行此程序有很大的机会使您进入开放中继,因此请小心。”
设置代理服务器的步骤与调试服务器相似。
smtpd_proxy.py
import smtpd
import asyncore
server = smtpd.pureproxy(('127.0.0.1', 1025), ('mail', 25))
asyncore.loop()
但是,它不会输出任何输出,因此要验证其是否正常运行,请查看邮件服务器日志。
aug 20 19:16:34 homer sendmail[6785]: m9jngxjb006785:
from=<[email protected]>, size=248, class=0, nrcpts=1,
msgid=<[email protected]>,
proto=esmtp, daemon=mta, relay=[192.168.1.17]
另请参见
-
-[smtplib
](“ smtplib:简单邮件传输协议客户端。”)–提供了客户端界面。
-电子邮件
-解析电子邮件。
-asyncore
-用于编写异步服务器的基本模块。
-– internet邮件格式*,定义电子邮件格式。
-–取代rfc 2822。
本译文仅用于学习和交流目的,转载请务必注明文章译者、出处、和本文链接
我们的翻译工作遵照 cc 协议,如果我们的工作有侵犯到您的权益,请及时联系380玩彩网官网入口。