def test_complex_get(self): original_dct = { 'details': { 'key1': 'value1', 'subkey': { 'subkey': 'subvalue' } } } dct = DotDict(original_dct) assert dct.get('does.not.exist') is None assert dct.get('details') == {'key1': 'value1','subkey': {'subkey': 'subvalue'}} assert dct.get('details.key1') == 'value1' assert dct.get('details.subkey') == {'subkey':'subvalue'} assert dct.get('details.subkey.subkey') == 'subvalue'
def onMessage(self, message, metadata): if 'source' not in message: return (message, metadata) if not message['source'] == 'guardduty': return (message, metadata) # reformat the date fields to iosformat for date_key in self.date_keys: if key_exists(date_key, message): message = self.convert_key_date_format(date_key, message) # convert the dict to a dot dict for saner deep key/value processing message = DotDict(message) # pull out the likely source IP address for ipaddress_key in self.ipaddress_keys: if 'sourceipaddress' not in message['details'].keys(): if key_exists(ipaddress_key, message): message.details.sourceipaddress = message.get( ipaddress_key) # if we still haven't found what we are looking for #U2 # sometimes it's in a list if 'sourceipaddress' not in message['details'].keys(): if key_exists('details.finding.action.portProbeAction.portProbeDetails', message) \ and isinstance(message.details.finding.action.portProbeAction.portProbeDetails, list): # inspect the first list entry and see if it contains an IP portProbeDetails = DotDict(message.details.finding.action. portProbeAction.portProbeDetails[0]) if key_exists('remoteIpDetails.ipAddressV4', portProbeDetails): message.details.sourceipaddress = portProbeDetails.remoteIpDetails.ipAddressV4 # recovert the message back to a plain dict return (dict(message), metadata)
def test_complex_get(self): original_dct = { 'details': { 'key1': 'value1', 'subkey': { 'subkey': 'subvalue' } } } dct = DotDict(original_dct) assert dct.get('does.not.exist') is None assert dct.get('details') == { 'key1': 'value1', 'subkey': { 'subkey': 'subvalue' } } assert dct.get('details.key1') == 'value1' assert dct.get('details.subkey') == {'subkey': 'subvalue'} assert dct.get('details.subkey.subkey') == 'subvalue'
def onAggregation(self, aggreg): # aggreg['count']: number of items in the aggregation, ex: number of failed login attempts # aggreg['value']: value of the aggregation field, ex: [email protected] # aggreg['events']: list of events in the aggregation category = aggreg['config']['alert_category'] tags = aggreg['config']['alert_tags'] severity = aggreg['config']['alert_severity'] url = aggreg['config']['alert_url'] # Find all affected hosts # Normally, the hostname data is in e.hostname so try that first, # but fall back to e.hostname if it is missing, or nothing at all if there's no hostname! ;-) hostnames = [] for e in aggreg['events']: event_source = e['_source'] if 'hostname' in event_source: hostnames.append(event_source['hostname']) summary = '{} ({}): {}'.format( aggreg['config']['alert_summary'], aggreg['count'], aggreg['value'], ) # If additional summary fields is defined, loop through each # and pull out the value from each event (if it exists) # and append key=value(s) to the summary field if 'additional_summary_fields' in aggreg['config']: for additional_field in aggreg['config'][ 'additional_summary_fields']: values_found = [] # If the field exists in each EVENT, include it in alert summary for event in aggreg['events']: dot_event = DotDict(event['_source']) value = dot_event.get(additional_field) if value: values_found.append(value) # Let's add the key=value(s) to summary if len(values_found) != 0: values_str = '{}'.format(', '.join(set(values_found))) summary += " ({0}={1})".format(additional_field, values_str) if hostnames: summary += ' [{}]'.format(', '.join(set(hostnames))) return self.createAlertDict(summary, category, tags, aggreg['events'], severity, url)
def onMessage(self, message, metadata): if 'source' not in message: return (message, metadata) if not message['source'] == 'guardduty': return (message, metadata) # reformat the date fields to iosformat for date_key in self.date_keys: if key_exists(date_key, message): if message.get(date_key) is None: continue else: message = self.convert_key_date_format(date_key, message) # convert the dict to a dot dict for saner deep key/value processing message = DotDict(message) # pull out the likely source IP address for ipaddress_key in self.ipaddress_keys: if 'sourceipaddress' not in message['details']: if key_exists(ipaddress_key, message): message.details.sourceipaddress = message.get( ipaddress_key) # if we still haven't found what we are looking for #U2 # sometimes it's in a list if 'sourceipaddress' not in message['details']: if key_exists('details.finding.action.portprobeaction.portprobedetails', message) \ and isinstance(message.details.finding.action.portprobeaction.portprobedetails, list): # inspect the first list entry and see if it contains an IP portprobedetails = DotDict( message.details.finding.action.portprobeaction.portprobedetails[0]) if key_exists('remoteipdetails.ipaddressv4', portprobedetails): message.details.sourceipaddress = portprobedetails.remoteipdetails.ipaddressv4 # recovert the message back to a plain dict return (dict(message), metadata)