From f757a448a236335b8c86282a9bc8883366bd394c Mon Sep 17 00:00:00 2001 From: dadada Date: Sat, 16 May 2020 17:14:18 +0200 Subject: [PATCH] init --- .gitignore | 4 ++ bin/mailbox2matrix | 95 ++++++++++++++++++++++++++++++++++++++++++++++ default.nix | 11 ++++++ requirements.txt | 2 + 4 files changed, 112 insertions(+) create mode 100644 .gitignore create mode 100755 bin/mailbox2matrix create mode 100644 default.nix create mode 100644 requirements.txt diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..f803179 --- /dev/null +++ b/.gitignore @@ -0,0 +1,4 @@ +fginfo.sh +apitoken.txt +requirements*.nix +requirements_frozen.txt diff --git a/bin/mailbox2matrix b/bin/mailbox2matrix new file mode 100755 index 0000000..a0e9ab7 --- /dev/null +++ b/bin/mailbox2matrix @@ -0,0 +1,95 @@ +#!/usr/bin/env python + +import asyncio +import email +import pathlib +import os +import sys +from nio import (AsyncClient, Api, ClientConfig) +from inotify_simple import INotify, flags + + +class Client(AsyncClient): + + def send_message(self, From, Subject): + return self.room_send( + room_id=self.room, + message_type="m.room.message", + content={ + "msgtype": "m.text", + "body": "From:\t%s\nSubject:\t%s" % (From, Subject) + } + ) + + async def process_message(self, name): + # delete message + path = pathlib.Path(os.path.join(self.maildir, name)) + message = email.message_from_file(open(path, 'r')) + # send message + response = await self.send_message(message['from'], message['subject']) + path.unlink() + + # TODO implement retry for old mails + async def process_queued(self): + for name in os.listdir(self.maildir): + await self.process_message(name) + + async def run(self, password=None, token=None): + if token is None: + response = await self.login(password, device_name = self.device) + print("Access Token is", response.access_token) + else: + self.access_token = token + + await self.process_queued() + + while True: + for event in self.notify.read(): + (_, _, _, name) = event + if flags.CREATE in flags.from_mask(event.mask): + await self.process_message(name) + + async def shutdown(sig, loop): + print('Shutting down') + await self.close() + + def __init__(self, homeserver, user, device, room, maildir): + super().__init__(homeserver, user) + self.device = device + self.room = room + self.notify = INotify() + self.maildir = maildir + watch_flags = flags.CREATE + wd = self.notify.add_watch(maildir, watch_flags) + + +def main(): + homeserver = sys.argv[1] + username = sys.argv[2] + device = sys.argv[3] + room = sys.argv[4] + maildir = sys.argv[5] + if len(sys.argv) > 5: + tokenfile = sys.argv[6] + + client = Client(homeserver, username, device, room, maildir) + + loop = asyncio.get_event_loop() + + try: + password = None + token = None + if os.path.isfile(tokenfile): + with open(tokenfile) as f: + token = f.readlines()[0].strip('\n') + else: + password = input('Could not find file for API-token. Please specify password.\nPassword: ') + loop.run_until_complete(client.run(password = password, token = token)) + except KeyboardInterrupt: + client.shutdown() + finally: + loop.close() + + +if __name__ == "__main__": + main() diff --git a/default.nix b/default.nix new file mode 100644 index 0000000..e79699d --- /dev/null +++ b/default.nix @@ -0,0 +1,11 @@ +with import {}; +let + pythonEnv = python37.withPackages(ps: [ + ps.matrix-nio + ps.inotify + ]); +in mkShell { + builtInputs = [ + pythonEnv + ]; +} diff --git a/requirements.txt b/requirements.txt new file mode 100644 index 0000000..4df7496 --- /dev/null +++ b/requirements.txt @@ -0,0 +1,2 @@ +matrix-nio +inotify