# This program is free software; you can redistribute it and/or modify it under # the terms of the GNU Lesser General Public License as published by the Free # Software Foundation; either version 3 of the License, or (at your option) any # later version. See http://www.gnu.org/copyleft/lgpl.html for the full text # of the license. __author__ = 'Marco Trevisan' __copyright__ = '(c) 2021 Canonical Ltd.' import dbus import fcntl import os import subprocess from collections import OrderedDict from dbusmock import DBusTestCase BUS_NAME = 'org.gnome.Mutter.TestDBusMocksManager' MAIN_OBJ = '/org/gnome/Mutter/TestDBusMocksManager' MAIN_IFACE = 'org.gnome.Mutter.TestDBusMocksManager' SYSTEM_BUS = True def load(mock, parameters): mock.mocks = OrderedDict() DBusTestCase.setUpClass() mock.dbus_mock = DBusTestCase() mock.dbus_mock.setUp() mock.templates_dir = parameters['templates-dir'] def set_nonblock(fd): '''Set a file object to non-blocking''' flags = fcntl.fcntl(fd, fcntl.F_GETFL) fcntl.fcntl(fd, fcntl.F_SETFL, flags | os.O_NONBLOCK) @dbus.service.method(MAIN_IFACE, in_signature='s') def StartFromTemplate(self, template): if template in self.mocks.keys(): raise KeyError('Template {} already started'.format(template)) mock_server, mock_obj = self.dbus_mock.spawn_server_template(template, {}, stdout=subprocess.PIPE) set_nonblock(mock_server.stdout) self.mocks[template] = (mock_server, mock_obj) @dbus.service.method(MAIN_IFACE, in_signature='s') def StartFromLocalTemplate(self, template): path = os.path.join(self.templates_dir, template + '.py') return self.StartFromTemplate(path) @dbus.service.method(MAIN_IFACE, in_signature='s') def StopTemplate(self, template): (mock_server, mock_obj) = self.mocks.pop(template) mock_server.terminate() mock_server.wait() @dbus.service.method(MAIN_IFACE, in_signature='s') def StopLocalTemplate(self, template): path = os.path.join(self.templates_dir, template + '.py') return self.StopTemplate(path) @dbus.service.method(MAIN_IFACE) def Cleanup(self): for (mock_server, mock_obj) in reversed(self.mocks.values()): mock_server.terminate() mock_server.wait() self.dbus_mock.tearDown() DBusTestCase.tearDownClass() @dbus.service.method(MAIN_IFACE, out_signature='as') def ListRunningTemplates(self): return list(self.mocks.keys())