예제 #1
0
파일: pymail.py 프로젝트: yann2192/Pymail
class imap:
    commands = {
        "help" : "for help :)",
        "exit" : "To exit ;)",
        "add_account" : "...",
        "list_account" : "...",
        "del_account" : "...",
        "stat" : "...",
        "list" : "...",
        "show" : "...",
        "save" : "...",
        "delete" : "...",
        }

    def __init__(self):
        self.db = Index()
        self.get_mdp()
        
    def help(self):
        for i in self.commands:
            print(i,":",self.commands[i])

    def get_mdp(self):
        if os.path.exists(config.keypath) is False:
            self.mdp = sha256(getpass("Global Password : "******"[!] Bad password !")

    def change_mdp(self):
        pass
        
    def loop(self):
        while True:
            try:
                buffer = input('\n> ')
                if buffer == "exit":
                    return
                elif buffer in self.commands:
                    eval("self.%s()" % buffer)
                else:
                    print("Command not found")
            except Exception as e:
                print(e)

    def list_account(self):
        accounts = self.db.get_all()
        print("Accounts : ")
        if accounts == []:
            print(">> None")
        else:
            for i in accounts:
                id = i[0]
                name = i[1]
                host = i[2]
                port = int(i[3])
                login = i[4]
                print("%s) %s : %s@%s:%d" % (id, name, login, host, port))

    def get_account(self, num):
        account = self.db.get_data_by_id(num)
        id = account[0]
        name = account[1]
        host = account[2]
        port = int(account[3])
        login = account[4]
        pwd = b64decode(account[5].encode())
        iv = pwd[:16]
        pwd = pwd[16:]
        ctx = serpent_cbc(self.mdp, iv)
        pwd = ctx.decrypt(pwd)
        pwdlen = unpack('H', pwd[:2])[0]
        pwd = pwd[2:2+pwdlen].decode()
        return {"id":id, "name":name, "host":host, "port":port, "login":login, "pwd":pwd}
                
    def add_account(self):
        name = input("Account name : ")
        host = input("Host : ")
        port = int(input("Port : "))
        login = input("Login : "******"[+] Account add.")

    def del_account(self):
        id = int(input('id : '))
        self.db.rm_data(id)
        print("[+] Account deleted.")

    def stat(self):
        nb = len(self.db.get_all())
        for i in range(nb):
            account = self.get_account(i+1)
            s = self.connect(account)
            print(str(account["id"])+")",account["name"],":",s.status('INBOX', '(MESSAGES UNSEEN)')[1][0].decode())
            self.close(s)
        
    def list(self):
        num = int(input('id : '))
        try:
            lim = int(input('limit (5) : '))
        except:
            lim = 5
        self.get_mail_index(num, lim)

    def show(self):
        num = int(input('id : '))
        mail = input('mail : ')
        print(self.get_mail(num, mail))

    def save(self):
        num = int(input('id : '))
        mail = input('mail : ')
        out = input('file : ')
        buff = str(self.get_mail(num, mail))
        with open(out, 'w') as f:
            f.write(buff)
        print("Done.")

    def delete(self):
        num = int(input('id : '))
        mail = input('mail : ')
        account = self.get_account(num)
        s = self.connect(account)
        s.store(mail, '+FLAGS', '\\Deleted')
        self.close(s)
        
    def get_mail_index(self, num, z = None):
        account = self.get_account(num)
        s = self.connect(account)
        typ, data = s.search(None, 'ALL')
        index = data[0].decode().split()
        index.reverse()
        print()
        for i in index:
            try:
                if z != None and int(index[0])-z == int(i):
                    break
            except: pass
            try:
                typ, data = s.fetch(i, 'BODY[HEADER]')
                msg = email.message_from_bytes(data[0][1])
                print(i+") ", end='')
                print("from :",msg['from'])
                print("subject :",msg['subject'])
            except Exception as e:
                print(i+") Error :",e)
            print()
        self.close(s)

    def get_mail(self, num, i):
        account = self.get_account(num)
        s = self.connect(account)
        typ, data = s.fetch(i, '(RFC822)')
        msg = email.message_from_bytes(data[0][1])
        return msg
        
    def connect_all(self):
        for i in range(len(self.serv)):
            self.connect(i)

    def connect(self, account):
        #print("[.]",account["name"], "SSL connection ...")
        s = imaplib.IMAP4_SSL(account["host"], account["port"])
        #print("[+] Done.")
        #print("[.] Login with",account["login"],"...")
        try:
            s.login(account["login"], account["pwd"])
        except:
            raise Exception("[!] Fail to log")
        #print("[+] Done.")
        s.select()
        return s
            
    def close(self, s):
        s.close()
        s.logout()
            
    def fetchall(self):
        for i in range(len(self.serv)):
            self.fetch(i)
            
    def fetch(self, x):
        self.mails[x] = [] 
        print("[.] Fetch al",self.serv[x][0],"mails ...")
        sys.stdout.flush()
        typ, data = self.s[x].search(None, 'ALL')
        j = 0
        z = str(int(data[0].decode().count(' '))+1)
        sys.stdout.write("0/"+z)
        sys.stdout.flush()
        for num in data[0].decode().split():
            typ, data = self.s[x].fetch(str(num), '(RFC822)')
            self.mails[x].append((num,data[0][1]))
            j += 1
            sys.stdout.write("\r"+str(j)+"/"+z) 
            sys.stdout.flush()
        print("\n[+] Done.")