#!/usr/bin/env python3

###################################################################
# To the extent possible under law, the person who associated CC0 #
# with phlog-bot.py has waived all copyright and related or       #
# neighboring rights to phlog-bot.py.                             #
#                                                                 #
# https://creativecommons.org/publicdomain/zero/1.0/              #
###################################################################

# NO WARRANTY!!!!
# PLEASE DON'T RUN THIS SCRIPT UNLESS YOU HAVE BACKUPS OF YOUR
# MAILFILE OR ANYTHING ELSE THIS SCRIPT TOUCHES PLEASE.

import mailbox
import json
import time
import datetime
import os

gopherdir = "/home/lro/gopher/test"
userdictionaryfile = "users.json"
mailboxf = "test-mbox"
today = datetime.date.today()
todayfmt = today.strftime("%d")
yearmonth = today.strftime("%Y")+"-"+today.strftime("%m")

def get_unread_emails(mailboxfile):
   unread = []
   if not os.path.isfile(mailboxfile):
       print("Mailboxfile doesn't exist: %s" % (mailboxfile))
       return unread

   mailboxfp = mailbox.mbox(mailboxfile)
   ind = 0
   for message in mailboxfp:
       flags = message.get_flags()
       if flags.find('R') == -1:
           unread.append(message)
           message.add_flag('R')
           mailboxfp[ind] = message
       ind = ind + 1

   mailboxfp.lock()
   mailboxfp.flush()
   mailboxfp.unlock()
   mailboxfp.close()
   return unread

def load_dictionary(dictfile):
   if not os.path.isfile(dictfile):
       return []

   usersfile = open(dictfile)
   userdictionary = json.load(usersfile)
   usersfile.close()
   return userdictionary

def get_from_lower(message):
   From = message.get_from()
   return From.split(" ")[0].lower()

def user_in_dict(email, dictionary):
   try:
       return dictionary[email]
   except KeyError:
       return False

def phlog_post_contents(email):
   return email.get_payload()

def write_phlog_post(filename, contents):
   ind = 0
   justfilenamenotpath = filename.split("/")[-1]
   while os.path.isfile(filename):
       if ind == 99:
           break

       ind += 1
       filename = filename.split(".")[0].split("_")[0]+"_"+str(ind)+".txt"
       justfilenamenotpath = filename.split("/")[-1]

   with open(filename, "w") as phlogfile:
       phlogfile.write(contents)

   return justfilenamenotpath

def add_gophermap(gophermap, filename, description):
   entry = "0%s        %s" % (description, filename)

   with open(gophermap, "r") as gfp:
       buf = gfp.readlines()

   with open(gophermap, "w") as gfp:
       for line in buf:
           if "==================================================" in line:
               line = line+"\n"+entry
           gfp.write(line)

def update_gophermap(gophermap, filename, description):
   entry = "0%s        %s" % (description, filename)

   with open(gophermap, "r") as gfp:
       buf = gfp.readlines()

   posts = 0
   for line in buf:
       if line.startswith("0"):
           posts += 1
           if posts > 10:
               buf.remove(line)
               posts -= 1

   with open(gophermap, "w") as gfp:
       for line in buf:
           if "==================================================" in line:
               line = line+"\n"+entry
           gfp.write(line)

def create_archive_dir(phlogdir, yearmonth):
   if not os.path.isdir(phlogdir+"/"+yearmonth):
       os.mkdir(phlogdir+"/"+yearmonth)
       with open(phlogdir+"/"+yearmonth+"/gophermap", "w+") as f:
           f.write("i==================================================\n")
       with open(phlogdir+"/gophermap", "a") as f:
           f.write("\n\n1Archive of phlosts from: "+yearmonth+"        "+yearmonth)

def new_phlog_entry(message):
   email = get_from_lower(message)
   username = user_in_dict(email, userdictionary)
   if not username:
       print("User: %s not in user dictionary" % (email))
       return

   phlogtitle = message['subject']
   phlogfilename = todayfmt + ".txt"
   phlogcontents = phlog_post_contents(message)
   phlogdir = gopherdir+"/"+username

   create_archive_dir(phlogdir, yearmonth)

   phlogfilename = write_phlog_post(phlogdir+"/"+yearmonth+"/"+phlogfilename, phlogcontents)
   ymd = "<"+yearmonth+"-"+todayfmt+">"

   update_gophermap(phlogdir+"/gophermap", yearmonth+"/"+phlogfilename, phlogtitle+" "+ymd)
   add_gophermap(phlogdir+"/"+yearmonth+"/gophermap", phlogfilename, phlogtitle+" "+ymd)
   update_gophermap(gopherdir+"/gophermap", username+"/"+yearmonth+"/"+phlogfilename, username+" - "+phlogtitle+" "+ymd)
   print("Added phlog post for %s" % (username))

userdictionary = load_dictionary(userdictionaryfile)

for message in get_unread_emails(mailboxf):
   new_phlog_entry(message)