def __init__(self, channel, params, evt_callback=None): """ @param channel identifies the particular protocol instance. @param params the particular parameters for this channel. """ InstrumentProtocol.__init__(self, evt_callback) self._channel = channel # initialize values for the params: MyProtocol.next_base_value += 1000 next_value = MyProtocol.next_base_value self._values = {} for param in params: next_value += 1 self._values[param] = next_value
def setUp(self): self.mock = DotDict() self.mock.port_agent = Mock(name='port_agent_client') self.mock.callback = Mock(name='callback') def mock_set(values, startup=True): assert isinstance(values, dict) return_string = "" for key in values.keys(): return_string += "%s=%s" % (key, values[key] ) # inefficient, I know return return_string self.driver = SingleConnectionInstrumentDriver(self.mock.callback) # set some values self.driver._protocol = InstrumentProtocol(self.mock.callback) self.driver.set_resource = mock_set self.driver._protocol._param_dict.add( "foo", r'foo=(.*)', lambda match: int(match.group(1)), lambda x: str(x), direct_access=True, startup_param=True, default_value=10) self.driver._protocol._param_dict.set_default("foo") self.driver._protocol._param_dict.add( "bar", r'bar=(.*)', lambda match: int(match.group(1)), lambda x: str(x), direct_access=False, startup_param=True, default_value=15) self.driver._protocol._param_dict.set_default("bar") self.driver._protocol._param_dict.add( "baz", r'baz=(.*)', lambda match: int(match.group(1)), lambda x: str(x), direct_access=True, default_value=30) self.driver._protocol._param_dict.set_default("baz") self.driver._protocol._param_dict.add( "bat", r'bat=(.*)', lambda match: int(match.group(1)), lambda x: str(x), startup_param=False, default_value=40) self.driver._protocol._param_dict.set_default("bat") self.driver._protocol._cmd_dict.add("cmd1") self.driver._protocol._cmd_dict.add("cmd2") self.driver._protocol._driver_dict.add( DriverDictKey.VENDOR_SW_COMPATIBLE, True)
def setUp(self): """ """ self.callback_result = None self._trigger_count = 0 self._events = [] self.protocol = InstrumentProtocol(self.event_callback)
class TestUnitInstrumentProtocol(IonUnitTestCase): """ Test cases for instrument protocol class. Functions in this class provide instrument protocol unit tests and provide a tutorial on use of the protocol interface. """ def setUp(self): """ """ self.callback_result = None def protocol_callback(self, arg): callback_result = arg self.protocol = InstrumentProtocol(protocol_callback) def test_extraction(self): sample_line = "SATPAR0229,10.01,2206748544,234" result = self.protocol._extract_sample(SatlanticPARDataParticle, SAMPLE_REGEX, sample_line, publish=False) self.assertTrue(result['parsed']) self.assertTrue(result['raw']) # Test the format of the result in the individual driver tests. Here, # just tests that the result is there. def test_publish_raw(self): """ Tests to see if raw data is appropriately published back out to the InstrumentAgent via the event callback. """ # build a packet # have it published by the protocol (force state if needed) # delay? # catch it in the callback # confirm it came back # compare response to original packet self.assertTrue(False) def test_publish_parsed_data(self): """ Tests to see if parsed data is appropriately published back to the InstrumentAgent via the event callback. """ # similar to above self.assertTrue(False) def test_publish_engineering_data(self): """ Tests to see if engineering data is appropriately published back to the InstrumentAgent via the event callback. """ # similar to above self.assertTrue(False)
def setUp(self): """ """ self.callback_result = None def protocol_callback(self, arg): callback_result = arg self.protocol = InstrumentProtocol(protocol_callback)
def setUp(self): """ """ self.callback_result = None self._trigger_count = 0 def protocol_callback(self, arg): callback_result = arg self.protocol = InstrumentProtocol(protocol_callback)
def __init__(self, driver_event): """ Protocol constructor. @param driver_event Driver process event callback. """ # Construct protocol superclass. InstrumentProtocol.__init__(self, driver_event) # Build protocol state machine. self._protocol_fsm = ThreadSafeFSM(ProtocolState, ProtocolEvent, ProtocolEvent.ENTER, ProtocolEvent.EXIT) # Add event handlers for protocol state machine. handlers = { ProtocolState.UNKNOWN: [ (ProtocolEvent.ENTER, self._handler_generic_enter), (ProtocolEvent.EXIT, self._handler_generic_exit), (ProtocolEvent.DISCOVER, self._handler_unknown_discover), ], ProtocolState.COMMAND: [ (ProtocolEvent.ENTER, self._handler_generic_enter), (ProtocolEvent.EXIT, self._handler_generic_exit), (ProtocolEvent.START_DIRECT, self._handler_command_start_direct), (ProtocolEvent.GET, self._handler_command_get), (ProtocolEvent.SET, self._handler_command_set), (ProtocolEvent.START_AUTOSAMPLE, self._handler_command_start_autosample), (ProtocolEvent.ACQUIRE_SAMPLE, self._handler_command_start_poll), (ProtocolEvent.CALIBRATE, self._handler_command_start_calibrate), (ProtocolEvent.START_NAFION, self._handler_command_start_nafion_regen), (ProtocolEvent.START_ION, self._handler_command_start_ion_regen), (ProtocolEvent.ERROR, self._handler_error), (ProtocolEvent.POWEROFF, self._handler_command_poweroff), (ProtocolEvent.START_MANUAL, self._handler_command_start_manual), ], ProtocolState.AUTOSAMPLE: [ (ProtocolEvent.ENTER, self._handler_generic_enter), (ProtocolEvent.EXIT, self._handler_generic_exit), (ProtocolEvent.ACQUIRE_SAMPLE, self._handler_autosample_acquire_sample), (ProtocolEvent.STOP, self._handler_stop_generic), (ProtocolEvent.STOP_AUTOSAMPLE, self._handler_stop_generic), (ProtocolEvent.ERROR, self._handler_error), ], ProtocolState.POLL: [ (ProtocolEvent.ENTER, self._handler_generic_enter), (ProtocolEvent.EXIT, self._handler_generic_exit), (ProtocolEvent.STOP, self._handler_stop_generic), (ProtocolEvent.ERROR, self._handler_error), ], ProtocolState.ERROR: [ (ProtocolEvent.ENTER, self._handler_generic_enter), (ProtocolEvent.EXIT, self._handler_generic_exit), (ProtocolEvent.CLEAR, self._handler_error_clear), ], ProtocolState.CALIBRATE: [ (ProtocolEvent.ENTER, self._handler_generic_enter), (ProtocolEvent.EXIT, self._handler_generic_exit), (ProtocolEvent.STOP, self._handler_stop_generic), (ProtocolEvent.ERROR, self._handler_error), ], ProtocolState.REGEN: [ (ProtocolEvent.ENTER, self._handler_generic_enter), (ProtocolEvent.EXIT, self._handler_generic_exit), (ProtocolEvent.STOP_REGEN, self._handler_stop_regen), (ProtocolEvent.REGEN_COMPLETE, self._handler_regen_complete), (ProtocolEvent.ERROR, self._handler_error), ], ProtocolState.DIRECT_ACCESS: [ (ProtocolEvent.ENTER, self._handler_direct_access_enter), (ProtocolEvent.EXIT, self._handler_direct_access_exit), (ProtocolEvent.STOP_DIRECT, self._handler_direct_access_stop_direct), (ProtocolEvent.EXECUTE_DIRECT, self._handler_direct_access_execute_direct), ], ProtocolState.MANUAL_OVERRIDE: [ (ProtocolEvent.ENTER, self._handler_generic_enter), (ProtocolEvent.EXIT, self._handler_generic_exit), (ProtocolEvent.STOP_MANUAL, self._handler_manual_override_stop), (ProtocolEvent.GET_SLAVE_STATES, self._handler_manual_get_slave_states), ], } for state in handlers: for event, handler in handlers[state]: self._protocol_fsm.add_handler(state, event, handler) # Construct the parameter dictionary containing device parameters, # current parameter values, and set formatting functions. self._build_param_dict() self._build_command_dict() self._build_driver_dict() # State state machine in UNKNOWN state. self._protocol_fsm.start(ProtocolState.UNKNOWN) # commands sent sent to device to be filtered in responses for telnet DA self._sent_cmds = [] self._slave_protocols = {} self.initialize_scheduler()
class TestUnitInstrumentProtocol(MiUnitTestCase): """ Test cases for instrument protocol class. Functions in this class provide instrument protocol unit tests and provide a tutorial on use of the protocol interface. """ def setUp(self): """ """ self.callback_result = None self._trigger_count = 0 self._events = [] self.protocol = InstrumentProtocol(self.event_callback) def event_callback(self, event, value=None): log.debug("Test event callback: %s" % event) self._events.append(event) self._trigger_count += 1 def _scheduler_callback(self): """ Callback to test the scheduler """ self._trigger_count += 1 def assert_scheduled_event_triggered(self, event_count=1): count = 0 for i in range(0, 40): count = self._trigger_count log.debug("check for triggered event, count %d" % self._trigger_count) if(count >= event_count): break time.sleep(0.3) self.assertGreater(count, 0) def test_extraction(self): sample_line = "SATPAR0229,10.01,2206748544,234\r\n" ntptime = ntplib.system_to_ntp_time(time.time()) result = self.protocol._extract_sample(SatlanticPARDataParticle, SAMPLE_REGEX, sample_line, ntptime, publish=False) log.debug("R: %s" % result) self.assertEqual(result['stream_name'], SatlanticPARDataParticle(None, None).data_particle_type()) # Test the format of the result in the individual driver tests. Here, # just tests that the result is there. @unittest.skip('Not Written') def test_publish_raw(self): """ Tests to see if raw data is appropriately published back out to the InstrumentAgent via the event callback. """ # build a packet # have it published by the protocol (force state if needed) # delay? # catch it in the callback # confirm it came back # compare response to original packet self.assertTrue(False) @unittest.skip('Not Written') def test_publish_parsed_data(self): """ Tests to see if parsed data is appropriately published back to the InstrumentAgent via the event callback. """ # similar to above self.assertTrue(False) @unittest.skip('Not Written') def test_publish_engineering_data(self): """ Tests to see if engineering data is appropriately published back to the InstrumentAgent via the event callback. """ # similar to above self.assertTrue(False) def test_get_running_config(self): """ Checks to see that one can successfully get the running config from an instrument protocol. """ # set some values log.debug("First param_dict: %s", self.protocol._param_dict.get_config()) self.protocol._param_dict.add("foo", r'foo=(.*)', lambda match : int(match.group(1)), lambda x : str(x), direct_access=True, default_value=10) self.protocol._param_dict.set_default("foo") # test hack to set w/o fetch self.protocol._param_dict.add("bar", r'bar=(.*)', lambda match : int(match.group(1)), lambda x : str(x), direct_access=False, default_value=15) self.protocol._param_dict.set_default("bar") self.assertEquals(self.protocol._param_dict.get("foo"), 10) self.assertEquals(self.protocol._param_dict.get("bar"), 15) result = self.protocol.get_cached_config() self.assertEquals(result['foo'], 10) self.assertEquals(result['bar'], 15) self.protocol._param_dict.update("bar=20") result = self.protocol.get_cached_config() self.assertEquals(result['foo'], 10) self.assertEquals(result['bar'], 20) self.assertEquals(self.protocol._param_dict.get("bar"), 20) # get and check the running config result = self.protocol.get_cached_config() self.assertTrue(isinstance(result, dict)) self.assertEquals(result['foo'], 10) self.assertEquals(result['bar'], 20) def test_init_values(self): """ Test getting and setting the initialization value for a parameter """ # set an additional value for test self.protocol._param_dict.add("foo", r'foo=(.*)', lambda match : int(match.group(1)), lambda x : str(x), direct_access=True, startup_param=True, default_value=10) self.protocol._param_dict.add("bar", r'bar=(.*)', lambda match : int(match.group(1)), lambda x : str(x), direct_access=False, startup_param=True, default_value=0) self.protocol._param_dict.add("baz", r'baz=(.*)', lambda match : int(match.group(1)), lambda x : str(x), direct_access=True, default_value=20) self.protocol._param_dict.add("bat", r'bat=(.*)', lambda match : int(match.group(1)), lambda x : str(x), startup_param=False, default_value=20) self.protocol._param_dict.add("qux", r'qux=(.*)', lambda match : int(match.group(1)), lambda x : str(x), startup_param=True) self.protocol._param_dict.add("rok", r'rok=(.*)', lambda match : int(match.group(1)), lambda x : str(x)) self.protocol._param_dict.update("qux=6666") # mark init params self.assertRaises(InstrumentParameterException, self.protocol.set_init_params, []) self.protocol.set_init_params({DriverConfigKey.PARAMETERS: {"foo": 1111, "baz":2222}}) # get new startup config self.assertRaises(InstrumentProtocolException, self.protocol.get_startup_config) self.protocol.set_init_params({DriverConfigKey.PARAMETERS: {"foo": 1111, "baz":2222, "bat": 11, "qux": 22}}) result = self.protocol.get_startup_config() self.assertEquals(len(result), 5) self.assertEquals(result["foo"], 1111) # init param self.assertEquals(result["bar"], 0) # init param with default value self.assertEquals(result["baz"], 2222) # non-init param, but value specified self.assertEquals(result["bat"], 11) # set param self.assertEquals(result["qux"], 22) # set param self.assertIsNone(result.get("rok")) # defined in paramdict, no config def test_apply_startup_params(self): """ Test that the apply startup parameters method exists and throws a "not implemented" exception for the base class """ self.assertRaises(NotImplementedException, self.protocol.apply_startup_params) def test_scheduler(self): """ Test to see that the scheduler can add and remove jobs properly Jobs are just queued for adding unit we call initialize_scheduler then the jobs are actually created. """ dt = datetime.datetime.now() + datetime.timedelta(0,1) job_name = 'test_job' startup_config = { DriverConfigKey.SCHEDULER: { job_name: { DriverSchedulerConfigKey.TRIGGER: { DriverSchedulerConfigKey.TRIGGER_TYPE: TriggerType.ABSOLUTE, DriverSchedulerConfigKey.DATE: dt } } } } self.protocol.set_init_params(startup_config) # Verify we are initialized properly self.assertIsNone(self.protocol._scheduler) self.assertEqual(self.protocol._scheduler_config, {}) self.assertEqual(self.protocol._scheduler_callback, {}) # Verify the the scheduler is created self.protocol.initialize_scheduler() self.assertIsInstance(self.protocol._scheduler, DriverScheduler) self.assertEqual(self.protocol._scheduler_config, {}) self.assertEqual(self.protocol._scheduler_callback, {}) # Now lets see some magic happen. Lets add our schedulers. Generally # This would be done as part of the protocol init, but it can happen # anytime. If the scheduler has already been initialized the # job will be started right away self.protocol._add_scheduler(job_name, self._scheduler_callback) self.assertEqual(0, self._trigger_count) self.assert_scheduled_event_triggered() def test_scheduler_event(self): """ Test if we can add and trigger jobs using events instead of callbacks We will create two event triggers, foo and bar. They should come in that order. """ self.protocol._protocol_fsm = Mock() #self.protocol._fsm.on_event = Mock() dt = datetime.datetime.now() + datetime.timedelta(0,1) foo_scheduler = 'foo' bar_scheduler = 'bar' startup_config = { DriverConfigKey.SCHEDULER: { foo_scheduler: { DriverSchedulerConfigKey.TRIGGER: { DriverSchedulerConfigKey.TRIGGER_TYPE: TriggerType.INTERVAL, DriverSchedulerConfigKey.SECONDS: 1 } }, bar_scheduler: { DriverSchedulerConfigKey.TRIGGER: { DriverSchedulerConfigKey.TRIGGER_TYPE: TriggerType.INTERVAL, DriverSchedulerConfigKey.SECONDS: 2 } } } } self.protocol.set_init_params(startup_config) # Verify we are initialized properly self.assertIsNone(self.protocol._scheduler) self.assertEqual(self.protocol._scheduler_config, {}) self.assertEqual(self.protocol._scheduler_callback, {}) # Verify the the scheduler is created self.protocol.initialize_scheduler() self.assertIsInstance(self.protocol._scheduler, DriverScheduler) self.assertEqual(self.protocol._scheduler_config, {}) self.assertEqual(self.protocol._scheduler_callback, {}) # Now lets see some magic happen. Lets add our schedulers. Generally # This would be done as part of the protocol init, but it can happen # anytime. If the scheduler has already been initialized the # job will be started right away foo_event='foo' bar_event='bar' self.protocol._add_scheduler_event(foo_scheduler, foo_event) self.protocol._add_scheduler_event(bar_scheduler, bar_event) self.assertEqual(0, self._trigger_count)