Skip to content

Commit

Permalink
Switch to system bus instead of session bus (#69)
Browse files Browse the repository at this point in the history
  • Loading branch information
r0x0d authored Dec 17, 2024
1 parent b9c6927 commit c393d4a
Show file tree
Hide file tree
Showing 6 changed files with 34 additions and 31 deletions.
1 change: 1 addition & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,7 @@ link-systemd-units: ## Link the systemd units to /etc/systemd/user
@echo "Linking the systemd units from $(CLAD_SYSTEMD_DEVEL_PATH) to $(SYSTEMD_USER_UNITS)/clad.service"
@sed -e 's/{{ EXEC_START }}/$(CLAD_VENV_BIN)/' \
-e 's/{{ CONFIG_FILE_PATH }}/$(XDG_CONFIG_DIRS)/' \
-e 's/{{ DBUS_SESSION_ADDRESS }}/$(subst /,\/,$(DBUS_SESSION_BUS_ADDRESS))/' \
$(CLAD_SYSTEMD_DEVEL_PATH) > $(CLAD_SYSTEMD_USER_PATH)
@ln -s $(CLAD_SYSTEMD_USER_PATH) $(SYSTEMD_USER_UNITS)/clad.service

Expand Down
6 changes: 3 additions & 3 deletions command_line_assistant/dbus/constants.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

ERROR_MAPPER = ErrorMapper()

SESSION_BUS = SystemMessageBus(error_mapper=ERROR_MAPPER)
SYSTEM_BUS = SystemMessageBus(error_mapper=ERROR_MAPPER)

SERVICE_NAMESPACE = ("com", "redhat", "lightspeed")

Expand All @@ -13,9 +13,9 @@

# Define the service identifier for a query
QUERY_IDENTIFIER = DBusServiceIdentifier(
namespace=QUERY_NAMESAPCE, message_bus=SESSION_BUS
namespace=QUERY_NAMESAPCE, message_bus=SYSTEM_BUS
)
# Define the service identifier for a history
HISTORY_IDENTIFIER = DBusServiceIdentifier(
namespace=HISTORY_NAMESPACE, message_bus=SESSION_BUS
namespace=HISTORY_NAMESPACE, message_bus=SYSTEM_BUS
)
14 changes: 6 additions & 8 deletions command_line_assistant/dbus/server.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
from command_line_assistant.dbus.constants import (
HISTORY_IDENTIFIER,
QUERY_IDENTIFIER,
SESSION_BUS,
SYSTEM_BUS,
)
from command_line_assistant.dbus.context import HistoryContext, QueryContext
from command_line_assistant.dbus.interfaces import HistoryInterface, QueryInterface
Expand All @@ -19,24 +19,22 @@ def serve(config: Config):
"""Start the daemon."""
logger.info("Starting clad!")
try:
SESSION_BUS.publish_object(
SYSTEM_BUS.publish_object(
QUERY_IDENTIFIER.object_path, QueryInterface(QueryContext(config))
)
SESSION_BUS.publish_object(
SYSTEM_BUS.publish_object(
HISTORY_IDENTIFIER.object_path, HistoryInterface(HistoryContext(config))
)

# The flag DBUS_NAME_FLAG_REPLACE_EXISTING is needed during development
# so ew can replace the existing bus.
# TODO(r0x0d): See what to do with it later.
SESSION_BUS.register_service(
QUERY_IDENTIFIER.service_name, flags=DBUS_NAME_FLAG_REPLACE_EXISTING
)
SESSION_BUS.register_service(
SYSTEM_BUS.register_service(QUERY_IDENTIFIER.service_name)
SYSTEM_BUS.register_service(
HISTORY_IDENTIFIER.service_name, flags=DBUS_NAME_FLAG_REPLACE_EXISTING
)
loop = EventLoop()
loop.run()
finally:
# Unregister the DBus service and objects.
SESSION_BUS.disconnect()
SYSTEM_BUS.disconnect()
2 changes: 2 additions & 0 deletions data/development/systemd/clad-devel.service
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@ PrivateTmp=yes
RemainAfterExit=no
ExecStart={{ EXEC_START }}
Environment="XDG_CONFIG_DIRS={{ CONFIG_FILE_PATH }}"
# This is a workaround for intended only for local development.
Environment="DBUS_SYSTEM_BUS_ADDRESS={{ DBUS_SESSION_ADDRESS }}"

[Install]
WantedBy=multi-user.target
Expand Down
12 changes: 9 additions & 3 deletions data/release/com.redhat.lightspeed.conf
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,18 @@
<busconfig>
<!-- Allow the command line assistant service to own the name -->
<policy context="default">
<allow own="com.redhat.lightspeed"/>
<allow own="com.redhat.lightspeed.query"/>
<allow own="com.redhat.lightspeed.history"/>
</policy>

<!-- Allow any user to invoke methods -->
<policy context="default">
<allow send_destination="com.redhat.lightspeed"/>
<allow receive_sender="com.redhat.lightspeed"/>
<allow send_destination="com.redhat.lightspeed.query"/>
<allow receive_sender="com.redhat.lightspeed.query"/>
</policy>

<policy context="default">
<allow send_destination="com.redhat.lightspeed.history"/>
<allow receive_sender="com.redhat.lightspeed.history"/>
</policy>
</busconfig>
30 changes: 13 additions & 17 deletions tests/dbus/test_server.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,9 @@

def test_serve(monkeypatch):
event_loop_mock = mock.Mock()
session_bus_mock = mock.Mock()
system_bus_mock = mock.Mock()
monkeypatch.setattr(server, "EventLoop", event_loop_mock)
monkeypatch.setattr(server, "SESSION_BUS", session_bus_mock)
monkeypatch.setattr(server, "SYSTEM_BUS", system_bus_mock)
config = Config()

server.serve(config)
Expand All @@ -20,51 +20,47 @@ def test_serve(monkeypatch):

def test_serve_registers_services(monkeypatch):
event_loop_mock = mock.Mock()
session_bus_mock = mock.Mock()
system_bus_mock = mock.Mock()
monkeypatch.setattr(server, "EventLoop", event_loop_mock)
monkeypatch.setattr(server, "SESSION_BUS", session_bus_mock)
monkeypatch.setattr(server, "SYSTEM_BUS", system_bus_mock)
config = Config()

server.serve(config)

assert session_bus_mock.publish_object.call_count == 2
assert session_bus_mock.register_service.call_count == 2
assert system_bus_mock.publish_object.call_count == 2
assert system_bus_mock.register_service.call_count == 2
assert (
session_bus_mock.register_service.call_args_list[0][1]["flags"]
== DBUS_NAME_FLAG_REPLACE_EXISTING
)
assert (
session_bus_mock.register_service.call_args_list[1][1]["flags"]
system_bus_mock.register_service.call_args_list[1][1]["flags"]
== DBUS_NAME_FLAG_REPLACE_EXISTING
)


def test_serve_cleanup_on_exception(monkeypatch):
event_loop_mock = mock.Mock()
event_loop_mock.return_value.run.side_effect = Exception("Test error")
session_bus_mock = mock.Mock()
system_bus_mock = mock.Mock()
monkeypatch.setattr(server, "EventLoop", event_loop_mock)
monkeypatch.setattr(server, "SESSION_BUS", session_bus_mock)
monkeypatch.setattr(server, "SYSTEM_BUS", system_bus_mock)
config = Config()

try:
server.serve(config)
except Exception:
pass

session_bus_mock.disconnect.assert_called_once()
system_bus_mock.disconnect.assert_called_once()


def test_serve_creates_interfaces(monkeypatch):
event_loop_mock = mock.Mock()
session_bus_mock = mock.Mock()
system_bus_mock = mock.Mock()
monkeypatch.setattr(server, "EventLoop", event_loop_mock)
monkeypatch.setattr(server, "SESSION_BUS", session_bus_mock)
monkeypatch.setattr(server, "SYSTEM_BUS", system_bus_mock)
config = Config()

server.serve(config)

publish_calls = session_bus_mock.publish_object.call_args_list
publish_calls = system_bus_mock.publish_object.call_args_list
assert len(publish_calls) == 2
assert isinstance(publish_calls[0][0][1], server.QueryInterface)
assert isinstance(publish_calls[1][0][1], server.HistoryInterface)

0 comments on commit c393d4a

Please sign in to comment.