python2.7实现邮件发送功能

yipeiwu_com6年前Python基础

要想实现一个能够发送带有文本、图片、附件的python程序,首先要熟悉两大模块:

email以及smtplib

然后对于MIME(邮件扩展)要有一定认知,因为有了扩展才能发送附件以及图片这些媒体或者非文本信息

最后一个比较细节的方法就是MIMEMultipart,要理解其用法以及对应参数所实现的功能区别

发送邮件三部曲:

创建协议对象
连接邮件服务器
登陆并发送邮件

from email.header import Header
from email.mime.base import MIMEBase
from email.mime.text import MIMEText
import mimetypes

from email.mime.multipart import MIMEMultipart
import os
import smtplib

from email import Encoders as email_encoders


class Message(object):
 def __init__(self, from_addr, to_addr, subject="", html="", text=None, cc_addr=[], attachment=[]):

  self.from_addr = from_addr
  self.subject = subject

  if to_addr:
   if isinstance(to_addr, list):
    self.to_addr = to_addr
   else:
    self.to_addr = [d for d in to_addr.split(',')]
  else:
   self.to_addr = []

  if cc_addr:
   if isinstance(cc_addr, list):
    self.cc_addr = cc_addr
   else:
    self.cc_addr = [d for d in cc_addr.split(',')]
  else:
   self.cc_addr = []

  if html is not None:
   self.body = html
   self.body_type = "html"
  else:
   self.body = text
   self.body_type = "plain"

  self.parts = []
  if isinstance(attachment, list):
   for file in attachment:
    self.add_attachment(file)

 def add_attachment(self, file_path, mimetype=None):
  """
   If *mimetype* is not specified an attempt to guess it is made. If nothing
   is guessed then `application/octet-stream` is used.
  """
  if not mimetype:
   mimetype, _ = mimetypes.guess_type(file_path)

  if mimetype is None:
   mimetype = 'application/octet-stream'

  type_maj, type_min = mimetype.split('/')
  with open(file_path, 'rb') as fh:
   part_data = fh.read()

   part = MIMEBase(type_maj, type_min)
   part.set_payload(part_data)
   email_encoders.encode_base64(part)

   part_filename = os.path.basename(file_path)
   part.add_header('Content-Disposition', 'attachment; filename="%s"'
       % part_filename)
   part.add_header('Content-ID', part_filename)

   self.parts.append(part)

 def __to_mime_message(self):
  """Returns the message as
  :py:class:`email.mime.multipart.MIMEMultipart`."""

  ## To get the message work in iOS, you need use multipart/related, not the multipart/alternative
  msg = MIMEMultipart('related')
  msg['Subject'] = self.subject
  msg['From'] = self.from_addr
  msg['To'] = ','.join(self.to_addr)

  if len(self.cc_addr) > 0:
   msg['CC'] = ','.join(self.cc_addr)

  body = MIMEText(self.body, self.body_type)
  msg.attach(body)

  # Add Attachment
  for part in self.parts:
   msg.attach(part)

  return msg

 def send(self, smtp_server='localhost'):

  smtp = smtplib.SMTP()
  smtp.connect(smtp_server)
  smtp.sendmail(from_addr=self.from_addr, to_addrs=self.to_addr + self.cc_addr, msg=self.__to_mime_message().as_string())
  smtp.close()

对于实际发送程序,要注意个参数的类型,比如from_addr是字符串,to_addr和cc_addr以及attachment都是列表

from mail_base import Message
import datetime
from_addr = 'xxx'
mail_to = 'xxx'


def send_go():
 time_now = datetime.datetime.now().strftime('%Y-%m-%d %H:%M')
 attach_files = ['testcsv.xlsm','test1.jpg','test2.jpg','test3.jpg']
 mail_msg = """
  <p>Hi Lockey:</p>
  <p><img src="cid:test1.jpg"></p>####要特别注意这里,正文插入图片的特殊格式!!!
  <hr/>
  <p style="text-indent:16px">Here is the latest paper link from The Economist, you can click <a href="https://lockeycheng.github.io/iooi/index.html" rel="external nofollow" >Go</a> for a full view!</p>
  <hr/>
  <p>Best Regards</p>
  <p>
   Any question please mail to <a href='mailto:iooiooi23@163.com'>Lockey23</a>.
  </p>
  <p>Sent at {} PST</p>
  """.format(time_now)
 subject = '[Halo] - ' + 'A new paper published!'
 msg = Message(from_addr=from_addr,
     to_addr=[mail_to],
     cc_addr=[mail_to],
     subject=subject,
     attachment=attach_files,
     html=mail_msg
     )
 msg.send()

if __name__ == '__main__':
 send_go()

对于测试程序我们命名为sendGo.py,运行测试程序

~$ python sendGo.py

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持【听图阁-专注于Python设计】。

相关文章

python将字典列表导出为Excel文件的方法

python将字典列表导出为Excel文件的方法

将如下的字典列表内容导出为Excel表格文件形式: 关于上图字典列表的写入,请参考文章:/post/169088.htm python将字典列表导出为Excel文件的方法,如下所示:...

python 获取文件下所有文件或目录os.walk()的实例

在python3.6版本中去掉了os.path.walk()函数 os.walk() 函数声明:walk(top,topdown=True,oneerror=None) 1、参数top表...

python的Crypto模块实现AES加密实例代码

python的Crypto模块实现AES加密实例代码

本文主要探索的是python的Crypto模块实现AES加密,分享了具体实现代码,下面看看具体内容。 学了使用Crypto模块的AES来加密文件,现在记录下来便于后边儿查看。 在刚开始...

numpy:np.newaxis 实现将行向量转换成列向量

np.newaxis 新增一个轴 如何将数组[0,1,2]转换成列向量 用ndarray[: , np.newaxis] 代码实质就是将原本的(0,1,2)移到行上,然后新增一列 其实...

在Python中用has_key()方法查找键是否存在的教程

 如果给定的键在字典可用,has_key()方法返回true,否则返回false。 语法 以下是has_key()方法的语法: dict.has_key(key) 参...