1

I am using my company's smtp server to send email using python's email module. When I do that my email html is not rendering correctly. This is what I got:

  sender = 'abc@abc.com'
  # Create message container - the correct MIME type is multipart/alternative.
  msg = MIMEMultipart('multipart')
  msg['Subject'] = "My Report"
  msg['From'] = sender
  msg['To'] = ", ".join(recipients)

  # Create the body of the message using html in msg_body
  h = unicode(msg_body).encode("utf-8", "ignore")
  # Record the MIME type
  part = MIMEText(h, 'html')

  # Attach parts into message container.
  msg.attach(part)

  pngfiles = ['image.png']  
  for file in pngfiles:
      # Open the files in binary mode. 
      fp = open(file, 'rb')
      img = MIMEImage(fp.read())
      fp.close()
      msg.attach(img)

  # Send the message via local SMTP server.
  s = smtplib.SMTP('send.abc.com')  
  s.sendmail(msg.get("From"), recipients, msg.as_string())
  s.quit()

What should I do differently ?

Ankur Agarwal
  • 23,692
  • 41
  • 137
  • 208
  • Possibly related to [this](http://stackoverflow.com/questions/31715138/how-to-add-href-link-in-email-content-when-sending-email-through-smtplib)? – TigerhawkT3 Jul 30 '15 at 21:44
  • My subtype is already 'html' as you can see. – Ankur Agarwal Jul 30 '15 at 21:54
  • The issue was that I had to set charset as 'utf-8'. From the docs: **If _text(first argument) is unicode, it is encoded using the output_charset of _charset, otherwise it is used as-is.** Default is us-ascii. In my case first argument was unicode. part = MIMEText(h, 'html', 'utf-8') – Ankur Agarwal Jul 30 '15 at 23:13

1 Answers1

5

Just wanted to throw out there how easy it is to send emails with attachments using yagmail (full disclose: I'm the developer). My philosophy was to have to only once figure out how to deal with the MIME stuff, and then never look back.

You can use the following 3 lines to send your email:

import yagmail
yag = yagmail.SMTP(sender, your_password)

# assuming your undefined "msg_body" is just some message (string)
yag.send(recipients, 'My report', contents = [msg_body, '/local/path/to/image.png'])

You can do all kind of things with contents: if you have a list of stuff it will nicely combine it. For example, a list of filenames will make it so that it will attach all. Mix it with some message, and it will have a message.

Any string that is a valid file will be attached, other strings are just text.

It will nicely handle HTML code, images (inline), text and any other files. And yes, I'm quite proud of it.

I encourage you to read the github documentation to see other nice features, for example you do not have to have your password / username in the script (extra safety) by using the keyring. Set it up once, and you'll be happy....

Oh yea, to install, you can use:

pip install yagmail  # python 2
pip3 install yagmail # python 3
PascalVKooten
  • 20,643
  • 17
  • 103
  • 160