Skip to content

Commit f4d5293

Browse files
Murko: continue thaw if redis is down (#1750)
* Dont crash if MurkoResultsDevice cant connect to redis * Fix device and add test * Fix * Fixes * Add test for coverage * Tiny change * Always set motors to 0 if connection fails * Small change to test --------- Co-authored-by: Dominic Oram <[email protected]>
1 parent 9f12091 commit f4d5293

File tree

2 files changed

+57
-3
lines changed

2 files changed

+57
-3
lines changed

src/dodal/devices/i04/murko_results.py

Lines changed: 18 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@
1313
soft_signal_r_and_setter,
1414
soft_signal_rw,
1515
)
16-
from redis.asyncio import StrictRedis
16+
from redis.asyncio import ConnectionError, StrictRedis
1717

1818
from dodal.devices.i04.constants import RedisConstants
1919
from dodal.devices.oav.oav_calculations import (
@@ -103,24 +103,39 @@ def __init__(
103103
self.z_mm, self._z_mm_setter = soft_signal_r_and_setter(float)
104104
super().__init__(name=name)
105105

106+
async def _check_redis_connection(self):
107+
try:
108+
await self.redis_client.ping() # type: ignore
109+
return True
110+
except ConnectionError:
111+
LOGGER.warning(
112+
f"Failed to connect to redis: {self.redis_client}. Murko results device will not trigger"
113+
)
114+
return False
115+
106116
def _reset(self):
107117
self._last_omega = None
108118
self._results: list[MurkoResult] = []
109119

110120
@AsyncStatus.wrap
111121
async def stage(self):
112-
await self.pubsub.subscribe("murko-results")
122+
self.redis_connected = await self._check_redis_connection()
123+
if self.redis_connected:
124+
await self.pubsub.subscribe("murko-results")
113125
self._x_mm_setter(0)
114126
self._y_mm_setter(0)
115127
self._z_mm_setter(0)
116128

117129
@AsyncStatus.wrap
118130
async def unstage(self):
119131
self._reset()
120-
await self.pubsub.unsubscribe()
132+
if self.redis_connected:
133+
await self.pubsub.unsubscribe()
121134

122135
@AsyncStatus.wrap
123136
async def trigger(self):
137+
if not self.redis_connected:
138+
return
124139
sample_id = await self.sample_id.get_value()
125140
t_last_result = time.time()
126141
while True:

tests/devices/i04/test_murko_results.py

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88
import pytest
99
from ophyd_async.core import init_devices
1010
from pytest import approx
11+
from redis.asyncio import ConnectionError
1112

1213
from dodal.devices.i04.murko_results import (
1314
RESULTS_COMPLETE_MESSAGE,
@@ -25,6 +26,7 @@ async def murko_results(mock_strict_redis: MagicMock) -> MurkoResultsDevice:
2526
with init_devices(mock=True):
2627
murko_results = MurkoResultsDevice(name="murko_results")
2728
murko_results.pubsub = AsyncMock()
29+
murko_results.redis_connected = True
2830
return murko_results
2931

3032

@@ -443,6 +445,7 @@ async def test_trigger_calls_get_message_and_hget(
443445
async def test_assert_subscribes_to_queue_and_clears_results_on_stage(
444446
murko_results: MurkoResultsDevice,
445447
):
448+
murko_results._check_redis_connection = AsyncMock(return_value=True)
446449
murko_results._x_mm_setter(1)
447450
murko_results._y_mm_setter(2)
448451
murko_results._z_mm_setter(3)
@@ -807,3 +810,39 @@ async def test_trigger_stops_if_no_message_in_5_seconds_and_raises_warning(
807810
and record.levelname == "WARNING"
808811
for record in caplog.records
809812
)
813+
814+
815+
async def test_if_redis_connection_failed_then_no_error_is_raised_and_motors_set_to_0(
816+
murko_results: MurkoResultsDevice,
817+
):
818+
murko_results.redis_client.ping = AsyncMock(side_effect=ConnectionError)
819+
await murko_results.stage()
820+
await murko_results.trigger()
821+
await murko_results.unstage()
822+
assert await murko_results.x_mm.get_value() == 0
823+
assert await murko_results.y_mm.get_value() == 0
824+
assert await murko_results.z_mm.get_value() == 0
825+
826+
827+
async def test_if_redis_connection_failed_and_motors_have_values_then_motors_set_to_0(
828+
murko_results: MurkoResultsDevice,
829+
):
830+
murko_results.redis_client.ping = AsyncMock(side_effect=ConnectionError)
831+
murko_results._x_mm_setter(1)
832+
murko_results._y_mm_setter(2)
833+
murko_results._z_mm_setter(3)
834+
assert await murko_results.x_mm.get_value() == 1
835+
assert await murko_results.y_mm.get_value() == 2
836+
assert await murko_results.z_mm.get_value() == 3
837+
await murko_results.stage()
838+
assert await murko_results.x_mm.get_value() == 0
839+
assert await murko_results.y_mm.get_value() == 0
840+
assert await murko_results.z_mm.get_value() == 0
841+
842+
843+
async def test_if_redis_connects_then_pubsub_is_subscribed_to(
844+
murko_results: MurkoResultsDevice,
845+
):
846+
murko_results.redis_client.ping = AsyncMock()
847+
await murko_results.stage()
848+
murko_results.pubsub.subscribe.assert_called_once() # type: ignore

0 commit comments

Comments
 (0)