def test_subscribe_no_data_then_set_data(self): # subscribe request = Subscribe(path=["b", "attr", "value"], delta=False) request.set_callback(Mock()) self.handle_subscribe(request) assert (self.o._tree.children["attr"].children["value"].update_requests ) == ([request]) self.assert_called_with(request.callback, Update(value=None)) request.callback.reset_mock() # set data and check response self.block["attr"] = Dummy() with self.o.changes_squashed: self.block.attr["value"] = 32 self.o.add_squashed_change(["b", "attr", "value"], 32) assert self.block.attr.value == 32 self.assert_called_with(request.callback, Update(value=32)) request.callback.reset_mock() # unsubscribe unsub = Unsubscribe() unsub.set_callback(request.callback) self.handle_unsubscribe(unsub) self.assert_called_with(request.callback, Return(value=None)) request.callback.reset_mock() # notify and check no longer responding with self.o.changes_squashed: self.block.attr["value"] = 33 self.o.add_squashed_change(["b", "attr", "value"], 33) assert self.block.attr.value == 33 request.callback.assert_not_called()
def test_unsubscribe(self): # Test that we remove the relevant subscription only and that # updates are no longer sent block = MagicMock(to_dict=MagicMock(return_value={ "attr": "0", "inner": { "attr2": "other" } })) p = Process("proc", MagicMock()) sub_1 = Subscribe(MagicMock(), MagicMock(), ["block"], False) sub_2 = Subscribe(MagicMock(), MagicMock(), ["block"], False) sub_1.set_id(1234) sub_2.set_id(4321) change_1 = BlockChanges([[["block", "attr"], "1"]]) change_2 = BlockChanges([[["block", "attr"], "2"]]) unsub_1 = Unsubscribe(MagicMock(), MagicMock()) unsub_1.set_id(1234) p.q.get = MagicMock(side_effect=[ sub_1, sub_2, change_1, unsub_1, change_2, PROCESS_STOP ]) p._handle_block_add(BlockAdd(block, "block")) p.recv_loop() self.assertEqual([sub_2], p._subscriptions) self.assertEquals(1, len(unsub_1.response_queue.put.call_args_list)) response = unsub_1.response_queue.put.call_args_list[0][0][0] self.assertIsNone(response.value) self.assertIs(unsub_1.context, response.context) sub_1_responses = sub_1.response_queue.put.call_args_list sub_2_responses = sub_2.response_queue.put.call_args_list self.assertEquals(2, len(sub_1_responses)) self.assertEquals(3, len(sub_2_responses))
def setUp(self): self.callback = MagicMock() self.subscribe = Subscribe(32, ["."]) self.subscribe.set_callback(self.callback) self.subscribes = {self.subscribe.generate_key(): self.subscribe} self.o = Unsubscribe(32) self.o.set_callback(self.callback)
def notify_closed_connection(self, response): """Let the process know not to send any more updates or deltas""" self.log_warning("Response %s cannot be sent as connection closed", response) if isinstance(response, (Delta, Update)): request = Unsubscribe(response.context, self.q) request.set_id(response.id) self.send_to_process(request)
def notify_closed_connection(self, response): """Let the process know not to send any more updates or deltas""" self.log_warning( "Response %s cannot be sent as connection closed", response) if isinstance(response, (Delta, Update)): request = Unsubscribe(response.context, self.q) request.set_id(response.id) self.send_to_process(request)
def unsubscribe(self, id_): """Terminates the subscription to an attribute Args: id_ (Int): the identifier of the subscription to halt""" self._subscriptions.pop(id_) request = Unsubscribe(None, self.q) request.set_id(id_) self.process.q.put(request)
def test_unsubscribe_error(self): p = Process("proc", MagicMock()) unsub = Unsubscribe(MagicMock(), MagicMock()) unsub.set_id(1234) unsub.response_queue.qsize.return_value = 0 p.q.get = MagicMock(side_effect=[unsub, PROCESS_STOP]) p.recv_loop() responses = unsub.response_queue.put.call_args_list self.assertEquals(1, len(responses)) response = responses[0][0][0] self.assertEquals(Error, type(response))
def test_unsubscribe_error(self): p = Process("proc", MagicMock()) unsub = Unsubscribe(MagicMock(), MagicMock()) unsub.set_id(1234) p.q.get = MagicMock(side_effect=[unsub, PROCESS_STOP]) p.recv_loop() responses = unsub.response_queue.put.call_args_list self.assertEquals(1, len(responses)) response = responses[0][0][0] self.assertEquals(Error, type(response)) self.assertEquals("No subscription found for id 1234", response.message)
class TestUnsubscribe(unittest.TestCase): def setUp(self): self.callback = MagicMock() self.subscribe = Subscribe(32, callback=self.callback) self.subscribes = {self.subscribe.generate_key(): self.subscribe} self.o = Unsubscribe(32, self.callback) def test_init(self): assert self.o.typeid == "malcolm:core/Unsubscribe:1.0" assert self.o.id == 32 def test_keys_same(self): assert self.subscribes[self.o.generate_key()] == self.subscribe def test_doc(self): assert get_doc_json("unsubscribe") == self.o.to_dict()
def test_when_matches(self): self.o._q.put(Update(1, "value1")) self.o._q.put(Return(1)) self.o.when_matches(["block", "attr", "value"], "value1", timeout=0.01) assert self.controller.handle_request.call_args_list == [ call(Subscribe(1, ["block", "attr", "value"])), call(Unsubscribe(1)) ]
def test_when_not_matches(self): self.o._q.put(Update(1, "value2")) with self.assertRaises(BadValueError) as cm: self.o.when_matches(["block", "attr", "value"], "value1", ["value2"], timeout=0.01) assert str(cm.exception) == "Waiting for 'value1', got 'value2'" self.assert_handle_request_called_with( Subscribe(1, ["block", "attr", "value"]), Unsubscribe(1))
def test_when_matches_func(self): self.o._q.put(Update(1, "value1")) self.o._q.put(Return(1)) def f(value): return value.startswith("v") self.o.when_matches(["block", "attr", "value"], f, timeout=0.01) self.assert_handle_request_called_with( Subscribe(1, ["block", "attr", "value"]), Unsubscribe(1))
def test_when_not_matches(self): self.o._q.put(Update(1, "value2")) with self.assertRaises(BadValueError): self.o.when_matches(["block", "attr", "value"], "value1", ["value2"], timeout=0.01) assert self.controller.handle_request.call_args_list == [ call(Subscribe(1, ["block", "attr", "value"])), call(Unsubscribe(1)) ]
def test_unsubscribe(self): # Test that we remove the relevant subscription only and that # updates are no longer sent block = MagicMock(to_dict=MagicMock(return_value={ "attr": "0", "inner": { "attr2": "other" } })) p = Process("proc", MagicMock()) sub_1 = Subscribe(MagicMock(), MagicMock(), ["block"], False) sub_1.response_queue.qsize.return_value = 0 sub_2 = Subscribe(MagicMock(), MagicMock(), ["block"], False) sub_2.response_queue.qsize.return_value = 0 sub_1.set_id(1234) sub_2.set_id(1234) change_1 = BlockChanges([[["block", "attr"], "1"]]) change_2 = BlockChanges([[["block", "attr"], "2"]]) unsub_1 = Unsubscribe(sub_1.context, sub_1.response_queue) unsub_1.set_id(sub_1.id) p.q.get = MagicMock(side_effect=[ sub_1, sub_2, change_1, unsub_1, change_2, PROCESS_STOP ]) p._handle_block_add(BlockAdd(block, "block", None)) p.recv_loop() self.assertEqual([sub_2], list(p._subscriptions.values())) sub_1_responses = sub_1.response_queue.put.call_args_list sub_2_responses = sub_2.response_queue.put.call_args_list self.assertEquals(3, len(sub_1_responses)) self.assertEquals(sub_1_responses[0][0][0].value["attr"], "0") self.assertEquals(sub_1_responses[1][0][0].value["attr"], "1") self.assertIsInstance(sub_1_responses[2][0][0], Return) self.assertEquals(3, len(sub_2_responses)) self.assertEquals(sub_2_responses[0][0][0].value["attr"], "0") self.assertEquals(sub_2_responses[1][0][0].value["attr"], "1") self.assertEquals(sub_2_responses[2][0][0].value["attr"], "2")
def test_unsubscribe(self): # Test that we remove the relevant subscription only and that # updates are no longer sent block = MagicMock( to_dict=MagicMock( return_value={"attr": "0", "inner": {"attr2": "other"}})) p = Process("proc", MagicMock()) sub_1 = Subscribe( MagicMock(), MagicMock(), ["block"], False) sub_1.response_queue.qsize.return_value = 0 sub_2 = Subscribe( MagicMock(), MagicMock(), ["block"], False) sub_2.response_queue.qsize.return_value = 0 sub_1.set_id(1234) sub_2.set_id(1234) change_1 = BlockChanges([[["block", "attr"], "1"]]) change_2 = BlockChanges([[["block", "attr"], "2"]]) unsub_1 = Unsubscribe(sub_1.context, sub_1.response_queue) unsub_1.set_id(sub_1.id) p.q.get = MagicMock(side_effect=[sub_1, sub_2, change_1, unsub_1, change_2, PROCESS_STOP]) p._handle_block_add(BlockAdd(block, "block", None)) p.recv_loop() self.assertEqual([sub_2], list(p._subscriptions.values())) sub_1_responses = sub_1.response_queue.put.call_args_list sub_2_responses = sub_2.response_queue.put.call_args_list self.assertEquals(3, len(sub_1_responses)) self.assertEquals(sub_1_responses[0][0][0].value["attr"], "0") self.assertEquals(sub_1_responses[1][0][0].value["attr"], "1") self.assertIsInstance(sub_1_responses[2][0][0], Return) self.assertEquals(3, len(sub_2_responses)) self.assertEquals(sub_2_responses[0][0][0].value["attr"], "0") self.assertEquals(sub_2_responses[1][0][0].value["attr"], "1") self.assertEquals(sub_2_responses[2][0][0].value["attr"], "2")
def test_handle_request(self): q = Queue() request = Get(id=41, path=["mri", "myAttribute"], callback=q.put) self.o.handle_request(request) response = q.get(timeout=.1) self.assertIsInstance(response, Return) assert response.id == 41 assert response.value["value"] == "hello_block" # It's part2 that will get the attribute as it was defined second self.part2.myAttribute.meta.writeable = False request = Put(id=42, path=["mri", "myAttribute"], value='hello_block', callback=q.put) self.o.handle_request(request) response = q.get(timeout=.1) self.assertIsInstance(response, Error) # not writeable assert response.id == 42 self.part2.myAttribute.meta.writeable = True self.o.handle_request(request) response = q.get(timeout=.1) self.assertIsInstance(response, Return) assert response.id == 42 assert response.value == "hello_block" request = Post(id=43, path=["mri", "my_method"], callback=q.put) self.o.handle_request(request) response = q.get(timeout=.1) self.assertIsInstance(response, Return) assert response.id == 43 assert response.value['ret'] == "world" # cover the controller._handle_post path for parameters request = Post(id=43, path=["mri", "my_method"], parameters={'dummy': 1}, callback=q.put) self.o.handle_request(request) response = q.get(timeout=.1) self.assertIsInstance(response, Return) assert response.id == 43 assert response.value['ret'] == "world" request = Subscribe(id=44, path=["mri", "myAttribute"], delta=False, callback=q.put) self.o.handle_request(request) response = q.get(timeout=.1) self.assertIsInstance(response, Update) assert response.id == 44 assert response.value["typeid"] == "epics:nt/NTScalar:1.0" assert response.value["value"] == "hello_block" request = Unsubscribe(id=44, callback=q.put) self.o.handle_request(request) response = q.get(timeout=.1) self.assertIsInstance(response, Return) assert response.id == 44
def setUp(self): self.callback = MagicMock() self.subscribe = Subscribe(32, callback=self.callback) self.subscribes = {self.subscribe.generate_key(): self.subscribe} self.o = Unsubscribe(32, self.callback)
def test_when_matches(self): self.o._q.put(Update(1, "value1")) self.o._q.put(Return(1)) self.o.when_matches(["block", "attr", "value"], "value1", timeout=0.01) self.assert_handle_request_called_with( Subscribe(1, ["block", "attr", "value"]), Unsubscribe(1))
def setUp(self): self.context = MagicMock() self.response_queue = MagicMock() self.unsubscribe = Unsubscribe(self.context, self.response_queue)