Email

接收 Pop/IMAP 電子郵件,然後加密轉發到 gmail

  • April 11, 2012

基本上,我有一個可以作為 POP3 或 IMAP 訪問的電子郵件帳戶。我想接收所有傳入的電子郵件,對其進行加密,然後將加密版本轉發到我的 gmail 帳戶(這樣我就可以在我的手機/gmail 帳戶上看到主題/通知;並可能使用密碼解密消息——儘管這是最後一個step 最初不需要執行)。

我可能可以編寫一個 python 腳本來執行此操作,但使用適當的 linux 工具似乎是一條更好的路線。我已經設置了後綴(在衛星配置中)以發送外發郵件。

在 linux 機器上讀取 POP3/IMAP 並將其用於 gpg 使用我的公鑰加密電子郵件的正文和附件(不是主題標頭)並將其轉發到我的 gmail 帳戶的最簡單方法是什麼?

(作為記錄;它違反工作政策(部分是為了遵守美國 HIPAA 法律)讓我將未加密的電子郵件版本發送到我的手機;因為有人可能故意(或無意)將受保護的數據通過電子郵件發送到我的手機。工作認為 GPG 是安全的。)

我只是看到了另一個回應,我猜我從來沒有寫過我實際實施的解決方案。事實證明,python imaplib 很簡單,我寫了一個非常快速的腳本。除非進行一些更改(例如,將我的各種 USERNAME、EMAILPASSWORD、WORKDOMAINNAME、MYGPGKEYID 匿名化)。我也不只是發送加密它;但在主題前加上發件人的使用者名,並將一些標題內容放在 GPG 之前(以防我在手機上閱讀它並且無法解密)。

#!/usr/bin/python

import imaplib
import email
from datetime import datetime,timedelta
import shelve
from subprocess import Popen, PIPE

def piped_call(command1, arg1_list, command2, arg2_list):
   """
   if arg1_tuple = (a10, a11, a12); arg2_tuple is (a20, a21)    
   This executes "command1 a10 a11 a12 | command2 a20 a21 a22"
   """
   if type(arg1_list) not in (list, tuple):
       arg1_list = [arg1_list,]
   if type(arg2_list) not in (list, tuple):
       arg2_list = [arg2_list,]
   p1 = Popen([command1,]+list(arg1_list), stdout=PIPE)
   p2 = Popen([command2,]+list(arg2_list), stdin=p1.stdout, stdout=PIPE)
   p1.stdout.close()
   return p2.communicate()[0]

shlf = shelve.open('/home/USERNAME/mail/mail.shlf')
# This shelf (a persistent python dictionary written to file) has as its key 
# the IMAP message ids of all emails that have been processed by this script.
# Every time the script runs, I fetch all emails from the current day
# (except from midnight to 1am, where I fetch all emails since yesterday)
# and then send all emails that haven't been sent previously 
# by checking message ids against the python shelf.

M = imaplib.IMAP4_SSL(host='imap.WORKDOMAINNAME.com', port=993)
M.login('EMAILUSERNAME', 'EMAILPASSWORD')
M.select()
dt = datetime.now() - timedelta(0,5*60*60) 
# Only search for messages since the day of an hour earlier.  
# This way messages from yesterday don't get lost at midnight; as well as limiting the number of messages to process through to just todays.    
typ, uid_data = M.uid('search', None, '(SINCE %s)' % dt.strftime('%d-%b-%Y'))

for num in uid_data[0].split():
   typ, data = M.uid('fetch', num, '(RFC822)')
   e = email.message_from_string(data[0][1])
   print 'Message %s\n%s\n' % (num, e['subject'])
   if num not in shlf:
       sender_email = e['return-path']
       for s in ('<', '>', '@WORKDOMAINNAME.com'):
           sender_email = sender_email.replace(s,'')
       subject = "%s: %s" % (sender_email, e['Subject'])
       body = ("From: %s\n"
               "To: %s\n"
               "Cc: %s\n"
               "Subject: %s\n\n" % (e['From'], e['To'], e['Cc'], e['subject']))
       payload = e.get_payload()
       if type(payload) in (list, tuple):
           payload = str(payload[0])
       else:
           payload = str(payload)
       encrypted_payload = piped_call('echo', (payload,),
                                      'gpg', ('-e', '-a', '-r', 'MYGPGKEYID'))
       body += encrypted_payload
       piped_call('echo', (body,), 
                  'mail', ['USERNAME@gmail.com', '-s', subject])
       shlf[num] = datetime.now()


M.close()
M.logout()

然後,我將以下幾行添加到我的 crontab 中(上面的腳本在名為 mail 的目錄中命名為 mail.py),因此它將在工作日的正常時間(MF 8-7pm)每 5 分鐘執行一次,而在其他時間則不那麼頻繁. (crontab -e)

# Every 5 minutes, M-F from 8am - 7pm.    
*/5 8-19 * * 1-5  cd /home/USERNAME/mail && ./mail.py >> /home/USERNAME/mail/mail.log 2>&1
# Every 30 minutes, Sat&Sun from 8am-7pm
0,30 8-19 * * 6,7  cd /home/USERNAME/mail && ./mail.py >> /home/USERNAME/mail/mail.log 2>&1
# Every 30 minutes, M-F 8pm-2am; (no emails 2am-8am)
0,30 0-2,20-23 * * 1-5  cd /home/USERNAME/mail && ./mail.py >> /home/USERNAME/mail/mail.log 2>&1
# Every 60 minutes, Sat&Sun hours 8pm-2am; (no emails 2am-8am)
0 0-2,20-23 * * 6-7  cd /home/USERNAME/mail && ./mail.py >> /home/USERNAME/mail/mail.log 2>&1

引用自:https://unix.stackexchange.com/questions/19046