Eudoraclean
Views:
Eudora (used to) automatically save attachments to emails in a separate directory, i.e. the mime-encoded attachments in emails were removed from the email and the file decoded and stored in the directory on the file system.
This is all when and good but people ended up with a lot of old attachments filling up their home directories even thought the original emails had been deleted.
This script examines emails and attachments and deletes any attachments that do not have a corresponding email.
This is one of my very first python scripts - one of my first scripts even. BACK UP YOUR FILES. I AM AN IDIOT AND ALL MY CODE IS DANGEROUS
#####################################################################################
#
# EudoraClean
# ~~~~~~~~~~~
#
# Removes orphaned attachments from Eudora's n:\Do_Not_Delete_MAIL\Attachments folder
#
# Make into a binary using py2exe (that way you don't need to install python everywhere)
#
# Kieran kjw@varndean.ac.uk
#
#####################################################################################
import os # grab module needed to access the filesystem
from ScrolledText import ScrolledText # grab text area with scroll bar (for log output)
from Tkinter import * # grab GUI module
import win32com.client # grab MS Component Object Model module
#####################################################################################
class EudoraClean:
#####################################################################################
def __init__(self, master):
frame = Frame(master)
frame.pack()
w = Label(frame, text="Eudora Clean", font=('bold', 30))
w.pack()
self.log = ScrolledText(frame, borderwidth=2, font=16, width=70, height=5, padx=5, pady=5)
self.log.pack()
self.log.insert(END, 'This program will delete old attachments from Eudora which were not deleted automatically\n\n')
self.log.insert(END, 'Please make sure you close Eudora before clicking on "Delete Files"')
self.delFiles = Button(frame, text="Delete Files", font=20, command=self.cleanAttachments)
self.delFiles.pack(padx=5, pady=5, anchor=E)
self.button = Button(frame, text="Exit", font=20, command=frame.quit)
self.button.pack(padx=5, pady=5, anchor=E)
# end __init__
#####################################################################################
#####################################################################################
def updateLog(self, txt):
self.log.insert(END, txt)
self.log.see(END)
# end updateLog
#####################################################################################
#####################################################################################
def cleanAttachments(self):
self.log.delete(0.0,END)
c = 0 #count
ac = 0 #attachments count
attachments = {} # dictionary of attachments referenced in mailboxes
mailboxes = {} # dictionary of mailbox files
mailpath = 'n:/Do_Not_Delete_MAIL/'
attachpath = mailpath + '/Attachments/'
hadError = 0
tooDeep = 0
if os.path.isdir(attachpath):
for x in os.listdir(mailpath):
if os.path.splitext(x)[1] == '.mbx':
mailboxes[c] = mailpath + x
c = c + 1
elif os.path.splitext(x)[1] == '.fol':
for y in os.listdir(mailpath + x):
if os.path.splitext(y)[1] == '.mbx':
mailboxes[c] = mailpath + x + '/' + y
c = c + 1
elif os.path.splitext(y)[1] == '.fol':
for z in os.listdir(mailpath + x + '/' + y):
if os.path.splitext(z)[1] == '.mbx':
mailboxes[c] = mailpath + x + '/' + y + '/' + z
c = c + 1
elif os.path.splitext(z)[1] == '.fol':
self.updateLog("ERROR: Too many nested folders!\nPlease winge at kjw@varndean.ac.uk so he'll make it work for you\n:-)")
tooDeep = 1
else:
self.updateLog("Can't find your email files!\nNo work to do.")
if not tooDeep and os.path.isdir(attachpath):
for x in mailboxes:
mailbox=open(mailboxes[x])
for line in mailbox:
if (line[:56]) == 'Attachment Converted: n:\\Do_Not_Delete_MAIL\\Attachments\\':
attachments[ac]=line[22:-1]
ac = ac + 1
c = 0 # reset counter
for x in os.listdir(attachpath):
delme = 1
for y in attachments:
if x == os.path.basename(attachments[y]):
delme = 0
if delme == 1:
self.updateLog('Removing: ' + x + '\n')
try:
os.remove(attachpath + x)
c = c + 1
except:
self.updateLog('ERROR with file: ' + str(sys.exc_info()[0]) + '\n')
hadError = 1
if c > 0 and not hadError:
self.updateLog(str(c) + ' old attachment(s) deleted')
elif c == 0 and not hadError:
self.updateLog('No old attachments found, no files were deleted')
elif c == 0 and hadError:
self.updateLog('One or more errors occurred, no files deleted')
elif c > 0 and hadError:
self.updateLog(str(c) + ' old attachment(s) deleted but one or more errors occurred')
# End cleanAttachments
#####################################################################################
# end EudoraClean
#####################################################################################
#####################################################################################
class EudoraWarn:
#####################################################################################
def __init__(self, master):
self.msg = ''
frame = Frame(master)
frame.pack()
w = Label(frame, text='Please close Eudora,\nthen try again', font=('bold', 20))
w.pack()
b = Button(frame, text="OK", font=20, command=frame.quit)
b.pack(padx=5, pady=5, anchor=E)
# end __init__
#####################################################################################
# end EudoraWarn
#####################################################################################
Eudora = 0
root=Tk() # create window
root.title('Eudora Clean')
WMIService = win32com.client.Dispatch("WbemScripting.SWbemLocator") # connect to COM
SWbemServices = WMIService.ConnectServer(".","root\cimv2")
winProcs = SWbemServices.ExecQuery("Select * from Win32_Process") # get all proccess info
for x in winProcs: # find Eudora!!
if x.Description == "Eudora.exe":
Eudora = 1
if Eudora:
App=EudoraWarn(root)
else:
App=EudoraClean(root)
