Programmatically sending an email is really a good tool for developer’s paraphernalia. This is really handy when one automates task and wants to get notified by an email for success or failure. Lately I have written Python script to automate some jobs and incorporated method to send email notification. I thought to share this simple script here so my readers can get benefited.

Using local MTA-SMTP connection

#!/usr/bin/env python
import smtplib
from email.mime.text import MIMEText

EMAIL_SUBJECT = "Email from Python script"
EMAIL_FROM = "notification@code4reference.com"
EMAIL_RECEIVERS = ['your_email@gmail.com']

def listToStr(lst):
    """This method makes comma separated list item string"""
    return ','.join(lst)

def send_email(msg):
    """This method sends an email""" 
  
    msg_header = "From: " + EMAIL_FROM + "\n" + \
                 "To: " + listToStr(EMAIL_RECEIVERS) + "\n" + \
                 "Subject: " + EMAIL_SUBJECT + "\n"
    msg_body =  msg_header + msg

    try:
      #establish a connection with the local SMTP server.
      smtpObj = smtplib.SMTP('localhost')
      #Now send the email
      smtpObj.sendmail(EMAIL_FROM, EMAIL_RECEIVERS, msg_body)
      #Close the connection and session.
      smtpObj.quit()
    except SMTPException as error:
      print "Error: unable to send email :  {err}".format(err=error)

def main():
    """This is a simple main() function which demonstrate sending of email using smtplib."""
    send_email("Test email was generated by Python using smtplib and email libraries");

if __name__ == "__main__":
   """If this script is run as stand alone then call main() function."""
    main()

Before running this script make sure your system has Mail Transfer Agent(MTA) configured. If it is not then read this post to configure Mail-server on Ubuntu 12.04.
If you are not interested to configure your own MTA then you can probably used the SMTP service provided by other Mail server e.g Gmail, yahoo, etc. But these service providers put some email limits to control spamming. If your application/script is sending email more than this limit then the service can detect it as spamming and may lock your account. You can find gmail email limit from here whereas Yahoo SMTP limit is provided here.

Using Gmail SMTP

Google SMTP server is located here smtp.gmail.com. According to the standard the SMTP port is 25 but Gmail doesn’t use this port instead it uses port 587. Script uses this information to establish a connection and sends an email.

#!/usr/bin/env python
from smtplib import SMTP
from smtplib import SMTPException
from email.mime.text import MIMEText
import sys

#Global varialbes
EMAIL_SUBJECT = "Email from Python script"
EMAIL_RECEIVERS = ['receiverId@gmail.com']
EMAIL_SENDER  =  'senderId@gmail.com'
GMAIL_SMTP = "smtp.gmail.com"
GMAIL_SMTP_PORT = 587
TEXT_SUBTYPE = "plain"

def listToStr(lst):
    """This method makes comma separated list item string"""
    return ','.join(lst)

def send_email(content, pswd):
    """This method sends an email"""     
    
    #Create the message
    msg = MIMEText(content, TEXT_SUBTYPE)
    msg["Subject"] = EMAIL_SUBJECT
    msg["From"] = EMAIL_SENDER
    msg["To"] = listToStr(EMAIL_RECEIVERS)
    
    try:
      smtpObj = SMTP(GMAIL_SMTP, GMAIL_SMTP_PORT)
      #Identify yourself to GMAIL ESMTP server.
      smtpObj.ehlo()
      #Put SMTP connection in TLS mode and call ehlo again.
      smtpObj.starttls()
      smtpObj.ehlo()
      #Login to service
      smtpObj.login(user=EMAIL_SENDER, password=pswd)
      #Send email
      smtpObj.sendmail(EMAIL_SENDER, EMAIL_RECEIVERS, msg.as_string())
      #close connection and session.
      smtpObj.quit();
    except SMTPException as error:
      print "Error: unable to send email :  {err}".format(err=error)

def main(pswd):
    """This is a simple main() function which demonstrates sending of email using smtplib."""
    send_email("Test email was generated by Python using smtplib and email libraries", pswd);

if __name__ == "__main__":
    """If this script is executed as stand alone then call main() function."""
    if len(sys.argv) == 2:
        main(sys.argv[1])
    else:
        print "Please provide password"
        sys.exit(0)

If scripts uses SMTP to send emails then Gmail can detect it as suspicious activity and it may ask you to change the password. This is a kind-of-annoying. To avoid such issues it always suggested to configure your own MTA.

Using Yahoo SMTP

Yahoo exposed SMTP service here smtp.mail.yahoo.com and 465 port. Unlike Gmail, It expects a SSL SMTP connection.

#!/usr/bin/env python
from smtplib import SMTP
from smtplib import SMTP_SSL
from smtplib import SMTPException
from email.mime.text import MIMEText
import sys

