一个简单的邮件发送的例子,代码如下:
import smtplib
from email.mime.text import MIMEText
smtp_server = 'smtp.qq.com'
email_user = '[email protected]'
email_pass = ''()
sender = email_user
receiver = '[email protected]'
msg = MIMEText(u'test')
server = smtplib.SMTP_SSL(smtp_server, 465)
server.set_debuglevel(1)
server.login(email_user, email_pass)
server.sendmail(sender, receiver, msg.as_string())
server.quit()
print('finish')
但是我在自己电脑上面执行这个代码的时候竟然报错了
从错误信息上来看是因为我的代码里面有中文字符串导致编码格式有问题,但是本身这个代码里面是没有任何中文输入输出的,所以只能单步调试,调试哪里出现了中文入参。
当调试到:
fqdn = socket.getfqdn()
这里下一步的时候会跳转到这里
并且input入参里面有中文名,查看前后文发现这里是获取了我的计算机名。然后在这里抛出异常
try:
hostname, aliases, ipaddrs = gethostbyaddr(name)
except error:
pass
因为我后面又写了一段测试程序来验证这个问题:
import socket
a = socket.gethostname()
print(a)
b = socket.gethostbyaddr(a)
print(b)
执行出来的结果和上面的一直,socket.gethostaddr()的时候传入的中文字符串会抛出错误。
这里可以看出来socket.gethostbyaddr是直接将 张彬彬 三个汉字直接作为入参传入的,而没有经过编码处理,所以我改了socket.py里面的代码,有两个改法:
1、hostname, aliases, ipaddrs = gethostbyaddr(name.encode())
传入编码后的值,这样下面识别的时候还是识别张彬彬这三个汉字,只是编码过后的结果而已。
2、hostname, aliases, ipaddrs = gethostbyaddr(repr(name))
使用repr方法将name转为机器可以识别的字符串格式,这里就可以很明显的区分str和repr的区别,使用repr之后结果正常,而是用str()则不可行,我的猜想是gethostbyaddr就已经是面向底层的东西了,所以需要编码过后的或者面向底层的格式才可以,所以repr返回的结果可以被接受,而str不可行。因为gethostbyaddr()这个方法的实现我已经找不到了,所以猜测是调用的底层库。
这点欢迎大家讨论,我只是用python3.6.3测试出来的结果。