From d5ecc78e261360f7a8202931990b567498ad766c Mon Sep 17 00:00:00 2001 From: Sindre Hansen Date: Tue, 3 Sep 2024 20:32:16 +0200 Subject: [PATCH] Add observer mode --- blueye/sdk/connection.py | 6 +++++- blueye/sdk/drone.py | 18 ++++++++++++++---- tests/conftest.py | 11 +++++++++++ tests/test_sdk.py | 12 ++++++++++++ 4 files changed, 42 insertions(+), 5 deletions(-) diff --git a/blueye/sdk/connection.py b/blueye/sdk/connection.py index 061271c0..cc330533 100644 --- a/blueye/sdk/connection.py +++ b/blueye/sdk/connection.py @@ -345,9 +345,13 @@ def sync_time(self, time: int, timeout: float = 0.05): return self._send_request_get_response(request, blueye.protocol.SyncTimeRep, timeout) def connect_client( - self, client_info: blueye.protocol.ClientInfo = None, timeout: float = 0.05 + self, + client_info: blueye.protocol.ClientInfo = None, + is_observer: bool = False, + timeout: float = 0.05, ) -> blueye.protocol.ConnectClientRep: client = client_info or self._get_client_info() + client.is_observer = is_observer request = blueye.protocol.ConnectClientReq(client_info=client) return self._send_request_get_response(request, blueye.protocol.ConnectClientRep, timeout) diff --git a/blueye/sdk/drone.py b/blueye/sdk/drone.py index e3b5f5e8..410a5f03 100755 --- a/blueye/sdk/drone.py +++ b/blueye/sdk/drone.py @@ -182,6 +182,7 @@ def __init__( auto_connect=True, timeout=10, disconnect_other_clients=False, + connect_as_observer=False, ): self._ip = ip self.camera = Camera(self, is_guestport_camera=False) @@ -204,7 +205,11 @@ def __init__( Guestport telemetry message has been recieved yet.""" if auto_connect is True: - self.connect(timeout=timeout, disconnect_other_clients=disconnect_other_clients) + self.connect( + timeout=timeout, + disconnect_other_clients=disconnect_other_clients, + connect_as_observer=connect_as_observer, + ) def _verify_required_blunux_version(self, requirement: str): """Verify that Blunux version is higher than requirement @@ -270,6 +275,7 @@ def connect( client_info: blueye.protocol.ClientInfo = None, timeout: float = 4, disconnect_other_clients: bool = False, + connect_as_observer: bool = False, ): """Establish a connection to the drone @@ -286,7 +292,9 @@ def connect( - *timeout*: Seconds to wait for connection. The first connection on boot can be a little slower than the following ones - *disconnect_other_clients*: If True, disconnect clients until drone reports that we are in - control + control. If the connect_as_observer field is set to true, this + argument is ignored + - *connect_as_observer*: If True, the client will not be promoted to in control of the drone ** Raises ** - *ConnectionError*: If the connection attempt fails @@ -308,7 +316,9 @@ def connect( try: self.ping() - connect_resp = self._req_rep_client.connect_client(client_info=client_info) + connect_resp = self._req_rep_client.connect_client( + client_info=client_info, is_observer=connect_as_observer + ) except blueye.protocol.exceptions.ResponseTimeout as e: raise ConnectionError("Could not establish connection with drone") from e logger.info(f"Connection successful, client id: {connect_resp.client_id}") @@ -317,7 +327,7 @@ def connect( self.client_id = connect_resp.client_id self.in_control = connect_resp.client_id == connect_resp.client_id_in_control self.connected = True - if disconnect_other_clients and not self.in_control: + if disconnect_other_clients and not self.in_control and not connect_as_observer: self.take_control() self._drone_info_cb_id = self.telemetry.add_msg_callback( [blueye.protocol.DroneInfoTel], diff --git a/tests/conftest.py b/tests/conftest.py index 6e869627..4605f7de 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -112,3 +112,14 @@ def mocked_drone( if hasattr(request, "param"): drone.software_version_short = request.param return drone + + +@pytest.fixture +def mocked_drone_not_connected( + mocker, + mocked_requests, + mocked_ctrl_client, + mocked_watchdog_publisher, + mocked_req_rep_client, +): + return blueye.sdk.Drone(auto_connect=False) diff --git a/tests/test_sdk.py b/tests/test_sdk.py index 92efed3b..f67c98ce 100644 --- a/tests/test_sdk.py +++ b/tests/test_sdk.py @@ -311,3 +311,15 @@ def test_dive_time_returns_expected_value(mocked_drone): def test_dive_time_returns_none_on_missing_telemetry(mocked_drone): assert mocked_drone.dive_time is None + + +def test_connect_as_observer(mocked_drone_not_connected): + mocked_drone_not_connected.connect(connect_as_observer=True) + mocked_drone_not_connected._req_rep_client.connect_client.assert_called_with( + client_info=None, is_observer=True + ) + + +def test_connect_as_observer_ignores_diconnect_other_clients(mocked_drone_not_connected): + mocked_drone_not_connected.connect(disconnect_other_clients=True, connect_as_observer=True) + mocked_drone_not_connected._req_rep_client.disconnect_client.assert_not_called()