class TriggerInstanceDispatcher(consumers.MessageHandler): message_type = dict def __init__(self, connection, queues): super(TriggerInstanceDispatcher, self).__init__(connection, queues) self.rules_engine = RulesEngine() def process(self, instance): trigger = instance['trigger'] payload = instance['payload'] trigger_instance = None try: trigger_instance = container_utils.create_trigger_instance( trigger, payload or {}, date_utils.get_datetime_utc_now(), raise_on_no_trigger=True) except: # We got a trigger ref but we were unable to create a trigger instance. # This could be because a trigger object wasn't found in db for the ref. LOG.exception('Failed to create trigger_instance %s.', instance) return if trigger_instance: try: self.rules_engine.handle_trigger_instance(trigger_instance) except: # This could be a large message but at least in case of an exception # we get to see more context. # Beyond this point code cannot really handle the exception anyway so # eating up the exception. LOG.exception('Failed to handle trigger_instance %s.', instance) return
class TriggerInstanceDispatcher(consumers.MessageHandler): message_type = dict def __init__(self, connection, queues): super(TriggerInstanceDispatcher, self).__init__(connection, queues) self.rules_engine = RulesEngine() def process(self, instance): trigger = instance['trigger'] payload = instance['payload'] try: trigger_instance = container_utils.create_trigger_instance( trigger, payload or {}, datetime.datetime.utcnow()) if trigger_instance: self.rules_engine.handle_trigger_instance(trigger_instance) except: # This could be a large message but at least in case of an exception # we get to see more context. # Beyond this point code cannot really handle the exception anyway so # eating up the exception. LOG.exception('Failed to handle trigger_instance %s.', instance)
def test_handle_trigger_instances(self): trigger_instance_1 = container_utils.create_trigger_instance( 'dummy_pack_1.st2.test.trigger1', { 'k1': 't1_p_v', 'k2': 'v2' }, date_utils.get_datetime_utc_now()) trigger_instance_2 = container_utils.create_trigger_instance( 'dummy_pack_1.st2.test.trigger1', { 'k1': 't1_p_v', 'k2': 'v2', 'k3': 'v3' }, date_utils.get_datetime_utc_now()) trigger_instance_3 = container_utils.create_trigger_instance( 'dummy_pack_1.st2.test.trigger2', { 'k1': 't1_p_v', 'k2': 'v2', 'k3': 'v3' }, date_utils.get_datetime_utc_now()) instances = [ trigger_instance_1, trigger_instance_2, trigger_instance_3 ] rules_engine = RulesEngine() for instance in instances: rules_engine.handle_trigger_instance(instance)
class Worker(ConsumerMixin): def __init__(self, connection): self.connection = connection self.rules_engine = RulesEngine() self._dispatcher = BufferedDispatcher() def shutdown(self): self._dispatcher.shutdown() def get_consumers(self, Consumer, channel): consumer = Consumer(queues=[RULESENGINE_WORK_Q], accept=['pickle'], callbacks=[self.process_task]) # use prefetch_count=1 for fair dispatch. This way workers that finish an item get the next # task and the work does not get queued behind any single large item. consumer.qos(prefetch_count=1) return [consumer] def process_task(self, body, message): # LOG.debug('process_task') # LOG.debug(' body: %s', body) # LOG.debug(' message.properties: %s', message.properties) # LOG.debug(' message.delivery_info: %s', message.delivery_info) try: self._dispatcher.dispatch(self._do_process_task, body['trigger'], body['payload']) finally: message.ack() def _do_process_task(self, trigger, payload): trigger_instance = container_utils.create_trigger_instance( trigger, payload or {}, datetime.datetime.utcnow()) if trigger_instance: self.rules_engine.handle_trigger_instance(trigger_instance)
def test_handle_trigger_instance_no_rules(self): trigger_instance = container_utils.create_trigger_instance( 'dummy_pack_1.st2.test.trigger3', {'k1': 't1_p_v', 'k2': 'v2'}, date_utils.get_datetime_utc_now() ) rules_engine = RulesEngine() rules_engine.handle_trigger_instance(trigger_instance) # should not throw.
def test_handle_trigger_instance_no_rules(self): trigger_instance = container_utils.create_trigger_instance( "dummy_pack_1.st2.test.trigger3", {"k1": "t1_p_v", "k2": "v2"}, date_utils.get_datetime_utc_now(), ) rules_engine = RulesEngine() rules_engine.handle_trigger_instance(trigger_instance) # should not throw.
def test_get_matching_rules_filters_disabled_rules(self): trigger_instance = container_utils.create_trigger_instance( "dummy_pack_1.st2.test.trigger1", {"k1": "t1_p_v", "k2": "v2"}, date_utils.get_datetime_utc_now() ) rules_engine = RulesEngine() matching_rules = rules_engine.get_matching_rules_for_trigger(trigger_instance) expected_rules = ["st2.test.rule2"] for rule in matching_rules: self.assertTrue(rule.name in expected_rules)
def test_get_matching_rules_filters_disabled_rules(self): trigger_instance = container_utils.create_trigger_instance( 'dummy_pack_1.st2.test.trigger1', {'k1': 't1_p_v', 'k2': 'v2'}, date_utils.get_datetime_utc_now() ) rules_engine = RulesEngine() matching_rules = rules_engine.get_matching_rules_for_trigger(trigger_instance) expected_rules = ['st2.test.rule2'] for rule in matching_rules: self.assertTrue(rule.name in expected_rules)
def test_get_matching_rules_filters_disabled_rules(self): trigger_instance = container_utils.create_trigger_instance( "dummy_pack_1.st2.test.trigger1", {"k1": "t1_p_v", "k2": "v2"}, date_utils.get_datetime_utc_now(), ) rules_engine = RulesEngine() matching_rules = rules_engine.get_matching_rules_for_trigger(trigger_instance) expected_rules = ["st2.test.rule2"] for rule in matching_rules: self.assertIn(rule.name, expected_rules)
class TriggerDispatcher(object): def __init__(self): self.rules_engine = RulesEngine() def dispatch(self, trigger, payload=None): """ """ trigger_instance = container_utils.create_trigger_instance( trigger, payload or {}, datetime.datetime.utcnow()) if trigger_instance: self.rules_engine.handle_trigger_instance(trigger_instance)
class TriggerInstanceDispatcher(consumers.MessageHandler): message_type = dict def __init__(self, connection, queues): super(TriggerInstanceDispatcher, self).__init__(connection, queues) self.rules_engine = RulesEngine() def process(self, instance): trigger = instance['trigger'] payload = instance['payload'] trigger_instance = None try: trigger_instance = container_utils.create_trigger_instance( trigger, payload or {}, date_utils.get_datetime_utc_now(), raise_on_no_trigger=True) except: # We got a trigger ref but we were unable to create a trigger instance. # This could be because a trigger object wasn't found in db for the ref. LOG.exception('Failed to create trigger_instance %s.', instance) return if trigger_instance: try: # Use trace_context from the instance and if not found create a new context # and use the trigger_instance.id as trace_tag. trace_context = instance.get(TRACE_CONTEXT, None) if not trace_context: trace_context = { TRACE_ID: 'trigger_instance-%s' % str(trigger_instance.id) } # add a trace or update an existing trace with trigger_instance trace_service.add_or_update_given_trace_context( trace_context=trace_context, trigger_instances=[ trace_service.get_trace_component_for_trigger_instance( trigger_instance) ]) self.rules_engine.handle_trigger_instance(trigger_instance) except: # This could be a large message but at least in case of an exception # we get to see more context. # Beyond this point code cannot really handle the exception anyway so # eating up the exception. LOG.exception('Failed to handle trigger_instance %s.', instance) return
class TriggerInstanceDispatcher(consumers.MessageHandler): message_type = dict def __init__(self, connection, queues): super(TriggerInstanceDispatcher, self).__init__(connection, queues) self.rules_engine = RulesEngine() def process(self, instance): trigger = instance['trigger'] payload = instance['payload'] trigger_instance = None try: trigger_instance = container_utils.create_trigger_instance( trigger, payload or {}, date_utils.get_datetime_utc_now(), raise_on_no_trigger=True) except: # We got a trigger ref but we were unable to create a trigger instance. # This could be because a trigger object wasn't found in db for the ref. LOG.exception('Failed to create trigger_instance %s.', instance) return if trigger_instance: try: # Use trace_context from the instance and if not found create a new context # and use the trigger_instance.id as trace_tag. trace_context = instance.get(TRACE_CONTEXT, None) if not trace_context: trace_context = { TRACE_ID: 'trigger_instance-%s' % str(trigger_instance.id) } # add a trace or update an existing trace with trigger_instance trace_service.add_or_update_given_trace_context( trace_context=trace_context, trigger_instances=[ trace_service.get_trace_component_for_trigger_instance(trigger_instance) ]) self.rules_engine.handle_trigger_instance(trigger_instance) except: # This could be a large message but at least in case of an exception # we get to see more context. # Beyond this point code cannot really handle the exception anyway so # eating up the exception. LOG.exception('Failed to handle trigger_instance %s.', instance) return
def test_handle_trigger_instances(self): trigger_instance_1 = container_utils.create_trigger_instance( "dummy_pack_1.st2.test.trigger1", {"k1": "t1_p_v", "k2": "v2"}, date_utils.get_datetime_utc_now() ) trigger_instance_2 = container_utils.create_trigger_instance( "dummy_pack_1.st2.test.trigger1", {"k1": "t1_p_v", "k2": "v2", "k3": "v3"}, date_utils.get_datetime_utc_now(), ) trigger_instance_3 = container_utils.create_trigger_instance( "dummy_pack_1.st2.test.trigger2", {"k1": "t1_p_v", "k2": "v2", "k3": "v3"}, date_utils.get_datetime_utc_now(), ) instances = [trigger_instance_1, trigger_instance_2, trigger_instance_3] rules_engine = RulesEngine() for instance in instances: rules_engine.handle_trigger_instance(instance)
def test_handle_trigger_instances(self): trigger_instance_1 = container_utils.create_trigger_instance( 'dummy_pack_1.st2.test.trigger1', {'k1': 't1_p_v', 'k2': 'v2'}, date_utils.get_datetime_utc_now() ) trigger_instance_2 = container_utils.create_trigger_instance( 'dummy_pack_1.st2.test.trigger1', {'k1': 't1_p_v', 'k2': 'v2', 'k3': 'v3'}, date_utils.get_datetime_utc_now() ) trigger_instance_3 = container_utils.create_trigger_instance( 'dummy_pack_1.st2.test.trigger2', {'k1': 't1_p_v', 'k2': 'v2', 'k3': 'v3'}, date_utils.get_datetime_utc_now() ) instances = [trigger_instance_1, trigger_instance_2, trigger_instance_3] rules_engine = RulesEngine() for instance in instances: rules_engine.handle_trigger_instance(instance)
def test_handle_trigger_instances(self): trigger_instance_1 = container_utils.create_trigger_instance( "dummy_pack_1.st2.test.trigger1", {"k1": "t1_p_v", "k2": "v2"}, date_utils.get_datetime_utc_now(), ) trigger_instance_2 = container_utils.create_trigger_instance( "dummy_pack_1.st2.test.trigger1", {"k1": "t1_p_v", "k2": "v2", "k3": "v3"}, date_utils.get_datetime_utc_now(), ) trigger_instance_3 = container_utils.create_trigger_instance( "dummy_pack_1.st2.test.trigger2", {"k1": "t1_p_v", "k2": "v2", "k3": "v3"}, date_utils.get_datetime_utc_now(), ) instances = [trigger_instance_1, trigger_instance_2, trigger_instance_3] rules_engine = RulesEngine() for instance in instances: rules_engine.handle_trigger_instance(instance)
class TriggerInstanceDispatcher(consumers.MessageHandler): message_type = dict def __init__(self, connection, queues): super(TriggerInstanceDispatcher, self).__init__(connection, queues) self.rules_engine = RulesEngine() def process(self, instance): trigger = instance['trigger'] payload = instance['payload'] try: trigger_instance = container_utils.create_trigger_instance( trigger, payload or {}, date_utils.get_datetime_utc_now()) if trigger_instance: self.rules_engine.handle_trigger_instance(trigger_instance) except: # This could be a large message but at least in case of an exception # we get to see more context. # Beyond this point code cannot really handle the exception anyway so # eating up the exception. LOG.exception('Failed to handle trigger_instance %s.', instance)
def test_handle_trigger_instance_no_rules(self): trigger_instance = container_utils.create_trigger_instance( "dummy_pack_1.st2.test.trigger3", {"k1": "t1_p_v", "k2": "v2"}, date_utils.get_datetime_utc_now() ) rules_engine = RulesEngine() rules_engine.handle_trigger_instance(trigger_instance) # should not throw.
def __init__(self, connection): self.connection = connection self.rules_engine = RulesEngine() self._dispatcher = BufferedDispatcher()
class TriggerInstanceDispatcher(consumers.StagedMessageHandler): message_type = dict def __init__(self, connection, queues): super(TriggerInstanceDispatcher, self).__init__(connection, queues) self.rules_engine = RulesEngine() def pre_ack_process(self, message): ''' TriggerInstance from message is create prior to acknowledging the message. This gets us a way to not acknowledge messages. ''' trigger = message['trigger'] payload = message['payload'] # Accomodate for not being able to create a TrigegrInstance if a TriggerDB # is not found. trigger_instance = container_utils.create_trigger_instance( trigger, payload or {}, date_utils.get_datetime_utc_now(), raise_on_no_trigger=True) return self._compose_pre_ack_process_response(trigger_instance, message) def process(self, pre_ack_response): trigger_instance, message = self._decompose_pre_ack_process_response(pre_ack_response) if not trigger_instance: raise ValueError('No trigger_instance provided for processing.') get_driver().inc_counter('trigger.%s.processed' % (trigger_instance.trigger)) try: # Use trace_context from the message and if not found create a new context # and use the trigger_instance.id as trace_tag. trace_context = message.get(TRACE_CONTEXT, None) if not trace_context: trace_context = { TRACE_ID: 'trigger_instance-%s' % str(trigger_instance.id) } # add a trace or update an existing trace with trigger_instance trace_service.add_or_update_given_trace_context( trace_context=trace_context, trigger_instances=[ trace_service.get_trace_component_for_trigger_instance(trigger_instance) ] ) container_utils.update_trigger_instance_status( trigger_instance, trigger_constants.TRIGGER_INSTANCE_PROCESSING) with CounterWithTimer(key='rule.processed'): with Timer(key='trigger.%s.processed' % (trigger_instance.trigger)): self.rules_engine.handle_trigger_instance(trigger_instance) container_utils.update_trigger_instance_status( trigger_instance, trigger_constants.TRIGGER_INSTANCE_PROCESSED) except: # TODO : Capture the reason for failure. container_utils.update_trigger_instance_status( trigger_instance, trigger_constants.TRIGGER_INSTANCE_PROCESSING_FAILED) # This could be a large message but at least in case of an exception # we get to see more context. # Beyond this point code cannot really handle the exception anyway so # eating up the exception. LOG.exception('Failed to handle trigger_instance %s.', trigger_instance) return @staticmethod def _compose_pre_ack_process_response(trigger_instance, message): """ Codify response of the pre_ack_process method. """ return {'trigger_instance': trigger_instance, 'message': message} @staticmethod def _decompose_pre_ack_process_response(response): """ Break-down response of pre_ack_process into constituents for simpler consumption. """ return response.get('trigger_instance', None), response.get('message', None)
def __init__(self): self.rules_engine = RulesEngine()
def __init__(self, connection, queues): super(TriggerInstanceDispatcher, self).__init__(connection, queues) self.rules_engine = RulesEngine()