#Global varialbes
EMAIL_SUBJECT = "Email from Python script"
EMAIL_RECEIVERS = ['receiverId@gmail.com']
EMAIL_SENDER  =  'senderId@yahoo.com'
TEXT_SUBTYPE = "plain"

YAHOO_SMTP = "smtp.mail.yahoo.com"
YAHOO_SMTP_PORT = 465

def listToStr(lst):
    """This method makes comma separated list item string"""
    return ','.join(lst)

def send_email(content, pswd):
    """This method sends an email""" 
    msg = MIMEText(content, TEXT_SUBTYPE)
    msg["Subject"] = EMAIL_SUBJECT
    msg["From"] = EMAIL_SENDER
    msg["To"] = listToStr(EMAIL_RECEIVERS)
    
    try:
      #Yahoo allows SMTP connection over SSL. 
      smtpObj = SMTP_SSL(YAHOO_SMTP, YAHOO_SMTP_PORT)
      #If SMTP_SSL is used then ehlo and starttls call are not required.
      smtpObj.login(user=EMAIL_SENDER, password=pswd)
      smtpObj.sendmail(EMAIL_SENDER, EMAIL_RECEIVERS, msg.as_string())
      smtpObj.quit();
    except SMTPException as error:
      print "Error: unable to send email :  {err}".format(err=error)

def main(pswd):
    """This is a simple main() function which demonstrates sending of email using smtplib."""
    send_email("Test email was generated by Python using smtplib and email libraries", pswd);

if __name__ == "__main__":
    """If this script is executed as stand alone then call main() function."""
    if len(sys.argv) == 2:
        main(sys.argv[1])
    else:
        print "Please provide password"
        sys.exit(0)

Email with attachment

Above scripts just send an email what if you want to attach something with it. You can use the below script to attach a picture and text file with the email.

#!/usr/bin/env python
from smtplib import SMTP
from smtplib import SMTPException
from email.MIMEMultipart import MIMEMultipart
from email.MIMEText import MIMEText
from email.MIMEImage import MIMEImage
import sys


EMAIL_SUBJECT = "Email from Python script with attachment."
EMAIL_FROM = 'senderId@gmail.com'
EMAIL_RECEIVER = 'receiverId@gmail.com'
GMAIL_SMTP = "smtp.gmail.com"
GMAIL_SMTP_PORT = 587
TEXT_SUBTYPE = "plain"

def listToStr(lst):
    """This method makes comma separated list item string"""
    return ','.join(lst)

def send_email(content, pswd):
    """This method sends an email""" 
  
    #Create the email.
    msg = MIMEMultipart()
    msg["Subject"] = EMAIL_SUBJECT
    msg["From"] = EMAIL_FROM
    msg["To"] = EMAIL_RECEIVER
    body = MIMEMultipart('alternative')
    body.attach(MIMEText(content, TEXT_SUBTYPE ))
    #Attach the message
    msg.attach(body)
    #Attach a text file
    msg.attach(MIMEText(file("code4reference.txt").read()))
    #Attach a picuture.
    msg.attach(MIMEImage(file("pic.jpg").read()))
    
    try:
      smtpObj = SMTP(GMAIL_SMTP, GMAIL_SMTP_PORT)
      #Identify yourself to GMAIL ESMTP server.
      smtpObj.ehlo()
      #Put SMTP connection in TLS mode and call ehlo again.
      smtpObj.starttls()
      smtpObj.ehlo()
      #Login to service
      smtpObj.login(user=EMAIL_FROM, password=pswd)
      #Send email
      smtpObj.sendmail(EMAIL_FROM, EMAIL_RECEIVER, msg.as_string())
      #close connection and session.
      smtpObj.quit()
    except SMTPException as error:
      print "Error: unable to send email :  {err}".format(err=error)

def main(pswd):
    """This is a simple main() function which demonstrate sending of email using smtplib."""
    send_email("Test email was generated by Python using smtplib and email libraries." + \
               " This email also has attachments. Please download tehm", pswd);

if __name__ == "__main__":
    """If this script is run as stand alone then call main() function."""
    if len(sys.argv) == 2:
        main(sys.argv[1]);
    else:
        print "Please provide the password"
        

If you are interested in source code you can get it from github/code4reference.

Hope this blog helped you in some way. If you like this blog then please share it. You can also leave your comment below.

Related topics

  1. Setting Mail Transfer Agent (MTA) on EC2 using exim4
, ,
Trackback

3 comments untill now

  1. Error: unable to send email : (535, ’5.7.0 (#AUTH003) Incorrect username or password.’)

  2. Ryan Vanwyk @ 2014-05-23 23:34

    these all scripts doesnt works on my end plz provide me solution

  3. @Ryan
    Please make sure that you have installed the email client on the same machine. If the machine doesn’t have it, then install exim4 and configure it. This link might help you to do this

    http://code4reference.com/2013/07/setting-email-server-on-ec2-using-exim4/

Add your comment now