From b71c6c60da448d8d79d40055533098bec3c21442 Mon Sep 17 00:00:00 2001 From: Mike Degatano Date: Mon, 12 Sep 2022 14:10:12 -0400 Subject: [PATCH] Share MessageBus across dbus objects (#3860) * Share MessageBus across dbus objects * Fix connect calls in tests --- supervisor/core.py | 1 + supervisor/dbus/agent/__init__.py | 13 +++--- supervisor/dbus/agent/apparmor.py | 5 ++- supervisor/dbus/agent/cgroup.py | 6 ++- supervisor/dbus/agent/datadisk.py | 6 ++- supervisor/dbus/agent/system.py | 6 ++- supervisor/dbus/hostname.py | 8 +++- supervisor/dbus/interface.py | 6 ++- supervisor/dbus/logind.py | 6 ++- supervisor/dbus/manager.py | 26 +++++++++++- supervisor/dbus/network/__init__.py | 17 ++++---- supervisor/dbus/network/accesspoint.py | 6 ++- supervisor/dbus/network/connection.py | 14 +++++-- supervisor/dbus/network/dns.py | 6 ++- supervisor/dbus/network/interface.py | 13 +++--- supervisor/dbus/network/setting/__init__.py | 6 ++- supervisor/dbus/network/settings.py | 9 +++-- supervisor/dbus/network/wireless.py | 10 +++-- supervisor/dbus/rauc.py | 6 ++- supervisor/dbus/resolved.py | 8 +++- supervisor/dbus/systemd.py | 6 ++- supervisor/dbus/timedate.py | 8 +++- supervisor/utils/dbus.py | 26 ++++++------ tests/api/test_dns.py | 2 +- tests/api/test_host.py | 4 +- tests/api/test_os.py | 6 +-- tests/conftest.py | 44 +++++++++++++-------- tests/dbus/agent/test_agent.py | 2 +- tests/dbus/agent/test_apparmor.py | 6 +-- tests/dbus/agent/test_cgroup.py | 3 +- tests/dbus/agent/test_datadisk.py | 6 +-- tests/dbus/agent/test_system.py | 2 +- tests/dbus/network/setting/test_init.py | 4 +- tests/dbus/network/test_accesspoint.py | 6 ++- tests/dbus/test_hostname.py | 4 +- tests/dbus/test_login.py | 4 +- tests/dbus/test_rauc.py | 8 ++-- tests/dbus/test_resolved.py | 2 +- tests/dbus/test_systemd.py | 16 ++++---- tests/dbus/test_timedate.py | 6 +-- tests/os/test_data_disk.py | 6 +-- tests/test_coresys.py | 2 +- tests/utils/test_dbus.py | 7 +++- 43 files changed, 222 insertions(+), 136 deletions(-) diff --git a/supervisor/core.py b/supervisor/core.py index 8a20f0513..1f57b5d96 100644 --- a/supervisor/core.py +++ b/supervisor/core.py @@ -298,6 +298,7 @@ class Core(CoreSysAttributes): self.sys_websession.close(), self.sys_ingress.unload(), self.sys_hardware.unload(), + self.sys_dbus.unload(), ] ) except asyncio.TimeoutError: diff --git a/supervisor/dbus/agent/__init__.py b/supervisor/dbus/agent/__init__.py index fc5c4e653..2db82c1ae 100644 --- a/supervisor/dbus/agent/__init__.py +++ b/supervisor/dbus/agent/__init__.py @@ -4,6 +4,7 @@ import logging from typing import Any from awesomeversion import AwesomeVersion +from dbus_next.aio.message_bus import MessageBus from ...exceptions import DBusError, DBusInterfaceError from ...utils.dbus import DBus @@ -78,14 +79,14 @@ class OSAgent(DBusInterface): self.dbus.set_property(DBUS_IFACE_HAOS, DBUS_ATTR_DIAGNOSTICS, value) ) - async def connect(self) -> None: + async def connect(self, bus: MessageBus) -> None: """Connect to system's D-Bus.""" try: - self.dbus = await DBus.connect(DBUS_NAME_HAOS, DBUS_OBJECT_HAOS) - await self.cgroup.connect() - await self.apparmor.connect() - await self.system.connect() - await self.datadisk.connect() + self.dbus = await DBus.connect(bus, DBUS_NAME_HAOS, DBUS_OBJECT_HAOS) + await self.cgroup.connect(bus) + await self.apparmor.connect(bus) + await self.system.connect(bus) + await self.datadisk.connect(bus) except DBusError: _LOGGER.warning("Can't connect to OS-Agent") except DBusInterfaceError: diff --git a/supervisor/dbus/agent/apparmor.py b/supervisor/dbus/agent/apparmor.py index 65a861dc5..72dd27bd7 100644 --- a/supervisor/dbus/agent/apparmor.py +++ b/supervisor/dbus/agent/apparmor.py @@ -3,6 +3,7 @@ from pathlib import Path from typing import Any from awesomeversion import AwesomeVersion +from dbus_next.aio.message_bus import MessageBus from ...utils.dbus import DBus from ..const import ( @@ -28,9 +29,9 @@ class AppArmor(DBusInterface): """Return version of host AppArmor parser.""" return AwesomeVersion(self.properties[DBUS_ATTR_PARSER_VERSION]) - async def connect(self) -> None: + async def connect(self, bus: MessageBus) -> None: """Get connection information.""" - self.dbus = await DBus.connect(DBUS_NAME_HAOS, DBUS_OBJECT_HAOS_APPARMOR) + self.dbus = await DBus.connect(bus, DBUS_NAME_HAOS, DBUS_OBJECT_HAOS_APPARMOR) @dbus_connected async def update(self): diff --git a/supervisor/dbus/agent/cgroup.py b/supervisor/dbus/agent/cgroup.py index b35e2a1c5..11c319d06 100644 --- a/supervisor/dbus/agent/cgroup.py +++ b/supervisor/dbus/agent/cgroup.py @@ -1,5 +1,7 @@ """CGroup object for OS-Agent.""" +from dbus_next.aio.message_bus import MessageBus + from ...utils.dbus import DBus from ..const import DBUS_NAME_HAOS, DBUS_OBJECT_HAOS_CGROUP from ..interface import DBusInterface @@ -9,9 +11,9 @@ from ..utils import dbus_connected class CGroup(DBusInterface): """CGroup object for OS Agent.""" - async def connect(self) -> None: + async def connect(self, bus: MessageBus) -> None: """Get connection information.""" - self.dbus = await DBus.connect(DBUS_NAME_HAOS, DBUS_OBJECT_HAOS_CGROUP) + self.dbus = await DBus.connect(bus, DBUS_NAME_HAOS, DBUS_OBJECT_HAOS_CGROUP) @dbus_connected async def add_devices_allowed(self, container_id: str, permission: str) -> None: diff --git a/supervisor/dbus/agent/datadisk.py b/supervisor/dbus/agent/datadisk.py index 0e1ae646a..bb2cc39fd 100644 --- a/supervisor/dbus/agent/datadisk.py +++ b/supervisor/dbus/agent/datadisk.py @@ -2,6 +2,8 @@ from pathlib import Path from typing import Any +from dbus_next.aio.message_bus import MessageBus + from ...utils.dbus import DBus from ..const import ( DBUS_ATTR_CURRENT_DEVICE, @@ -26,9 +28,9 @@ class DataDisk(DBusInterface): """Return current device used for data.""" return Path(self.properties[DBUS_ATTR_CURRENT_DEVICE]) - async def connect(self) -> None: + async def connect(self, bus: MessageBus) -> None: """Get connection information.""" - self.dbus = await DBus.connect(DBUS_NAME_HAOS, DBUS_OBJECT_HAOS_DATADISK) + self.dbus = await DBus.connect(bus, DBUS_NAME_HAOS, DBUS_OBJECT_HAOS_DATADISK) @dbus_connected async def update(self): diff --git a/supervisor/dbus/agent/system.py b/supervisor/dbus/agent/system.py index 5ed3600a7..2312533eb 100644 --- a/supervisor/dbus/agent/system.py +++ b/supervisor/dbus/agent/system.py @@ -1,5 +1,7 @@ """System object for OS-Agent.""" +from dbus_next.aio.message_bus import MessageBus + from ...utils.dbus import DBus from ..const import DBUS_NAME_HAOS, DBUS_OBJECT_HAOS_SYSTEM from ..interface import DBusInterface @@ -9,9 +11,9 @@ from ..utils import dbus_connected class System(DBusInterface): """System object for OS Agent.""" - async def connect(self) -> None: + async def connect(self, bus: MessageBus) -> None: """Get connection information.""" - self.dbus = await DBus.connect(DBUS_NAME_HAOS, DBUS_OBJECT_HAOS_SYSTEM) + self.dbus = await DBus.connect(bus, DBUS_NAME_HAOS, DBUS_OBJECT_HAOS_SYSTEM) @dbus_connected async def schedule_wipe_device(self) -> None: diff --git a/supervisor/dbus/hostname.py b/supervisor/dbus/hostname.py index 8f0995198..e94010040 100644 --- a/supervisor/dbus/hostname.py +++ b/supervisor/dbus/hostname.py @@ -2,6 +2,8 @@ import logging from typing import Any +from dbus_next.aio.message_bus import MessageBus + from ..exceptions import DBusError, DBusInterfaceError from ..utils.dbus import DBus from .const import ( @@ -33,10 +35,12 @@ class Hostname(DBusInterface): """Initialize Properties.""" self.properties: dict[str, Any] = {} - async def connect(self): + async def connect(self, bus: MessageBus): """Connect to system's D-Bus.""" try: - self.dbus = await DBus.connect(DBUS_NAME_HOSTNAME, DBUS_OBJECT_HOSTNAME) + self.dbus = await DBus.connect( + bus, DBUS_NAME_HOSTNAME, DBUS_OBJECT_HOSTNAME + ) except DBusError: _LOGGER.warning("Can't connect to systemd-hostname") except DBusInterfaceError: diff --git a/supervisor/dbus/interface.py b/supervisor/dbus/interface.py index 39e52c27b..15116bdba 100644 --- a/supervisor/dbus/interface.py +++ b/supervisor/dbus/interface.py @@ -3,6 +3,8 @@ from abc import ABC, abstractmethod from functools import wraps from typing import Any +from dbus_next.aio.message_bus import MessageBus + from ..utils.dbus import DBus @@ -31,7 +33,7 @@ class DBusInterface(ABC): return self.dbus is not None @abstractmethod - async def connect(self): + async def connect(self, bus: MessageBus): """Connect to D-Bus.""" def disconnect(self): @@ -47,5 +49,5 @@ class DBusInterfaceProxy(ABC): properties: dict[str, Any] | None = None @abstractmethod - async def connect(self): + async def connect(self, bus: MessageBus): """Connect to D-Bus.""" diff --git a/supervisor/dbus/logind.py b/supervisor/dbus/logind.py index 7a1cfe955..b88592a64 100644 --- a/supervisor/dbus/logind.py +++ b/supervisor/dbus/logind.py @@ -1,6 +1,8 @@ """Interface to Logind over D-Bus.""" import logging +from dbus_next.aio.message_bus import MessageBus + from ..exceptions import DBusError, DBusInterfaceError from ..utils.dbus import DBus from .const import DBUS_NAME_LOGIND, DBUS_OBJECT_LOGIND @@ -18,10 +20,10 @@ class Logind(DBusInterface): name = DBUS_NAME_LOGIND - async def connect(self): + async def connect(self, bus: MessageBus): """Connect to D-Bus.""" try: - self.dbus = await DBus.connect(DBUS_NAME_LOGIND, DBUS_OBJECT_LOGIND) + self.dbus = await DBus.connect(bus, DBUS_NAME_LOGIND, DBUS_OBJECT_LOGIND) except DBusError: _LOGGER.warning("Can't connect to systemd-logind") except DBusInterfaceError: diff --git a/supervisor/dbus/manager.py b/supervisor/dbus/manager.py index a3b4b5f7e..20cfcd44b 100644 --- a/supervisor/dbus/manager.py +++ b/supervisor/dbus/manager.py @@ -1,8 +1,12 @@ """D-Bus interface objects.""" import logging +from dbus_next import BusType +from dbus_next.aio.message_bus import MessageBus + from ..const import SOCKET_DBUS from ..coresys import CoreSys, CoreSysAttributes +from ..exceptions import DBusFatalError from .agent import OSAgent from .hostname import Hostname from .interface import DBusInterface @@ -31,6 +35,7 @@ class DBusManager(CoreSysAttributes): self._agent: OSAgent = OSAgent() self._timedate: TimeDate = TimeDate() self._resolved: Resolved = Resolved() + self._bus: MessageBus | None = None @property def systemd(self) -> Systemd: @@ -72,6 +77,11 @@ class DBusManager(CoreSysAttributes): """Return the resolved interface.""" return self._resolved + @property + def bus(self) -> MessageBus | None: + """Return the message bus.""" + return self._bus + async def load(self) -> None: """Connect interfaces to D-Bus.""" if not SOCKET_DBUS.exists(): @@ -80,6 +90,15 @@ class DBusManager(CoreSysAttributes): ) return + try: + self._bus = await MessageBus(bus_type=BusType.SYSTEM).connect() + except Exception as err: + raise DBusFatalError( + "Cannot connect to system D-Bus. Disabled any kind of host control!" + ) from err + + _LOGGER.info("Connected to system D-Bus.") + dbus_loads: list[DBusInterface] = [ self.agent, self.systemd, @@ -93,8 +112,13 @@ class DBusManager(CoreSysAttributes): for dbus in dbus_loads: _LOGGER.info("Load dbus interface %s", dbus.name) try: - await dbus.connect() + await dbus.connect(self._bus) except Exception as err: # pylint: disable=broad-except _LOGGER.warning("Can't load dbus interface %s: %s", dbus.name, err) self.sys_host.supported_features.cache_clear() + + async def unload(self) -> None: + """Close connection to D-Bus.""" + self._bus.disconnect() + _LOGGER.info("Closed conection to system D-Bus.") diff --git a/supervisor/dbus/network/__init__.py b/supervisor/dbus/network/__init__.py index c6faa0497..f384616cb 100644 --- a/supervisor/dbus/network/__init__.py +++ b/supervisor/dbus/network/__init__.py @@ -4,6 +4,7 @@ import logging from typing import Any from awesomeversion import AwesomeVersion, AwesomeVersionException +from dbus_next.aio.message_bus import MessageBus import sentry_sdk from ...exceptions import ( @@ -92,7 +93,7 @@ class NetworkManager(DBusInterface): ) obj_active_con = result[0] active_con = NetworkConnection(obj_active_con) - await active_con.connect() + await active_con.connect(self.dbus.bus) return active_con @dbus_connected @@ -106,7 +107,9 @@ class NetworkManager(DBusInterface): con_setting = NetworkSetting(obj_con_setting) active_con = NetworkConnection(obj_active_con) - await asyncio.gather(con_setting.connect(), active_con.connect()) + await asyncio.gather( + con_setting.connect(self.dbus.bus), active_con.connect(self.dbus.bus) + ) return con_setting, active_con @dbus_connected @@ -117,12 +120,12 @@ class NetworkManager(DBusInterface): else: return await self.dbus.get_property(DBUS_IFACE_NM, DBUS_ATTR_CONNECTIVITY) - async def connect(self) -> None: + async def connect(self, bus: MessageBus) -> None: """Connect to system's D-Bus.""" try: - self.dbus = await DBus.connect(DBUS_NAME_NM, DBUS_OBJECT_NM) - await self.dns.connect() - await self.settings.connect() + self.dbus = await DBus.connect(bus, DBUS_NAME_NM, DBUS_OBJECT_NM) + await self.dns.connect(bus) + await self.settings.connect(bus) except DBusError: _LOGGER.warning("Can't connect to Network Manager") except DBusInterfaceError: @@ -167,7 +170,7 @@ class NetworkManager(DBusInterface): # Connect to interface try: - await interface.connect() + await interface.connect(self.dbus.bus) except (DBusFatalError, DBusInterfaceMethodError) as err: # Docker creates and deletes interfaces quite often, sometimes # this causes a race condition: A device disappears while we diff --git a/supervisor/dbus/network/accesspoint.py b/supervisor/dbus/network/accesspoint.py index d8bb52ae1..5424645e0 100644 --- a/supervisor/dbus/network/accesspoint.py +++ b/supervisor/dbus/network/accesspoint.py @@ -1,5 +1,7 @@ """Connection object for Network Manager.""" +from dbus_next.aio.message_bus import MessageBus + from ...utils.dbus import DBus from ..const import ( DBUS_ATTR_FREQUENCY, @@ -54,7 +56,7 @@ class NetworkWirelessAP(DBusInterfaceProxy): """Return details about mac address.""" return int(self.properties[DBUS_ATTR_STRENGTH]) - async def connect(self) -> None: + async def connect(self, bus: MessageBus) -> None: """Get connection information.""" - self.dbus = await DBus.connect(DBUS_NAME_NM, self.object_path) + self.dbus = await DBus.connect(bus, DBUS_NAME_NM, self.object_path) self.properties = await self.dbus.get_properties(DBUS_IFACE_ACCESSPOINT) diff --git a/supervisor/dbus/network/connection.py b/supervisor/dbus/network/connection.py index 8f4823263..eb38943a6 100644 --- a/supervisor/dbus/network/connection.py +++ b/supervisor/dbus/network/connection.py @@ -1,6 +1,8 @@ """Connection object for Network Manager.""" from ipaddress import ip_address, ip_interface +from dbus_next.aio.message_bus import MessageBus + from ...const import ATTR_ADDRESS, ATTR_PREFIX from ...utils.dbus import DBus from ..const import ( @@ -89,9 +91,9 @@ class NetworkConnection(DBusInterfaceProxy): """Return a ip6 configuration object for the connection.""" return self._ipv6 - async def connect(self) -> None: + async def connect(self, bus: MessageBus) -> None: """Get connection information.""" - self.dbus = await DBus.connect(DBUS_NAME_NM, self.object_path) + self.dbus = await DBus.connect(bus, DBUS_NAME_NM, self.object_path) await self.update() @dbus_connected @@ -108,7 +110,9 @@ class NetworkConnection(DBusInterfaceProxy): # IPv4 if self.properties[DBUS_ATTR_IP4CONFIG] != DBUS_OBJECT_BASE: - ip4 = await DBus.connect(DBUS_NAME_NM, self.properties[DBUS_ATTR_IP4CONFIG]) + ip4 = await DBus.connect( + self.dbus.bus, DBUS_NAME_NM, self.properties[DBUS_ATTR_IP4CONFIG] + ) ip4_data = await ip4.get_properties(DBUS_IFACE_IP4CONFIG) self._ipv4 = IpConfiguration( @@ -127,7 +131,9 @@ class NetworkConnection(DBusInterfaceProxy): # IPv6 if self.properties[DBUS_ATTR_IP6CONFIG] != DBUS_OBJECT_BASE: - ip6 = await DBus.connect(DBUS_NAME_NM, self.properties[DBUS_ATTR_IP6CONFIG]) + ip6 = await DBus.connect( + self.dbus.bus, DBUS_NAME_NM, self.properties[DBUS_ATTR_IP6CONFIG] + ) ip6_data = await ip6.get_properties(DBUS_IFACE_IP6CONFIG) self._ipv6 = IpConfiguration( diff --git a/supervisor/dbus/network/dns.py b/supervisor/dbus/network/dns.py index 324e8b6e7..c6da4fe09 100644 --- a/supervisor/dbus/network/dns.py +++ b/supervisor/dbus/network/dns.py @@ -2,6 +2,8 @@ from ipaddress import ip_address import logging +from dbus_next.aio.message_bus import MessageBus + from ...const import ( ATTR_DOMAINS, ATTR_INTERFACE, @@ -53,10 +55,10 @@ class NetworkManagerDNS(DBusInterface): """Return Propertie configuraton.""" return self._configuration - async def connect(self) -> None: + async def connect(self, bus: MessageBus) -> None: """Connect to system's D-Bus.""" try: - self.dbus = await DBus.connect(DBUS_NAME_NM, DBUS_OBJECT_DNS) + self.dbus = await DBus.connect(bus, DBUS_NAME_NM, DBUS_OBJECT_DNS) except DBusError: _LOGGER.warning("Can't connect to DnsManager") except DBusInterfaceError: diff --git a/supervisor/dbus/network/interface.py b/supervisor/dbus/network/interface.py index c630bde7e..76654ae25 100644 --- a/supervisor/dbus/network/interface.py +++ b/supervisor/dbus/network/interface.py @@ -1,4 +1,7 @@ """NetworkInterface object for Network Manager.""" + +from dbus_next.aio.message_bus import MessageBus + from ...utils.dbus import DBus from ..const import ( DBUS_ATTR_ACTIVE_CONNECTION, @@ -74,9 +77,9 @@ class NetworkInterface(DBusInterfaceProxy): """Return the wireless data for this interface.""" return self._wireless - async def connect(self) -> None: + async def connect(self, bus: MessageBus) -> None: """Get device information.""" - self.dbus = await DBus.connect(DBUS_NAME_NM, self.object_path) + self.dbus = await DBus.connect(bus, DBUS_NAME_NM, self.object_path) self.properties = await self.dbus.get_properties(DBUS_IFACE_DEVICE) # Abort if device is not managed @@ -88,14 +91,14 @@ class NetworkInterface(DBusInterfaceProxy): self._connection = NetworkConnection( self.properties[DBUS_ATTR_ACTIVE_CONNECTION] ) - await self._connection.connect() + await self._connection.connect(bus) # Attach settings if self.connection and self.connection.setting_object != DBUS_OBJECT_BASE: self._settings = NetworkSetting(self.connection.setting_object) - await self._settings.connect() + await self._settings.connect(bus) # Wireless if self.type == DeviceType.WIRELESS: self._wireless = NetworkWireless(self.object_path) - await self._wireless.connect() + await self._wireless.connect(bus) diff --git a/supervisor/dbus/network/setting/__init__.py b/supervisor/dbus/network/setting/__init__.py index af7a348a9..53e99ca95 100644 --- a/supervisor/dbus/network/setting/__init__.py +++ b/supervisor/dbus/network/setting/__init__.py @@ -2,6 +2,8 @@ import logging from typing import Any +from dbus_next.aio.message_bus import MessageBus + from ....const import ATTR_METHOD, ATTR_MODE, ATTR_PSK, ATTR_SSID from ....utils.dbus import DBus from ...const import DBUS_NAME_NM @@ -158,9 +160,9 @@ class NetworkSetting(DBusInterfaceProxy): """Delete connection settings.""" await self.dbus.Settings.Connection.Delete() - async def connect(self) -> None: + async def connect(self, bus: MessageBus) -> None: """Get connection information.""" - self.dbus = await DBus.connect(DBUS_NAME_NM, self.object_path) + self.dbus = await DBus.connect(bus, DBUS_NAME_NM, self.object_path) data = await self.get_settings() # Get configuration settings we care about diff --git a/supervisor/dbus/network/settings.py b/supervisor/dbus/network/settings.py index 84092659b..0fa3a2162 100644 --- a/supervisor/dbus/network/settings.py +++ b/supervisor/dbus/network/settings.py @@ -2,12 +2,13 @@ import logging from typing import Any -from supervisor.dbus.network.setting import NetworkSetting +from dbus_next.aio.message_bus import MessageBus from ...exceptions import DBusError, DBusInterfaceError from ...utils.dbus import DBus from ..const import DBUS_NAME_NM, DBUS_OBJECT_SETTINGS from ..interface import DBusInterface +from ..network.setting import NetworkSetting from ..utils import dbus_connected _LOGGER: logging.Logger = logging.getLogger(__name__) @@ -19,10 +20,10 @@ class NetworkManagerSettings(DBusInterface): https://developer.gnome.org/NetworkManager/stable/gdbus-org.freedesktop.NetworkManager.Settings.html """ - async def connect(self) -> None: + async def connect(self, bus: MessageBus) -> None: """Connect to system's D-Bus.""" try: - self.dbus = await DBus.connect(DBUS_NAME_NM, DBUS_OBJECT_SETTINGS) + self.dbus = await DBus.connect(bus, DBUS_NAME_NM, DBUS_OBJECT_SETTINGS) except DBusError: _LOGGER.warning("Can't connect to Network Manager Settings") except DBusInterfaceError: @@ -37,7 +38,7 @@ class NetworkManagerSettings(DBusInterface): await self.dbus.Settings.AddConnection(("a{sa{sv}}", settings)) )[0] con_setting = NetworkSetting(obj_con_setting) - await con_setting.connect() + await con_setting.connect(self.dbus.bus) return con_setting @dbus_connected diff --git a/supervisor/dbus/network/wireless.py b/supervisor/dbus/network/wireless.py index a7a97ef39..4417a8e69 100644 --- a/supervisor/dbus/network/wireless.py +++ b/supervisor/dbus/network/wireless.py @@ -2,6 +2,8 @@ import asyncio import logging +from dbus_next.aio.message_bus import MessageBus + from ...utils.dbus import DBus from ..const import ( DBUS_ATTR_ACTIVE_ACCESSPOINT, @@ -46,16 +48,16 @@ class NetworkWireless(DBusInterfaceProxy): accesspoints = [NetworkWirelessAP(ap_obj) for ap_obj in accesspoints_data] for err in await asyncio.gather( - *[ap.connect() for ap in accesspoints], return_exceptions=True + *[ap.connect(self.dbus.bus) for ap in accesspoints], return_exceptions=True ): if err: _LOGGER.warning("Can't process an AP: %s", err) return accesspoints - async def connect(self) -> None: + async def connect(self, bus: MessageBus) -> None: """Get connection information.""" - self.dbus = await DBus.connect(DBUS_NAME_NM, self.object_path) + self.dbus = await DBus.connect(bus, DBUS_NAME_NM, self.object_path) self.properties = await self.dbus.get_properties(DBUS_IFACE_DEVICE_WIRELESS) # Get details from current active @@ -63,4 +65,4 @@ class NetworkWireless(DBusInterfaceProxy): self._active = NetworkWirelessAP( self.properties[DBUS_ATTR_ACTIVE_ACCESSPOINT] ) - await self._active.connect() + await self._active.connect(bus) diff --git a/supervisor/dbus/rauc.py b/supervisor/dbus/rauc.py index 367a53a69..cbf75c9ac 100644 --- a/supervisor/dbus/rauc.py +++ b/supervisor/dbus/rauc.py @@ -2,6 +2,8 @@ import logging from typing import Any +from dbus_next.aio.message_bus import MessageBus + from ..exceptions import DBusError, DBusInterfaceError from ..utils.dbus import DBus, DBusSignalWrapper from .const import ( @@ -35,10 +37,10 @@ class Rauc(DBusInterface): self._variant: str | None = None self._boot_slot: str | None = None - async def connect(self): + async def connect(self, bus: MessageBus): """Connect to D-Bus.""" try: - self.dbus = await DBus.connect(DBUS_NAME_RAUC, DBUS_OBJECT_BASE) + self.dbus = await DBus.connect(bus, DBUS_NAME_RAUC, DBUS_OBJECT_BASE) except DBusError: _LOGGER.warning("Can't connect to rauc") except DBusInterfaceError: diff --git a/supervisor/dbus/resolved.py b/supervisor/dbus/resolved.py index 33774baf3..b3ebc04b1 100644 --- a/supervisor/dbus/resolved.py +++ b/supervisor/dbus/resolved.py @@ -4,6 +4,8 @@ from __future__ import annotations import logging from typing import Any +from dbus_next.aio.message_bus import MessageBus + from ..exceptions import DBusError, DBusInterfaceError from ..utils.dbus import DBus from .const import ( @@ -54,10 +56,12 @@ class Resolved(DBusInterface): """Initialize Properties.""" self.properties: dict[str, Any] = {} - async def connect(self): + async def connect(self, bus: MessageBus): """Connect to D-Bus.""" try: - self.dbus = await DBus.connect(DBUS_NAME_RESOLVED, DBUS_OBJECT_RESOLVED) + self.dbus = await DBus.connect( + bus, DBUS_NAME_RESOLVED, DBUS_OBJECT_RESOLVED + ) except DBusError: _LOGGER.warning("Can't connect to systemd-resolved.") except DBusInterfaceError: diff --git a/supervisor/dbus/systemd.py b/supervisor/dbus/systemd.py index 16f6cd704..418421ecd 100644 --- a/supervisor/dbus/systemd.py +++ b/supervisor/dbus/systemd.py @@ -2,6 +2,8 @@ import logging from typing import Any +from dbus_next.aio.message_bus import MessageBus + from ..exceptions import DBusError, DBusInterfaceError from ..utils.dbus import DBus from .const import ( @@ -32,10 +34,10 @@ class Systemd(DBusInterface): """Initialize Properties.""" self.properties: dict[str, Any] = {} - async def connect(self): + async def connect(self, bus: MessageBus): """Connect to D-Bus.""" try: - self.dbus = await DBus.connect(DBUS_NAME_SYSTEMD, DBUS_OBJECT_SYSTEMD) + self.dbus = await DBus.connect(bus, DBUS_NAME_SYSTEMD, DBUS_OBJECT_SYSTEMD) except DBusError: _LOGGER.warning("Can't connect to systemd") except DBusInterfaceError: diff --git a/supervisor/dbus/timedate.py b/supervisor/dbus/timedate.py index 4b449fd14..346833171 100644 --- a/supervisor/dbus/timedate.py +++ b/supervisor/dbus/timedate.py @@ -3,6 +3,8 @@ from datetime import datetime import logging from typing import Any +from dbus_next.aio.message_bus import MessageBus + from ..exceptions import DBusError, DBusInterfaceError from ..utils.dbus import DBus from ..utils.dt import utc_from_timestamp @@ -57,10 +59,12 @@ class TimeDate(DBusInterface): """Return the system UTC time.""" return utc_from_timestamp(self.properties[DBUS_ATTR_TIMEUSEC] / 1000000) - async def connect(self): + async def connect(self, bus: MessageBus): """Connect to D-Bus.""" try: - self.dbus = await DBus.connect(DBUS_NAME_TIMEDATE, DBUS_OBJECT_TIMEDATE) + self.dbus = await DBus.connect( + bus, DBUS_NAME_TIMEDATE, DBUS_OBJECT_TIMEDATE + ) except DBusError: _LOGGER.warning("Can't connect to systemd-timedate") except DBusInterfaceError: diff --git a/supervisor/utils/dbus.py b/supervisor/utils/dbus.py index 2d9586638..723029571 100644 --- a/supervisor/utils/dbus.py +++ b/supervisor/utils/dbus.py @@ -5,8 +5,8 @@ import asyncio import logging from typing import Any -from dbus_next import BusType, InvalidIntrospectionError, Message, MessageType -from dbus_next.aio import MessageBus +from dbus_next import InvalidIntrospectionError, Message, MessageType +from dbus_next.aio.message_bus import MessageBus from dbus_next.introspection import Node from dbus_next.signature import Variant @@ -45,23 +45,18 @@ DBUS_METHOD_SET: str = "org.freedesktop.DBus.Properties.Set" class DBus: """DBus handler.""" - def __init__(self, bus_name: str, object_path: str) -> None: + def __init__(self, bus: MessageBus, bus_name: str, object_path: str) -> None: """Initialize dbus object.""" self.bus_name: str = bus_name self.object_path: str = object_path self.methods: set[str] = set() self.signals: set[str] = set() - self._bus: MessageBus | None = None - - def __del__(self): - """Delete dbus object.""" - if self._bus: - self._bus.disconnect() + self._bus: MessageBus = bus @staticmethod - async def connect(bus_name: str, object_path: str) -> DBus: + async def connect(bus: MessageBus, bus_name: str, object_path: str) -> DBus: """Read object data.""" - self = DBus(bus_name, object_path) + self = DBus(bus, bus_name, object_path) # pylint: disable=protected-access await self._init_proxy() @@ -69,6 +64,11 @@ class DBus: _LOGGER.debug("Connect to D-Bus: %s - %s", bus_name, object_path) return self + @property + def bus(self) -> MessageBus: + """Return message bus.""" + return self._bus + def _add_interfaces(self, introspection: Any): # Read available methods for interface in introspection.interfaces: @@ -88,10 +88,6 @@ class DBus: """Read interface data.""" # Wait for dbus object to be available after restart introspection: Node | None = None - try: - self._bus = await MessageBus(bus_type=BusType.SYSTEM).connect() - except Exception as err: - raise DBusFatalError() from err for _ in range(3): try: diff --git a/tests/api/test_dns.py b/tests/api/test_dns.py index bcae9724b..7d93e2709 100644 --- a/tests/api/test_dns.py +++ b/tests/api/test_dns.py @@ -29,7 +29,7 @@ async def test_llmnr_mdns_info(api_client, coresys: CoreSys): assert result["data"]["llmnr"] is False assert result["data"]["mdns"] is False - await coresys.dbus.resolved.connect() + await coresys.dbus.resolved.connect(coresys.dbus.bus) await coresys.dbus.resolved.update() resp = await api_client.get("/dns/info") diff --git a/tests/api/test_host.py b/tests/api/test_host.py index 5c85d2389..daf809e72 100644 --- a/tests/api/test_host.py +++ b/tests/api/test_host.py @@ -23,7 +23,7 @@ async def test_api_host_info(api_client, coresys_disk_info: CoreSys): """Test host info api.""" coresys = coresys_disk_info - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) await coresys.dbus.agent.update() resp = await api_client.get("/host/info") @@ -106,7 +106,7 @@ async def test_api_llmnr_mdns_info(api_client, coresys_disk_info: CoreSys): assert result["data"]["llmnr_hostname"] is None coresys.host.sys_dbus.resolved.is_connected = True - await coresys.dbus.resolved.connect() + await coresys.dbus.resolved.connect(coresys.dbus.bus) await coresys.dbus.resolved.update() resp = await api_client.get("/host/info") diff --git a/tests/api/test_os.py b/tests/api/test_os.py index a470195e5..198f955db 100644 --- a/tests/api/test_os.py +++ b/tests/api/test_os.py @@ -29,7 +29,7 @@ async def test_api_os_info(api_client): @pytest.mark.asyncio async def test_api_os_info_with_agent(api_client, coresys: CoreSys): """Test docker info api.""" - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) await coresys.dbus.agent.update() resp = await api_client.get("/os/info") @@ -41,7 +41,7 @@ async def test_api_os_info_with_agent(api_client, coresys: CoreSys): @pytest.mark.asyncio async def test_api_os_datadisk_move(api_client, coresys: CoreSys): """Test datadisk move without exists disk.""" - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) await coresys.dbus.agent.update() coresys.os._available = True @@ -54,7 +54,7 @@ async def test_api_os_datadisk_move(api_client, coresys: CoreSys): @pytest.mark.asyncio async def test_api_os_datadisk_list(api_client, coresys: CoreSys): """Test datadisk list function.""" - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) await coresys.dbus.agent.update() coresys.hardware.update_device( diff --git a/tests/conftest.py b/tests/conftest.py index a834d516d..b4a502c00 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -10,6 +10,7 @@ from uuid import uuid4 from aiohttp import web from awesomeversion import AwesomeVersion from dbus_next import introspection as intr +from dbus_next.aio.message_bus import MessageBus import pytest from securetar import SecureTarFile @@ -103,7 +104,13 @@ def docker() -> DockerAPI: @pytest.fixture -def dbus() -> DBus: +async def dbus_bus() -> MessageBus: + """Message bus mock.""" + yield AsyncMock(spec=MessageBus) + + +@pytest.fixture +def dbus(dbus_bus: MessageBus) -> DBus: """Mock DBUS.""" dbus_commands = [] @@ -189,63 +196,67 @@ def dbus() -> DBus: new=mock_wait_for_signal, ), patch( "supervisor.utils.dbus.DBus.get_property", new=mock_get_property + ), patch( + "supervisor.dbus.manager.MessageBus.connect", return_value=dbus_bus ): yield dbus_commands @pytest.fixture -async def network_manager(dbus) -> NetworkManager: +async def network_manager(dbus, dbus_bus: MessageBus) -> NetworkManager: """Mock NetworkManager.""" nm_obj = NetworkManager() nm_obj.dbus = dbus # Init - await nm_obj.connect() + await nm_obj.connect(dbus_bus) await nm_obj.update() yield nm_obj -async def mock_dbus_interface(dbus: DBus, instance: DBusInterface) -> DBusInterface: +async def mock_dbus_interface( + dbus: DBus, dbus_bus: MessageBus, instance: DBusInterface +) -> DBusInterface: """Mock dbus for a DBusInterface instance.""" instance.dbus = dbus - await instance.connect() + await instance.connect(dbus_bus) return instance @pytest.fixture -async def hostname(dbus: DBus) -> Hostname: +async def hostname(dbus: DBus, dbus_bus: MessageBus) -> Hostname: """Mock Hostname.""" - yield await mock_dbus_interface(dbus, Hostname()) + yield await mock_dbus_interface(dbus, dbus_bus, Hostname()) @pytest.fixture -async def timedate(dbus: DBus) -> TimeDate: +async def timedate(dbus: DBus, dbus_bus: MessageBus) -> TimeDate: """Mock Timedate.""" - yield await mock_dbus_interface(dbus, TimeDate()) + yield await mock_dbus_interface(dbus, dbus_bus, TimeDate()) @pytest.fixture -async def systemd(dbus: DBus) -> Systemd: +async def systemd(dbus: DBus, dbus_bus: MessageBus) -> Systemd: """Mock Systemd.""" - yield await mock_dbus_interface(dbus, Systemd()) + yield await mock_dbus_interface(dbus, dbus_bus, Systemd()) @pytest.fixture -async def os_agent(dbus: DBus) -> OSAgent: +async def os_agent(dbus: DBus, dbus_bus: MessageBus) -> OSAgent: """Mock OSAgent.""" - yield await mock_dbus_interface(dbus, OSAgent()) + yield await mock_dbus_interface(dbus, dbus_bus, OSAgent()) @pytest.fixture -async def resolved(dbus: DBus) -> Resolved: +async def resolved(dbus: DBus, dbus_bus: MessageBus) -> Resolved: """Mock REsolved.""" - yield await mock_dbus_interface(dbus, Resolved()) + yield await mock_dbus_interface(dbus, dbus_bus, Resolved()) @pytest.fixture async def coresys( - event_loop, docker, network_manager, aiohttp_client, run_dir + event_loop, docker, network_manager, dbus_bus, aiohttp_client, run_dir ) -> CoreSys: """Create a CoreSys Mock.""" with patch("supervisor.bootstrap.initialize_system"), patch( @@ -269,6 +280,7 @@ async def coresys( coresys_obj._machine_id = uuid4() # Mock host communication + coresys_obj._dbus._bus = dbus_bus coresys_obj._dbus._network = network_manager # Mock docker diff --git a/tests/dbus/agent/test_agent.py b/tests/dbus/agent/test_agent.py index 87befe755..f9cfd38c8 100644 --- a/tests/dbus/agent/test_agent.py +++ b/tests/dbus/agent/test_agent.py @@ -8,7 +8,7 @@ async def test_dbus_osagent(coresys: CoreSys): assert coresys.dbus.agent.version is None assert coresys.dbus.agent.diagnostics is None - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) await coresys.dbus.agent.update() assert coresys.dbus.agent.version == "1.1.0" diff --git a/tests/dbus/agent/test_apparmor.py b/tests/dbus/agent/test_apparmor.py index 63ccfd32f..1d291e431 100644 --- a/tests/dbus/agent/test_apparmor.py +++ b/tests/dbus/agent/test_apparmor.py @@ -11,7 +11,7 @@ async def test_dbus_osagent_apparmor(coresys: CoreSys): """Test coresys dbus connection.""" assert coresys.dbus.agent.apparmor.version is None - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) await coresys.dbus.agent.update() assert coresys.dbus.agent.apparmor.version == "2.13.2" @@ -24,7 +24,7 @@ async def test_dbus_osagent_apparmor_load(coresys: CoreSys, dbus: list[str]): Path("/data/apparmor/profile"), Path("/data/apparmor/cache") ) - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) dbus.clear() assert ( @@ -43,7 +43,7 @@ async def test_dbus_osagent_apparmor_unload(coresys: CoreSys, dbus: list[str]): Path("/data/apparmor/profile"), Path("/data/apparmor/cache") ) - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) dbus.clear() assert ( diff --git a/tests/dbus/agent/test_cgroup.py b/tests/dbus/agent/test_cgroup.py index 90ea6193b..30c643cbb 100644 --- a/tests/dbus/agent/test_cgroup.py +++ b/tests/dbus/agent/test_cgroup.py @@ -8,11 +8,10 @@ from supervisor.exceptions import DBusNotConnectedError async def test_dbus_osagent_cgroup_add_devices(coresys: CoreSys, dbus: list[str]): """Test wipe data partition on host.""" - with pytest.raises(DBusNotConnectedError): await coresys.dbus.agent.cgroup.add_devices_allowed("9324kl23j4kl", "*:* rwm") - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) dbus.clear() assert ( diff --git a/tests/dbus/agent/test_datadisk.py b/tests/dbus/agent/test_datadisk.py index 91765b52c..c60de7136 100644 --- a/tests/dbus/agent/test_datadisk.py +++ b/tests/dbus/agent/test_datadisk.py @@ -11,7 +11,7 @@ async def test_dbus_osagent_datadisk(coresys: CoreSys): """Test coresys dbus connection.""" assert coresys.dbus.agent.datadisk.current_device is None - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) await coresys.dbus.agent.update() assert coresys.dbus.agent.datadisk.current_device.as_posix() == "/dev/sda" @@ -22,7 +22,7 @@ async def test_dbus_osagent_datadisk_change_device(coresys: CoreSys, dbus: list[ with pytest.raises(DBusNotConnectedError): await coresys.dbus.agent.datadisk.change_device(Path("/dev/sdb")) - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) dbus.clear() assert await coresys.dbus.agent.datadisk.change_device(Path("/dev/sdb")) is None @@ -34,7 +34,7 @@ async def test_dbus_osagent_datadisk_reload_device(coresys: CoreSys, dbus: list[ with pytest.raises(DBusNotConnectedError): await coresys.dbus.agent.datadisk.reload_device() - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) dbus.clear() assert await coresys.dbus.agent.datadisk.reload_device() is None diff --git a/tests/dbus/agent/test_system.py b/tests/dbus/agent/test_system.py index 6e6c1413c..417298aed 100644 --- a/tests/dbus/agent/test_system.py +++ b/tests/dbus/agent/test_system.py @@ -11,7 +11,7 @@ async def test_dbus_osagent_system_wipe(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.agent.system.schedule_wipe_device() - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) dbus.clear() assert await coresys.dbus.agent.system.schedule_wipe_device() is None diff --git a/tests/dbus/network/setting/test_init.py b/tests/dbus/network/setting/test_init.py index 20ed60ac2..85297947c 100644 --- a/tests/dbus/network/setting/test_init.py +++ b/tests/dbus/network/setting/test_init.py @@ -134,7 +134,7 @@ async def mock_call_dbus_get_settings_signature( async def test_update(coresys: CoreSys): """Test network manager update.""" - await coresys.dbus.network.interfaces[TEST_INTERFACE].connect() + await coresys.dbus.network.interfaces[TEST_INTERFACE].connect(coresys.dbus.bus) interface = Interface.from_dbus_interface( coresys.dbus.network.interfaces[TEST_INTERFACE] ) @@ -154,7 +154,7 @@ async def test_update(coresys: CoreSys): async def test_ipv6_disabled_is_link_local(coresys: CoreSys): """Test disabled equals link local for ipv6.""" - await coresys.dbus.network.interfaces[TEST_INTERFACE].connect() + await coresys.dbus.network.interfaces[TEST_INTERFACE].connect(coresys.dbus.bus) interface = Interface.from_dbus_interface( coresys.dbus.network.interfaces[TEST_INTERFACE] ) diff --git a/tests/dbus/network/test_accesspoint.py b/tests/dbus/network/test_accesspoint.py index ecec4648b..8fac191dc 100644 --- a/tests/dbus/network/test_accesspoint.py +++ b/tests/dbus/network/test_accesspoint.py @@ -1,15 +1,17 @@ """Test NetworkWireless AP object.""" +from dbus_next.aio.message_bus import MessageBus + from supervisor.dbus.network.accesspoint import NetworkWirelessAP -async def test_accesspoint(dbus: list[str]): +async def test_accesspoint(dbus: list[str], dbus_bus: MessageBus): """Test accesspoint.""" wireless_ap = NetworkWirelessAP("/org/freedesktop/NetworkManager/AccessPoint/43099") assert wireless_ap.mac is None assert wireless_ap.mode is None - await wireless_ap.connect() + await wireless_ap.connect(dbus_bus) assert wireless_ap.mac == "E4:57:40:A9:D7:DE" assert wireless_ap.mode == 2 diff --git a/tests/dbus/test_hostname.py b/tests/dbus/test_hostname.py index e7c6a5fa4..b9ed783d5 100644 --- a/tests/dbus/test_hostname.py +++ b/tests/dbus/test_hostname.py @@ -10,7 +10,7 @@ async def test_dbus_hostname_info(coresys: CoreSys): """Test coresys dbus connection.""" assert coresys.dbus.hostname.hostname is None - await coresys.dbus.hostname.connect() + await coresys.dbus.hostname.connect(coresys.dbus.bus) await coresys.dbus.hostname.update() assert coresys.dbus.hostname.hostname == "homeassistant-n2" @@ -27,7 +27,7 @@ async def test_dbus_sethostname(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.hostname.set_static_hostname("StarWars") - await coresys.dbus.hostname.connect() + await coresys.dbus.hostname.connect(coresys.dbus.bus) dbus.clear() await coresys.dbus.hostname.set_static_hostname("StarWars") diff --git a/tests/dbus/test_login.py b/tests/dbus/test_login.py index 9b8dc62c7..b75649575 100644 --- a/tests/dbus/test_login.py +++ b/tests/dbus/test_login.py @@ -10,7 +10,7 @@ async def test_reboot(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.logind.reboot() - await coresys.dbus.logind.connect() + await coresys.dbus.logind.connect(coresys.dbus.bus) dbus.clear() assert await coresys.dbus.logind.reboot() is None @@ -22,7 +22,7 @@ async def test_power_off(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.logind.power_off() - await coresys.dbus.logind.connect() + await coresys.dbus.logind.connect(coresys.dbus.bus) dbus.clear() assert await coresys.dbus.logind.power_off() is None diff --git a/tests/dbus/test_rauc.py b/tests/dbus/test_rauc.py index 60327f7e1..625737ed4 100644 --- a/tests/dbus/test_rauc.py +++ b/tests/dbus/test_rauc.py @@ -11,7 +11,7 @@ async def test_rauc(coresys: CoreSys): assert coresys.dbus.rauc.boot_slot is None assert coresys.dbus.rauc.operation is None - await coresys.dbus.rauc.connect() + await coresys.dbus.rauc.connect(coresys.dbus.bus) await coresys.dbus.rauc.update() assert coresys.dbus.rauc.boot_slot == "B" @@ -23,7 +23,7 @@ async def test_install(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.rauc.install("rauc_file") - await coresys.dbus.rauc.connect() + await coresys.dbus.rauc.connect(coresys.dbus.bus) dbus.clear() async with coresys.dbus.rauc.signal_completed() as signal: @@ -38,7 +38,7 @@ async def test_get_slot_status(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.rauc.get_slot_status() - await coresys.dbus.rauc.connect() + await coresys.dbus.rauc.connect(coresys.dbus.bus) dbus.clear() slot_status = await coresys.dbus.rauc.get_slot_status() @@ -59,7 +59,7 @@ async def test_mark(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.rauc.mark(RaucState.GOOD, "booted") - await coresys.dbus.rauc.connect() + await coresys.dbus.rauc.connect(coresys.dbus.bus) dbus.clear() mark = await coresys.dbus.rauc.mark(RaucState.GOOD, "booted") diff --git a/tests/dbus/test_resolved.py b/tests/dbus/test_resolved.py index ecff22215..166f496f5 100644 --- a/tests/dbus/test_resolved.py +++ b/tests/dbus/test_resolved.py @@ -52,7 +52,7 @@ async def test_dbus_resolved_info(coresys_ip_bytes: CoreSys): assert coresys.dbus.resolved.dns is None - await coresys.dbus.resolved.connect() + await coresys.dbus.resolved.connect(coresys.dbus.bus) await coresys.dbus.resolved.update() assert coresys.dbus.resolved.llmnr_hostname == "homeassistant" diff --git a/tests/dbus/test_systemd.py b/tests/dbus/test_systemd.py index 74ea63d6b..5312cd740 100644 --- a/tests/dbus/test_systemd.py +++ b/tests/dbus/test_systemd.py @@ -16,7 +16,7 @@ async def test_dbus_systemd_info(coresys: CoreSys): assert coresys.dbus.systemd.boot_timestamp is None assert coresys.dbus.systemd.startup_time is None - await coresys.dbus.systemd.connect() + await coresys.dbus.systemd.connect(coresys.dbus.bus) async def mock_get_properties(dbus_obj, interface): return load_json_fixture( @@ -35,7 +35,7 @@ async def test_reboot(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.systemd.reboot() - await coresys.dbus.systemd.connect() + await coresys.dbus.systemd.connect(coresys.dbus.bus) dbus.clear() assert await coresys.dbus.systemd.reboot() is None @@ -47,7 +47,7 @@ async def test_power_off(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.systemd.power_off() - await coresys.dbus.systemd.connect() + await coresys.dbus.systemd.connect(coresys.dbus.bus) dbus.clear() assert await coresys.dbus.systemd.power_off() is None @@ -61,7 +61,7 @@ async def test_start_unit(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.systemd.start_unit("test_unit", "replace") - await coresys.dbus.systemd.connect() + await coresys.dbus.systemd.connect(coresys.dbus.bus) dbus.clear() assert ( @@ -78,7 +78,7 @@ async def test_stop_unit(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.systemd.stop_unit("test_unit", "replace") - await coresys.dbus.systemd.connect() + await coresys.dbus.systemd.connect(coresys.dbus.bus) dbus.clear() assert ( @@ -95,7 +95,7 @@ async def test_restart_unit(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.systemd.restart_unit("test_unit", "replace") - await coresys.dbus.systemd.connect() + await coresys.dbus.systemd.connect(coresys.dbus.bus) dbus.clear() assert ( @@ -112,7 +112,7 @@ async def test_reload_unit(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.systemd.reload_unit("test_unit", "replace") - await coresys.dbus.systemd.connect() + await coresys.dbus.systemd.connect(coresys.dbus.bus) dbus.clear() assert ( @@ -129,7 +129,7 @@ async def test_list_units(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.systemd.list_units() - await coresys.dbus.systemd.connect() + await coresys.dbus.systemd.connect(coresys.dbus.bus) dbus.clear() units = await coresys.dbus.systemd.list_units() diff --git a/tests/dbus/test_timedate.py b/tests/dbus/test_timedate.py index 3ef6f1885..c38037aaf 100644 --- a/tests/dbus/test_timedate.py +++ b/tests/dbus/test_timedate.py @@ -11,7 +11,7 @@ async def test_dbus_timezone(coresys: CoreSys): """Test coresys dbus connection.""" assert coresys.dbus.timedate.dt_utc is None - await coresys.dbus.timedate.connect() + await coresys.dbus.timedate.connect(coresys.dbus.bus) await coresys.dbus.timedate.update() assert coresys.dbus.timedate.dt_utc == datetime( @@ -30,7 +30,7 @@ async def test_dbus_settime(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.timedate.set_time(test_dt) - await coresys.dbus.timedate.connect() + await coresys.dbus.timedate.connect(coresys.dbus.bus) dbus.clear() assert await coresys.dbus.timedate.set_time(test_dt) is None @@ -42,7 +42,7 @@ async def test_dbus_setntp(coresys: CoreSys, dbus: list[str]): with pytest.raises(DBusNotConnectedError): await coresys.dbus.timedate.set_ntp(False) - await coresys.dbus.timedate.connect() + await coresys.dbus.timedate.connect(coresys.dbus.bus) dbus.clear() assert await coresys.dbus.timedate.set_ntp(False) is None diff --git a/tests/os/test_data_disk.py b/tests/os/test_data_disk.py index 04658637f..e23883708 100644 --- a/tests/os/test_data_disk.py +++ b/tests/os/test_data_disk.py @@ -13,7 +13,7 @@ from supervisor.hardware.data import Device @pytest.mark.asyncio async def tests_datadisk_current(coresys: CoreSys): """Test current datadisk.""" - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) await coresys.dbus.agent.update() assert coresys.os.datadisk.disk_used == PosixPath("/dev/sda") @@ -22,7 +22,7 @@ async def tests_datadisk_current(coresys: CoreSys): @pytest.mark.asyncio async def test_datadisk_move(coresys: CoreSys): """Test datadisk moved without exists device.""" - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) await coresys.dbus.agent.update() coresys.os._available = True @@ -33,7 +33,7 @@ async def test_datadisk_move(coresys: CoreSys): @pytest.mark.asyncio async def test_datadisk_list(coresys: CoreSys): """Test docker info api.""" - await coresys.dbus.agent.connect() + await coresys.dbus.agent.connect(coresys.dbus.bus) await coresys.dbus.agent.update() coresys.hardware.update_device( diff --git a/tests/test_coresys.py b/tests/test_coresys.py index 4a4fc04c8..8e4e898c3 100644 --- a/tests/test_coresys.py +++ b/tests/test_coresys.py @@ -14,7 +14,7 @@ async def test_timezone(run_dir, coresys: CoreSys): assert coresys.timezone == "UTC" assert coresys.config.timezone is None - await coresys.dbus.timedate.connect() + await coresys.dbus.timedate.connect(coresys.dbus.bus) await coresys.dbus.timedate.update() assert coresys.timezone == "Etc/UTC" diff --git a/tests/utils/test_dbus.py b/tests/utils/test_dbus.py index 5e4a8936e..e07680fa0 100644 --- a/tests/utils/test_dbus.py +++ b/tests/utils/test_dbus.py @@ -22,8 +22,11 @@ def test_remove_dbus_signature(): async def test_dbus_prepare_args(coresys: CoreSys): """Check D-Bus dynamic argument builder.""" - dbus = DBus("org.freedesktop.systemd1", "/org/freedesktop/systemd1") - signature, args = dbus._prepare_args( + dbus = DBus( + coresys.dbus.bus, "org.freedesktop.systemd1", "/org/freedesktop/systemd1" + ) + # pylint: disable=protected-access + signature, _ = dbus._prepare_args( True, 1, 1.0, "Value", ("a{sv}", {"Key": "Value"}) ) assert signature == "bidsa{sv}"