21.18. smtpd
- SMTP服务器¶
源代码: Lib / smtpd.py
此模块提供了几个类来实现SMTP(电子邮件)服务器。
存在几个服务器实现;一个是通用的无用的实现,可以被覆盖,而另外两个提供特定的邮件发送策略。
此外,SMTPChannel可以扩展为实现与SMTP客户端的非常具体的交互行为。
代码支持 RFC 5321以及 RFC 1870 SIZE和 RFC 6531 SMTPUTF8扩展。
21.18.1. SMTPServer Objects¶
- class
smtpd.
SMTPServer
(localaddr, remoteaddr, data_size_limit=33554432, map=None, enable_SMTPUTF8=False, decode_data=True)¶ 创建一个新的
SMTPServer
对象,并绑定到本地地址localaddr。它将remoteadd作为上游的SMTP中继。它继承自asyncore.dispatcher
,并在实例化时将自身插入到asyncore
的事件循环。data_size_limit指定将在
DATA
命令中接受的最大字节数。None
或0
的值表示无限制。map是用于连接的套接字映射(最初为空的字典是一个合适的值)。如果未指定,则使用
asyncore
全局套接字映射。enable_SMTPUTF8确定是否应启用
SMTPUTF8
扩展(如 RFC 6531中定义)。默认值为False
。如果设置为True
,则decode_data必须为False
(否则会引发错误)。当True
时,SMTPUTF8
被接受作为MAIL
命令的参数,并且当存在时传递到process_message()
在kwargs['mail_options']
列表中。decode_data指定是否应使用UTF-8解码SMTP事务的数据部分。出于向后兼容性的原因,默认值为
True
,但在Python 3.6中将更改为False
;明确指定关键字值以避免DeprecationWarning
。When decode_data is set toFalse
the server advertises the8BITMIME
extension (RFC 6152), accepts theBODY=8BITMIME
parameter to theMAIL
command, and when present passes it toprocess_message()
in thekwargs['mail_options']
list.-
process_message
(peer, mailfrom, rcpttos, data, **kwargs)¶ 引发
NotImplementedError
异常。在子类中重写此方法以对邮件做一些有用的事情。无论传递给构造函数的是什么remoteaddr,它将作为_remoteaddr
属性提供。对等体是远程主机的地址,mailfrom是包络发起者,rcpttos是包络收件人,数据包含电子邮件内容的字符串(应为 RFC 5321格式)。如果decode_data构造函数关键字设置为
True
,则数据参数将是Unicode字符串。如果设置为False
,它将是一个字节对象。kwargs是包含附加信息的字典。除非将
decode_data=False
或enable_SMTPUTF8=True
中的至少一个作为init参数给出,否则它为空,在这种情况下,它包含以下键:- mail_options:
- a list of all received parameters to the
MAIL
command (the elements are uppercase strings; example:['BODY=8BITMIME', 'SMTPUTF8']
). - rcpt_options:
- same as mail_options but for the
RCPT
command. Currently noRCPT TO
options are supported, so for now this will always be an empty list.
process_message
的实现应使用**kwargs
声明接受任意关键字参数,因为未来的功能增强可能会向kwargs字典添加键。返回
None
以请求正常的250 确定
响应;否则返回 RFC 5321格式的所需响应字符串。
-
channel_class
¶ 在子类中覆盖此项,以使用自定义
SMTPChannel
来管理SMTP客户端。
版本3.4中的新功能: 映射构造函数参数。
在3.5版本中更改: localaddr和remoteaddr现在可以包含IPv6地址。
New in version 3.5: the decode_data and enable_SMTPUTF8 constructor arguments, and the kwargs argument to
process_message()
when one or more of these is specified.-
21.18.2. DebuggingServer Objects¶
- class
smtpd.
DebuggingServer
(localaddr, remoteaddr)¶ 创建一个新的调试服务器。参数与
SMTPServer
相同。邮件将被丢弃,并打印到标准输出。
21.18.3. PureProxy Objects¶
- class
smtpd.
PureProxy
(localaddr, remoteaddr)¶ 创建一个新的纯代理服务器。参数与
SMTPServer
相同。一切都将传送到remoteaddr。注意运行该对象和容易令你变成一个开放中继,所以请小心。
21.18.4. MailmanProxy Objects¶
- class
smtpd.
MailmanProxy
(localaddr, remoteaddr)¶ 创建一个新的纯代理服务器。参数与
SMTPServer
相同。一切都将传送到remoteaddr,除非当地邮差配置知道一个地址,在这种情况下它将通过邮递员处理。注意运行该对象和容易令你变成一个开放中继,所以请小心。
21.18.5. SMTPChannel Objects¶
- class
smtpd.
SMTPChannel
(server, conn, addr, data_size_limit=33554432, map=None, enable_SMTPUTF8=False, decode_data=True)¶ 创建一个新的
SMTPChannel
对象,用于管理服务器和单个SMTP客户端之间的通信。conn和addr是根据下面描述的实际变量。
data_size_limit指定将在
DATA
命令中接受的最大字节数。None
或0
的值表示无限制。enable_SMTPUTF8确定是否应启用
SMTPUTF8
扩展(如 RFC 6531中定义)。默认值为False
。如果enable_SMTPUTF8和decode_data同时设置为True
,则会产生ValueError
可以在map中指定字典,以避免使用全局套接字映射。
decode_data指定是否应使用UTF-8解码SMTP事务的数据部分。出于向后兼容性的原因,默认值为
True
,但会在Python 3.6中更改为False
。明确指定关键字值,以避免DeprecationWarning
。要使用自定义SMTPChannel实现,您需要覆盖
SMTPServer
的SMTPServer.channel_class
。在版本3.5中已更改:添加了decode_data和enable_SMTPUTF8参数。
SMTPChannel
具有以下实例变量:-
smtp_server
¶ 保留产生此频道的
SMTPServer
。
-
conn
¶ 保存连接到客户端的套接字对象。
-
addr
¶ 保存客户端的地址,
socket.accept
返回的第二个值
-
received_lines
¶ 保存从客户端接收的行字符串(使用UTF-8解码)的列表。这些线将它们的
"\r\n"
线结束翻译为"\n"
。
-
smtp_state
¶ 保持通道的当前状态。This will be either
COMMAND
initially and thenDATA
after the client sends a “DATA” line.
-
seen_greeting
¶ 保存客户端在其“HELO”中发送的包含问候语的字符串。
-
mailfrom
¶ 保留一个字符串,其中包含来自客户端的“MAIL FROM:”行中标识的地址。
-
rcpttos
¶ 保存来自客户端的包含在“RCPT TO:”行中标识的地址的字符串列表。
-
received_data
¶ 保存包含客户端在DATA状态期间发送的所有数据的字符串,但不包括终止
"\r\n.\r\n"
。
-
fqdn
¶ 保存由
socket.getfqdn()
返回的服务器的完全限定域名。
SMTPChannel
通过在从客户端接收到命令行时调用名为smtp_<command>
的方法来操作。内置在SMTPChannel
类中的是处理以下命令(并适当地响应它们)的方法:命令 所采取的行动 HELO 接受来自客户端的问候语,并将其存储在 seen_greeting
中。将服务器设置为基本命令模式。EHLO 接受来自客户端的问候语,并将其存储在 seen_greeting
中。将服务器设置为扩展命令模式。NOOP 不采取任何行动。 放弃 干净地关闭连接。 邮件 接受“MAIL FROM:”语法,并将提供的地址存储为 mailfrom
。在扩展命令模式下,接受 RFC 1870 SIZE属性,并根据data_size_limit的值进行适当响应。RCPT 接受“RCPT TO:”语法,并将提供的地址存储在 rcpttos
列表中。RSET 重置 mailfrom
,rcpttos
和received_data
,但不是问候语。数据 将内部状态设置为 DATA
,并在received_data
中存储来自客户端的剩余行,直到终止符"\r\n.\r\n"
帮帮我 返回有关命令语法的最少信息 VRFY 返回代码252(服务器不知道地址是否有效) EXPN 报告命令未实现。 -