[Tutor] Use python to parse the subject line of emails, listen for and react to commands

Alan Gauld alan.gauld at btinternet.com
Sat Feb 28 00:26:39 CET 2015


On 27/02/15 19:43, Willie Sims wrote:
> I have started working with 2.7 simply because I don't know when the error
> is caused by me or because of version issues.
> This is how far I have gotten,
> I can access and pull emails that only come from a selected email address
> (OWNER)
> I have it parsed down to print the subject only
> And I have it saving the string to a file output.txt
> And I have it deleting the emails so they don't reread,
> Now I want to eval the output.txt and act on the keyword that is written,,

That's nearly always a bad idea. eval is a big security risk, especially 
if applied to external input. And as you've discovered,
it makes debugging into a bit of a nightmare.

> eval output.txt but get the error
>
> Traceback (most recent call last):
>    File "C:\Python27\New folder\start.py", line 82, in <module>
>      start_command = eval(open("output.txt").read())
>    File "<string>", line 1, in <module>
> NameError: name 'test' is not defined
>

That's probably because a line in output.txt contains the
word test which is not known to python. Without seeing
output.txt it's impossible to be more specific.

> import sys
> import imaplib
> import getpass
> import email
> import email.header
> import datetime
>
> EMAIL_ACCOUNT = "myemail at gmail.com"
> EMAIL_FOLDER = "INBOX"
> OWNER = "willie14228 at outlook.com"
> COMMAND_FILE = open("output.txt","w")
>
> def process_mailbox(M):
>      rv, data = M.search(None, "From", (OWNER))
>      if rv != 'OK':
>          print "No messages found!"
>          return
>      for num in data[0].split():
>          rv, data = M.fetch(num, '(RFC822)')
>          if rv != 'OK':
>              print "ERROR getting message", num
>              return
>          msg = email.message_from_string(data[0][1])
>          decode = email.header.decode_header(msg['Subject'])[0]
>          subject = unicode(decode[0])
>          print 'Message %s: %s' % (num, subject)
> COMMAND_FILE.write('%s' % (subject))
>          COMMAND_FILE.close()
>          #print 'Raw Date:', msg['Date']

I assume this is where the function is supposed to end?

Note that you are throwing away all the data you find. It is lost when 
the function exits. Are the print statements and file output sufficient?
Also note you have the file closure inside the loop. That means you only 
get the first item in the file before you close it I'm not clear what 
the loop is doing so it might be OK.

> M = imaplib.IMAP4_SSL('imap.gmail.com')
> try:
>      rv, data = M.login(EMAIL_ACCOUNT, getpass.getpass())
> except imaplib.IMAP4.error:
>      print "LOGIN FAILED!!! "
>      sys.exit(1)
> print rv, data
> rv, mailboxes = M.list()
> if rv == 'OK':
>      print "Mailboxes:"
>      print mailboxes
> rv, data = M.select(EMAIL_FOLDER)
> if rv == 'OK':
>      print "Processing mailbox...\n"
>      process_mailbox(M)
>      M.select('INBOX')  # select all trash
>      M.store("1:*", '+FLAGS', '\\Deleted')  #Flag all Trash as Deleted
>      M.expunge()
>      M.close()
> else:
>      print "ERROR: Unable to open mailbox ", rv
>
> M.logout()
> start_command = eval(open("output.txt").read())
>
>
> Traceback (most recent call last):
>    File "C:\Python27\New folder\start.py", line 82, in <module>
>      start_command = eval(open("output.txt").read())
>    File "<string>", line 1, in <module>
> NameError: name 'test' is not defined

-- 
Alan G
Author of the Learn to Program web site
http://www.alan-g.me.uk/
http://www.amazon.com/author/alan_gauld
Follow my photo-blog on Flickr at:
http://www.flickr.com/photos/alangauldphotos




More information about the Tutor mailing list