From 1cbe5b8a6d7b32464f7947256bc231bd1a2f0cfd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Damir=20Jeli=C4=87?= Date: Fri, 10 May 2019 15:25:41 +0200 Subject: [PATCH] ui: Rewrite the dbus code using pydbus. --- pantalaimon/panctl.py | 123 +++++++------------------ pantalaimon/ui.py | 202 ++++++++++++++++++++++-------------------- 2 files changed, 142 insertions(+), 183 deletions(-) diff --git a/pantalaimon/panctl.py b/pantalaimon/panctl.py index 5fffe2a..6a0bdc5 100644 --- a/pantalaimon/panctl.py +++ b/pantalaimon/panctl.py @@ -15,11 +15,8 @@ from prompt_toolkit.completion import Completer, Completion, PathCompleter from prompt_toolkit.document import Document from prompt_toolkit import print_formatted_text, HTML -import dbus +from pydbus import SessionBus from gi.repository import GLib -from dbus.mainloop.glib import DBusGMainLoop - -DBusGMainLoop(set_as_default=True) use_asyncio_event_loop() @@ -106,10 +103,7 @@ class PanCompleter(Completer): yield Completion(compl_word, -len(last_word)) def complete_users(self, last_word, pan_user): - devices = self.devices.list( - pan_user, - dbus_interface="org.pantalaimon1.devices" - ) + devices = self.devices.List(pan_user) users = set(device["user_id"] for device in devices) compl_words = self.filter_words(users, last_word) @@ -119,11 +113,7 @@ class PanCompleter(Completer): return "" def complete_devices(self, last_word, pan_user, user_id): - devices = self.devices.list_user_devices( - pan_user, - user_id, - dbus_interface="org.pantalaimon1.devices" - ) + devices = self.devices.ListUserDevices(pan_user, user_id) device_ids = [device["device_id"] for device in devices] compl_words = self.filter_words(device_ids, last_word) @@ -142,9 +132,7 @@ class PanCompleter(Completer): return compl_words def complete_pan_users(self, last_word): - users = self.ctl.list_users( - dbus_interface="org.pantalaimon1.control" - ) + users = self.ctl.ListUsers() compl_words = self.filter_words([i[0] for i in users], last_word) for compl_word in compl_words: @@ -282,27 +270,14 @@ class PanCtl: ] def __attrs_post_init__(self): - self.bus = dbus.SessionBus() - self.ctl = self.bus.get_object( - "org.pantalaimon1", - "/org/pantalaimon1/Control", - introspect=True - ) - self.devices = self.bus.get_object( - "org.pantalaimon1", - "/org/pantalaimon1/Devices", - introspect=True - ) - self.bus.add_signal_receiver( - self.show_sas, - dbus_interface="org.pantalaimon1.devices", - signal_name="sas_show" - ) - self.bus.add_signal_receiver( - self.show_info, - dbus_interface="org.pantalaimon1.control", - signal_name="info" - ) + self.bus = SessionBus() + self.pan_bus = self.bus.get("org.pantalaimon1") + + self.ctl = self.pan_bus["org.pantalaimon1.control"] + self.devices = self.pan_bus["org.pantalaimon1.devices"] + + self.ctl.Info.connect(self.show_info) + self.devices.SasReceived.connect(self.show_sas) def show_info(self, message): print(message) @@ -353,51 +328,13 @@ class PanCtl: def list_users(self): """List the daemons users.""" - users = self.ctl.list_users( - dbus_interface="org.pantalaimon1.control" - ) + users = self.ctl.ListUsers() print("pantalaimon users:") for user, device in users: print(" ", user, device) - def import_keys(self, args): - self.ctl.import_keys( - args.pan_user, - args.path, - args.passphrase, - dbus_interface="org.pantalaimon1.control" - ) - - def export_keys(self, args): - self.ctl.export_keys( - args.pan_user, - args.path, - args.passphrase, - dbus_interface="org.pantalaimon1.control" - ) - - def confirm_sas(self, args): - self.devices.confirm_sas( - args.pan_user, - args.user_id, - args.device_id, - dbus_interface="org.pantalaimon1.devices" - ) - - def accept_sas(self, args): - self.devices.accept_sas( - args.pan_user, - args.user_id, - args.device_id, - dbus_interface="org.pantalaimon1.devices" - ) - def list_devices(self, args): - devices = self.devices.list_user_devices( - args.pan_user, - args.user_id, - dbus_interface="org.pantalaimon1.devices" - ) + devices = self.devices.ListUserDevices(args.pan_user, args.user_id) print_formatted_text( HTML(f"Devices for user {args.user_id}:") @@ -431,29 +368,37 @@ class PanCtl: parser = PanctlParser() try: - parsed_args = parser.parse_args(result.split()) + args = parser.parse_args(result.split()) except ParseError: continue - command = parsed_args.subcommand + command = args.subcommand if command == "list-users": self.list_users() - elif command == "export-keys": - self.export_keys(parsed_args) - elif command == "import-keys": - self.import_keys(parsed_args) + self.ctl.ImportKeys(args.pan_user, args.path, args.passphrase) - elif command == "accept-verification": - self.accept_sas(parsed_args) + elif command == "export-keys": + self.ctl.ExportKeys(args.pan_user, args.path, args.passphrase) elif command == "list-devices": - self.list_devices(parsed_args) + self.list_devices(args) + + elif command == "accept-verification": + self.devices.AcceptKeyVerification( + args.pan_user, + args.user_id, + args.device_id + ) elif command == "confirm-verification": - self.confirm_sas(parsed_args) + self.devices.ConfirmKeyVerification( + args.pan_user, + args.user_id, + args.device_id + ) def main(): @@ -462,8 +407,8 @@ def main(): try: panctl = PanCtl() - except dbus.exceptions.DBusException: - print("Error, no pantalaimon bus found") + except GLib.Error as e: + print(f"Error, {e}") sys.exit(-1) fut = loop.run_in_executor( diff --git a/pantalaimon/ui.py b/pantalaimon/ui.py index fe57e9d..db5375b 100644 --- a/pantalaimon/ui.py +++ b/pantalaimon/ui.py @@ -1,11 +1,8 @@ import attr -import dbus -import dbus.exceptions -import dbus.service - -from dbus.mainloop.glib import DBusGMainLoop from gi.repository import GLib +from pydbus import SessionBus +from pydbus.generic import signal from queue import Empty from nio.store import TrustState @@ -24,19 +21,100 @@ from pantalaimon.thread_messages import ( ) from pantalaimon.log import logger -DBusGMainLoop(set_as_default=True) + +class Control: + """ + + + + + + + + + + + + + + + + + + + + + + + + """ + + def __init__(self, queue, user_list=None): + self.users = user_list + self.queue = queue + + def ListUsers(self): + """Return the list of pan users.""" + return self.users + + def ExportKeys(self, pan_user, filepath, passphrase): + message = ExportKeysMessage(pan_user, filepath, passphrase) + self.queue.put(message) + return + + def ImportKeys(self, pan_user, filepath, passphrase): + message = ImportKeysMessage(pan_user, filepath, passphrase) + self.queue.put(message) + return + + Info = signal() -class Devices(dbus.service.Object): - def __init__(self, bus_name, queue, device_list): - super().__init__(bus_name, "/org/pantalaimon1/Devices") +class Devices: + """ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + """ + + SasReceived = signal() + + def __init__(self, queue, device_list): self.device_list = device_list self.queue = queue - @dbus.service.method("org.pantalaimon1.devices", - in_signature="s", - out_signature="aa{ss}") - def list(self, pan_user): + def List(self, pan_user): device_store = self.device_list.get(pan_user, None) if not device_store: @@ -49,10 +127,7 @@ class Devices(dbus.service.Object): return device_list - @dbus.service.method("org.pantalaimon1.devices", - in_signature="ss", - out_signature="aa{ss}") - def list_user_devices(self, pan_user, user_id): + def ListUserDevices(self, pan_user, user_id): device_store = self.device_list.get(pan_user, None) if not device_store: @@ -65,9 +140,7 @@ class Devices(dbus.service.Object): return device_list.values() - @dbus.service.method("org.pantalaimon1.devices", - in_signature="sss") - def verify(self, pan_user, user_id, device_id): + def Verify(self, pan_user, user_id, device_id): message = DeviceVerifyMessage( pan_user, user_id, @@ -76,9 +149,7 @@ class Devices(dbus.service.Object): self.queue.put(message) return - @dbus.service.method("org.pantalaimon1.devices", - in_signature="sss") - def unverify(self, pan_user, user_id, device_id): + def UnVerify(self, pan_user, user_id, device_id): message = DeviceUnverifyMessage( pan_user, user_id, @@ -87,9 +158,7 @@ class Devices(dbus.service.Object): self.queue.put(message) return - @dbus.service.method("org.pantalaimon1.devices", - in_signature="sss") - def start_verify(self, pan_user, user_id, device_id): + def StartSas(self, pan_user, user_id, device_id): device_store = self.device_list.get(pan_user) if not device_store: @@ -100,23 +169,12 @@ class Devices(dbus.service.Object): logger.info(f"Verifying device {user_id} {device_id}") return - @dbus.service.signal( - dbus_interface="org.pantalaimon1.devices", - signature="sssa(ss)" - ) - def sas_show(self, pan_user, user_id, device_id, auth_string): - pass - - @dbus.service.method("org.pantalaimon1.devices", - in_signature="sss") - def confirm_sas(self, pan_user, user_id, device_id): + def ConfirmKeyVerification(self, pan_user, user_id, device_id): message = DeviceConfirmSasMessage(pan_user, user_id, device_id) self.queue.put(message) return - @dbus.service.method("org.pantalaimon1.devices", - in_signature="sss") - def accept_sas(self, pan_user, user_id, device_id): + def AcceptKeyVerification(self, pan_user, user_id, device_id): message = DeviceAcceptSasMessage(pan_user, user_id, device_id) self.queue.put(message) return @@ -138,49 +196,6 @@ class Devices(dbus.service.Object): } -class Control(dbus.service.Object): - def __init__(self, bus_name, queue, user_list=None): - super().__init__(bus_name, "/org/pantalaimon1/Control") - self.users = user_list - self.queue = queue - - @dbus.service.method("org.pantalaimon1.control", - out_signature="a(ss)") - def list_users(self): - return self.users - - @dbus.service.method("org.pantalaimon1.control", - in_signature="sss") - def export_keys(self, pan_user, filepath, passphrase): - message = ExportKeysMessage( - pan_user, - filepath, - passphrase - ) - self.queue.put(message) - - return - - @dbus.service.method("org.pantalaimon1.control", - in_signature="sss") - def import_keys(self, pan_user, filepath, passphrase): - message = ImportKeysMessage( - pan_user, - filepath, - passphrase - ) - self.queue.put(message) - - return - - @dbus.service.signal( - dbus_interface="org.pantalaimon1.control", - signature="s" - ) - def info(self, message): - pass - - @attr.s class GlibT: receive_queue = attr.ib() @@ -188,26 +203,25 @@ class GlibT: data_dir = attr.ib() loop = attr.ib(init=False) - bus_name = attr.ib(init=False) store = attr.ib(init=False) users = attr.ib(init=False) devices = attr.ib(init=False) - control_bus = attr.ib(init=False) - device_bus = attr.ib(init=False) + bus = attr.ib(init=False) + control_if = attr.ib(init=False) + device_if = attr.ib(init=False) def __attrs_post_init__(self): self.loop = None - self.bus_name = dbus.service.BusName("org.pantalaimon1", - bus=dbus.SessionBus(), - do_not_queue=True) - self.store = PanStore(self.data_dir) self.users = self.store.load_all_users() self.devices = self.store.load_all_devices() - self.control_bus = Control(self.bus_name, self.send_queue, self.users) - self.device_bus = Devices(self.bus_name, self.send_queue, self.devices) + self.control_if = Control(self.send_queue, self.users) + self.device_if = Devices(self.send_queue, self.devices) + + self.bus = SessionBus() + self.bus.publish("org.pantalaimon1", self.control_if, self.device_if) def message_callback(self): try: @@ -218,10 +232,10 @@ class GlibT: logger.debug(f"UI loop received message {message}") if isinstance(message, DevicesMessage): - self.device_bus.update_devices(message) + self.device_if.update_devices(message) elif isinstance(message, DeviceAuthStringMessage): - self.device_bus.sas_show( + self.device_if.SasReceived( message.pan_user, message.user_id, message.device_id, @@ -229,7 +243,7 @@ class GlibT: ) elif isinstance(message, InfoMessage): - self.control_bus.info(message.string) + self.control_if.Info(message.string) self.receive_queue.task_done() return True