def test_send_to_server(self, _): self.WS = WebsocketClientComms(self.p, params) self.WS.conn = MagicMock() request = Get(None, None, ["block", "attr"]) request.set_id(54) self.WS.send_to_server(request) self.WS.conn.write_message.assert_called_once_with( '{"typeid": "malcolm:core/Get:1.0", "id": 54, "endpoint": ["block", "attr"]}' )
def test_subscribe_initial(self, _, _2): self.WS = WebsocketClientComms(self.p, params) self.WS.subscribe_server_blocks("conn") self.assertEqual(self.WS.loop.add_callback.call_count, 1) request = self.WS.loop.add_callback.call_args[0][1] self.assertEqual(request.id, 0) self.assertEqual(request.typeid, "malcolm:core/Subscribe:1.0") self.assertEqual(request.endpoint, [".", "blocks", "value"]) self.assertEqual(request.delta, False)
def test_on_message_logs_exception(self, _, _1, json_mock): self.WS = WebsocketClientComms(self.p, params) self.WS.log_exception = MagicMock() exception = Exception() json_mock.loads.side_effect = exception self.WS.on_message("test") self.WS.log_exception.assert_called_once_with(exception)
def test_subscribe_initial(self, _): self.WS = WebsocketClientComms(self.p, params) self.WS.send_to_server = MagicMock() self.WS.subscribe_server_blocks() self.assertEqual(self.WS.send_to_server.call_count, 1) request = self.WS.send_to_server.call_args[0][0] self.assertEqual(request.id, 0) self.assertEqual(request.typeid, "malcolm:core/Subscribe:1.0") self.assertEqual(request.endpoint, [".", "blocks", "value"]) self.assertEqual(request.delta, False)
def test_start(self, ioloop_mock): loop_mock = MagicMock() ioloop_mock.current.return_value = loop_mock self.WS = WebsocketClientComms(self.p, params) self.WS.process.spawn = MagicMock() self.WS.start() self.assertEqual([call(self.WS.send_loop), call(self.WS.loop.start)], self.WS.process.spawn.call_args_list)
def test_wait(self, _): spawnable_mocks = [MagicMock(), MagicMock()] timeout = MagicMock() self.WS = WebsocketClientComms(self.p, params) self.WS.process.spawn = MagicMock(side_effect=spawnable_mocks) self.WS.start() self.WS.wait(timeout) spawnable_mocks[0].wait.assert_called_once_with(timeout=timeout) spawnable_mocks[1].wait.assert_called_once_with(timeout=timeout)
def test_init(self, ioloop_mock, connect_mock): self.WS = WebsocketClientComms(self.p, params) self.assertEqual(self.p, self.WS.process) self.assertEqual("ws://test:1/ws", self.WS.url) self.assertEqual(ioloop_mock.current(), self.WS.loop) connect_mock.assert_called_once_with( self.WS.url, callback=self.WS.subscribe_server_blocks, on_message_callback=self.WS.on_message) self.assertEqual(connect_mock(), self.WS.conn)
def test_stop(self, ioloop_mock, _): loop_mock = MagicMock() ioloop_mock.current.return_value = loop_mock self.WS = WebsocketClientComms(self.p, params) self.WS.start() self.WS.stop() loop_mock.add_callback.assert_called_once_with( ioloop_mock.current().stop) self.WS.process.spawn.return_value.assert_not_called()
def test_send_to_server(self, _, connect_mock, json_mock): self.WS = WebsocketClientComms(self.p, params) json_mock.reset_mock() result_mock = MagicMock() connect_mock().result.return_value = result_mock dumps_mock = MagicMock() json_mock.dumps.return_value = dumps_mock request_mock = MagicMock() self.WS.send_to_server(request_mock) json_mock.dumps.assert_called_once_with(request_mock.to_dict()) result_mock.write_message.assert_called_once_with(dumps_mock)
def test_on_message(self, _): self.WS = WebsocketClientComms(self.p, params) request = MagicMock() self.WS.requests[11] = request response = Return(11, MagicMock(), "me") message = """{ "typeid": "malcolm:core/Return:1.0", "id": 11, "value": "me" }""" self.WS.on_message(message) self.assertEquals(request.response_queue.put.call_count, 1) actual = request.response_queue.put.call_args[0][0] self.assertEquals(actual.to_dict(), response.to_dict())
def test_init(self, ioloop_mock): self.WS = WebsocketClientComms(self.p, params) self.assertEqual(self.p, self.WS.process) self.assertEqual("ws://test:1/ws", self.WS.url) self.assertEqual(ioloop_mock.current(), self.WS.loop) self.WS.loop.add_callback.assert_called_once_with( self.WS.recv_loop)
def test_send_to_server(self, _): self.WS = WebsocketClientComms(self.p, params) self.WS.conn = MagicMock() request = Get(None, None, ["block", "attr"]) request.set_id(54) self.WS.send_to_server(request) self.WS.conn.write_message.assert_called_once_with( '{"typeid": "malcolm:core/Get:1.0", "id": 54, "endpoint": ["block", "attr"]}')
def test_on_message(self, _, _1, json_mock, deserialize_mock): self.WS = WebsocketClientComms(self.p, params) message_dict = dict(name="TestMessage") json_mock.loads.return_value = message_dict response = MagicMock() response.id = 1 deserialize_mock.return_value = response request_mock = MagicMock() self.WS.requests[1] = request_mock self.WS.on_message("TestMessage") json_mock.loads.assert_called_once_with("TestMessage", object_pairs_hook=OrderedDict) deserialize_mock.assert_called_once_with(message_dict, Response) request_mock.response_queue.put.assert_called_once_with(response)
def test_stop(self, ioloop_mock): loop_mock = MagicMock() ioloop_mock.current.return_value = loop_mock self.WS = WebsocketClientComms(self.p, params) self.WS.start() loop_mock.reset_mock() self.WS.stop() loop_mock.add_callback.assert_called_once_with( ioloop_mock.current().stop) self.WS.process.spawn.return_value.assert_not_called()
def setUp(self): self.sf = SyncFactory("sync") self.process = Process("proc", self.sf) DefaultController("hello", self.process, parts=dict(hello=HelloPart(self.process, None))) DefaultController("counter", self.process, parts=dict(counter=CounterPart(self.process, None))) WebsocketServerComms(self.process, dict(port=self.socket)) self.process.start() self.process2 = Process("proc2", self.sf) WebsocketClientComms(self.process2, dict(hostname="localhost", port=self.socket)) self.process2.start()
def setUp(self): sf = SyncFactory("sync") self.process = Process("proc", sf) Hello(self.process, dict(mri="hello")) Counter(self.process, dict(mri="counter")) self.process.add_comms( WebsocketServerComms(self.process, dict(port=self.socket))) self.process.start() # If we don't wait long enough, sometimes the websocket_connect() # in process2 will hang... time.sleep(0.1) self.process2 = Process("proc2", sf) self.process2.add_comms( WebsocketClientComms(self.process2, dict(hostname="localhost", port=self.socket))) self.process2.start()
def make_process(): import sys import threading import argparse import logging from os import environ parser = argparse.ArgumentParser( description="Interactive shell for malcolm") parser.add_argument( '--client', '-c', help="Add a client to given server, like ws://localhost:8080 or pva") parser.add_argument( '--log', default="INFO", help="Lowest level of logs to see. One of: ERROR, WARNING, INFO, DEBUG " "Default is INFO") parser.add_argument( 'yaml', nargs="?", help="The YAML file containing the blocks to be loaded") args = parser.parse_args() # assuming loglevel is bound to the string value obtained from the # command line argument. Convert to upper case to allow the user to # specify --log=DEBUG or --log=debug numeric_level = getattr(logging, args.log.upper(), None) if not isinstance(numeric_level, int): raise ValueError('Invalid log level: %s' % args.log) logging.basicConfig(level=numeric_level) from malcolm.core import SyncFactory, Process from malcolm.yamlutil import make_include_creator sf = SyncFactory("Sync") if args.yaml: proc_name = os.path.basename(args.yaml).split(".")[-2] proc = Process(proc_name, sf) with open(args.yaml) as f: assembly = make_include_creator(f.read()) params = assembly.MethodMeta.prepare_input_map() assembly(proc, params) proc_name = "%s - imalcolm" % proc_name else: proc = Process("Process", sf) proc_name = "imalcolm" # set terminal title sys.stdout.write("\x1b]0;%s\x07" % proc_name) if args.client: if args.client.startswith("ws://"): from malcolm.comms.websocket import WebsocketClientComms hostname, port = args.client[5:].split(":") comms = WebsocketClientComms( proc, dict(hostname=hostname, port=int(port))) proc.add_comms(comms) else: raise ValueError("Don't know how to create client to %s" % args.client) def gui(block): global opener opener.open_gui(block, proc) try: environ['DISPLAY'] # If this environment variable doesn't exist then there is probably no # X server for us to talk to. except KeyError: pass else: from PyQt4.Qt import QApplication # Start qt def start_qt(): global app app = QApplication(sys.argv) app.setQuitOnLastWindowClosed(False) from malcolm.gui.guiopener import GuiOpener global opener opener = GuiOpener() app.exec_() qt_thread = threading.Thread(target=start_qt) qt_thread.start() return proc, gui
def test_on_message_logs_exception(self, _): self.WS = WebsocketClientComms(self.p, params) self.WS.log_exception = MagicMock() self.WS.on_message("test") self.WS.log_exception.assert_called_once_with( 'on_message(%r) failed', "test")
def test_on_message_logs_exception(self, _): self.WS = WebsocketClientComms(self.p, params) self.WS.log_exception = MagicMock() self.WS.on_message("test") self.WS.log_exception.assert_called_once_with('on_message(%r) failed', "test")
class TestWSClientComms(unittest.TestCase): def setUp(self): self.p = MagicMock() @patch('malcolm.comms.websocket.websocketclientcomms.websocket_connect') @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_init(self, ioloop_mock, connect_mock): self.WS = WebsocketClientComms(self.p, params) self.assertEqual(self.p, self.WS.process) self.assertEqual("ws://*****:*****@patch('malcolm.comms.websocket.websocketclientcomms.websocket_connect') @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_subscribe_initial(self, _, _2): self.WS = WebsocketClientComms(self.p, params) self.WS.subscribe_server_blocks("conn") self.assertEqual(self.WS.loop.add_callback.call_count, 1) request = self.WS.loop.add_callback.call_args[0][1] self.assertEqual(request.id, 0) self.assertEqual(request.typeid, "malcolm:core/Subscribe:1.0") self.assertEqual(request.endpoint, [".", "blocks", "value"]) self.assertEqual(request.delta, False) @patch('malcolm.comms.websocket.websocketclientcomms.deserialize_object') @patch('malcolm.comms.websocket.websocketclientcomms.json') @patch('malcolm.comms.websocket.websocketclientcomms.websocket_connect') @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_on_message(self, _, _1, json_mock, deserialize_mock): self.WS = WebsocketClientComms(self.p, params) message_dict = dict(name="TestMessage") json_mock.loads.return_value = message_dict response = MagicMock() response.id = 1 deserialize_mock.return_value = response request_mock = MagicMock() self.WS.requests[1] = request_mock self.WS.on_message("TestMessage") json_mock.loads.assert_called_once_with("TestMessage", object_pairs_hook=OrderedDict) deserialize_mock.assert_called_once_with(message_dict, Response) request_mock.response_queue.put.assert_called_once_with(response) @patch('malcolm.comms.websocket.websocketclientcomms.json') @patch('malcolm.comms.websocket.websocketclientcomms.websocket_connect') @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_on_message_logs_exception(self, _, _1, json_mock): self.WS = WebsocketClientComms(self.p, params) self.WS.log_exception = MagicMock() exception = Exception() json_mock.loads.side_effect = exception self.WS.on_message("test") self.WS.log_exception.assert_called_once_with(exception) @patch('malcolm.comms.websocket.websocketclientcomms.json') @patch('malcolm.comms.websocket.websocketclientcomms.websocket_connect') @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_send_to_server(self, _, connect_mock, json_mock): self.WS = WebsocketClientComms(self.p, params) json_mock.reset_mock() result_mock = MagicMock() connect_mock().result.return_value = result_mock dumps_mock = MagicMock() json_mock.dumps.return_value = dumps_mock request_mock = MagicMock() self.WS.send_to_server(request_mock) json_mock.dumps.assert_called_once_with(request_mock.to_dict()) result_mock.write_message.assert_called_once_with(dumps_mock) @patch('malcolm.comms.websocket.websocketclientcomms.websocket_connect') @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_start(self, ioloop_mock, _): loop_mock = MagicMock() ioloop_mock.current.return_value = loop_mock self.WS = WebsocketClientComms(self.p, params) self.WS.process.spawn = MagicMock() self.WS.start() self.assertEqual([call(self.WS.send_loop), call(self.WS.loop.start)], self.WS.process.spawn.call_args_list) @patch('malcolm.comms.websocket.websocketclientcomms.websocket_connect') @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_stop(self, ioloop_mock, _): loop_mock = MagicMock() ioloop_mock.current.return_value = loop_mock self.WS = WebsocketClientComms(self.p, params) self.WS.start() self.WS.stop() loop_mock.add_callback.assert_called_once_with( ioloop_mock.current().stop) self.WS.process.spawn.return_value.assert_not_called() @patch('malcolm.comms.websocket.websocketclientcomms.websocket_connect') @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_wait(self, _, _2): spawnable_mocks = [MagicMock(), MagicMock()] timeout = MagicMock() self.WS = WebsocketClientComms(self.p, params) self.WS.process.spawn = MagicMock(side_effect=spawnable_mocks) self.WS.start() self.WS.wait(timeout) spawnable_mocks[0].wait.assert_called_once_with(timeout=timeout) spawnable_mocks[1].wait.assert_called_once_with(timeout=timeout)
def test_init(self, ioloop_mock): self.WS = WebsocketClientComms(self.p, params) self.assertEqual(self.p, self.WS.process) self.assertEqual("ws://test:1/ws", self.WS.url) self.assertEqual(ioloop_mock.current(), self.WS.loop) self.WS.loop.add_callback.assert_called_once_with(self.WS.recv_loop)
class TestWSClientComms(unittest.TestCase): def setUp(self): self.p = MagicMock() @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_init(self, ioloop_mock): self.WS = WebsocketClientComms(self.p, params) self.assertEqual(self.p, self.WS.process) self.assertEqual("ws://*****:*****@patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_subscribe_initial(self, _): self.WS = WebsocketClientComms(self.p, params) self.WS.send_to_server = MagicMock() self.WS.subscribe_server_blocks() self.assertEqual(self.WS.send_to_server.call_count, 1) request = self.WS.send_to_server.call_args[0][0] self.assertEqual(request.id, 0) self.assertEqual(request.typeid, "malcolm:core/Subscribe:1.0") self.assertEqual(request.endpoint, [".", "blocks", "value"]) self.assertEqual(request.delta, False) @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_on_message(self, _): self.WS = WebsocketClientComms(self.p, params) request = MagicMock() self.WS.requests[11] = request response = Return(11, MagicMock(), "me") message = """{ "typeid": "malcolm:core/Return:1.0", "id": 11, "value": "me" }""" self.WS.on_message(message) self.assertEquals(request.response_queue.put.call_count, 1) actual = request.response_queue.put.call_args[0][0] self.assertEquals(actual.to_dict(), response.to_dict()) @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_on_message_logs_exception(self, _): self.WS = WebsocketClientComms(self.p, params) self.WS.log_exception = MagicMock() self.WS.on_message("test") self.WS.log_exception.assert_called_once_with('on_message(%r) failed', "test") @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_send_to_server(self, _): self.WS = WebsocketClientComms(self.p, params) self.WS.conn = MagicMock() request = Get(None, None, ["block", "attr"]) request.set_id(54) self.WS.send_to_server(request) self.WS.conn.write_message.assert_called_once_with( '{"typeid": "malcolm:core/Get:1.0", "id": 54, "endpoint": ["block", "attr"]}' ) @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_start(self, ioloop_mock): loop_mock = MagicMock() ioloop_mock.current.return_value = loop_mock self.WS = WebsocketClientComms(self.p, params) self.WS.process.spawn = MagicMock() self.WS.start() self.assertEqual([call(self.WS.send_loop), call(self.WS.loop.start)], self.WS.process.spawn.call_args_list) @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_stop(self, ioloop_mock): loop_mock = MagicMock() ioloop_mock.current.return_value = loop_mock self.WS = WebsocketClientComms(self.p, params) self.WS.start() loop_mock.reset_mock() self.WS.stop() loop_mock.add_callback.assert_called_once_with( ioloop_mock.current().stop) self.WS.process.spawn.return_value.assert_not_called() @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_wait(self, _): spawnable_mocks = [MagicMock(), MagicMock()] timeout = MagicMock() self.WS = WebsocketClientComms(self.p, params) self.WS.process.spawn = MagicMock(side_effect=spawnable_mocks) self.WS.start() self.WS.wait(timeout) spawnable_mocks[0].wait.assert_called_once_with(timeout=timeout) spawnable_mocks[1].wait.assert_called_once_with(timeout=timeout)
class TestWSClientComms(unittest.TestCase): def setUp(self): self.p = MagicMock() @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_init(self, ioloop_mock): self.WS = WebsocketClientComms(self.p, params) self.assertEqual(self.p, self.WS.process) self.assertEqual("ws://*****:*****@patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_subscribe_initial(self, _): self.WS = WebsocketClientComms(self.p, params) self.WS.send_to_server = MagicMock() self.WS.subscribe_server_blocks() self.assertEqual(self.WS.send_to_server.call_count, 1) request = self.WS.send_to_server.call_args[0][0] self.assertEqual(request.id, 0) self.assertEqual(request.typeid, "malcolm:core/Subscribe:1.0") self.assertEqual(request.endpoint, [".", "blocks", "value"]) self.assertEqual(request.delta, False) @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_on_message(self, _): self.WS = WebsocketClientComms(self.p, params) request = MagicMock() self.WS.requests[11] = request response = Return(11, MagicMock(), "me") message = """{ "typeid": "malcolm:core/Return:1.0", "id": 11, "value": "me" }""" self.WS.on_message(message) self.assertEquals(request.response_queue.put.call_count, 1) actual = request.response_queue.put.call_args[0][0] self.assertEquals(actual.to_dict(), response.to_dict()) @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_on_message_logs_exception(self, _): self.WS = WebsocketClientComms(self.p, params) self.WS.log_exception = MagicMock() self.WS.on_message("test") self.WS.log_exception.assert_called_once_with( 'on_message(%r) failed', "test") @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_send_to_server(self, _): self.WS = WebsocketClientComms(self.p, params) self.WS.conn = MagicMock() request = Get(None, None, ["block", "attr"]) request.set_id(54) self.WS.send_to_server(request) self.WS.conn.write_message.assert_called_once_with( '{"typeid": "malcolm:core/Get:1.0", "id": 54, "endpoint": ["block", "attr"]}') @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_start(self, ioloop_mock): loop_mock = MagicMock() ioloop_mock.current.return_value = loop_mock self.WS = WebsocketClientComms(self.p, params) self.WS.process.spawn = MagicMock() self.WS.start() self.assertEqual([call(self.WS.send_loop), call(self.WS.loop.start)], self.WS.process.spawn.call_args_list) @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_stop(self, ioloop_mock): loop_mock = MagicMock() ioloop_mock.current.return_value = loop_mock self.WS = WebsocketClientComms(self.p, params) self.WS.start() loop_mock.reset_mock() self.WS.stop() loop_mock.add_callback.assert_called_once_with( ioloop_mock.current().stop) self.WS.process.spawn.return_value.assert_not_called() @patch('malcolm.comms.websocket.websocketclientcomms.IOLoop') def test_wait(self, _): spawnable_mocks = [MagicMock(), MagicMock()] timeout = MagicMock() self.WS = WebsocketClientComms(self.p, params) self.WS.process.spawn = MagicMock(side_effect=spawnable_mocks) self.WS.start() self.WS.wait(timeout) spawnable_mocks[0].wait.assert_called_once_with(timeout=timeout) spawnable_mocks[1].wait.assert_called_once_with(timeout=timeout)
def make_process(): import argparse import logging import cothread cothread.iqt() cothread.input_hook._qapp.setQuitOnLastWindowClosed(False) parser = argparse.ArgumentParser( description="Interactive shell for malcolm") parser.add_argument( '--client', '-c', help="Add a client to given server, like ws://localhost:8080 or pva") parser.add_argument( '--log', default="INFO", help="Lowest level of logs to see. One of: ERROR, WARNING, INFO, DEBUG " "Default is INFO") parser.add_argument( 'yaml', nargs="?", help="The YAML file containing the assemblies to be loaded") args = parser.parse_args() # assuming loglevel is bound to the string value obtained from the # command line argument. Convert to upper case to allow the user to # specify --log=DEBUG or --log=debug numeric_level = getattr(logging, args.log.upper(), None) if not isinstance(numeric_level, int): raise ValueError('Invalid log level: %s' % args.log) logging.basicConfig(level=numeric_level) from malcolm.core import SyncFactory, Process from malcolm.assemblyutil import make_assembly from malcolm.gui.blockgui import BlockGui proc = Process("Process", SyncFactory("Sync")) guis = {} if args.yaml: with open(args.yaml) as f: assembly = make_assembly(f.read()) assembly(proc, {}) def gui(block): if block in guis: guis[block].show() else: guis[block] = BlockGui(proc, block) return guis[block] if args.client: if args.client.startswith("ws://"): from malcolm.comms.websocket import WebsocketClientComms hostname, port = args.client[5:].split(":") WebsocketClientComms(proc, dict(hostname=hostname, port=int(port))) else: raise ValueError("Don't know how to create client to %s" % args.client) return proc, gui