diff --git a/Integrations/integration-FireEye_ETP.yml b/Integrations/integration-FireEye_ETP.yml new file mode 100644 index 000000000000..05500b2f5970 --- /dev/null +++ b/Integrations/integration-FireEye_ETP.yml @@ -0,0 +1,918 @@ +commonfields: + id: FireEye ETP + version: -1 +name: FireEye ETP +display: FireEye ETP +category: Email Gateway +image: data:image/png;base64,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 +description: 'FireEye Email Threat Prevention (ETP Cloud) is a cloud-based platform + that protects against advanced email attacks. ' +configuration: +- display: 'Server URL. Valid values: https://etp.us.fireeye.com, https://etp.eu.fireeye.com, + https://etp.us.fireeyegov.com ' + name: server + defaultvalue: https://etp.us.fireeye.com + type: 0 + required: true +- display: API key + name: api_key + defaultvalue: "" + type: 4 + required: true +- display: Trust any certificate (unsecure) + name: unsecure + defaultvalue: "true" + type: 8 + required: false +- display: Use system proxy settings + name: proxy + defaultvalue: "" + type: 0 + required: false +- display: Fetch incidents + name: isFetch + defaultvalue: "" + type: 8 + required: false +- display: Incident type + name: incidentType + defaultvalue: "" + type: 13 + required: false +- display: Messages status. All messages with the status specified will be imported + as incidents. + name: message_status + defaultvalue: delivered (retroactive) + type: 0 + required: false +script: + script: |- + from datetime import timedelta, datetime + import requests + import os + import re + import copy + import json + # disable insecure warnings + from requests.packages.urllib3.exceptions import InsecureRequestWarning + requests.packages.urllib3.disable_warnings(InsecureRequestWarning) + + def set_proxies(): + if demisto.params()['proxy']: + http = os.environ['http_proxy'] or os.environ['HTTP_PROXY'] + https = os.environ['https_proxy'] or os.environ['HTTPS_PROXY'] + proxies = { + 'http': http, + 'https': https + } + return proxies + return None + + + ''' + GLOBAL VARS + ''' + + API_KEY = demisto.params().get('api_key') + PROXIES = set_proxies() + BASE_PATH = '{}/api/v1'.format(demisto.params().get('server')) + HTTP_HEADERS = { + 'Content-Type': 'application/json' + } + USE_SSL = not demisto.params().get('unsecure') + MESSAGE_STATUS = demisto.params().get('message_status') + + ''' + SAERCH ATTRIBUTES VALID VALUES + ''' + + REJECTION_REASONS = [ + 'ETP102', 'ETP103', 'ETP104', 'ETP200', 'ETP201', 'ETP203','ETP204', 'ETP205', + 'ETP300', 'ETP301', 'ETP302', 'ETP401','ETP402', 'ETP403', 'ETP404', 'ETP405'] + + STATUS_VALUES = ["accepted", "deleted", "delivered", "delivered (retroactive)", "dropped", + "dropped oob", "dropped (oob retroactive)", "permanent failure", "processing", "quarantined", "rejected", "temporary failure"] + + ''' + BASIC FUNCTIONS + ''' + def listify(comma_separated_list): + + if isinstance(comma_separated_list, list): + return comma_separated_list + return comma_separated_list.split(',') + + def http_request(method, url, body=None, headers={}, url_params=None): + ''' + returns the http response + ''' + + #add API key to headers + headers['x-fireeye-api-key'] = API_KEY + + request_kwargs = { + 'headers': headers, + 'verify': USE_SSL, + 'proxies': PROXIES + } + + #add optional arguments if specified + if body is not None: + request_kwargs['data'] = json.dumps(body) + if url_params is not None: + request_kwargs['params'] = json.dumps(url_params) + + LOG('attempting {} request sent to {} with body:\n{}'.format(method, url, json.dumps(body, indent=4))) + response = requests.request( + method, + url, + **request_kwargs + ) + #handle request failure + if response.status_code not in range(200,205): + raise ValueError('Request failed with status code {}\n{}'.format(response.status_code, response.text)) + return response.json() + + def return_error_entry(message): + entry = { + 'Type': entryTypes['error'], + 'Contents': e.message, + 'ContentsFormat': formats['text'], + } + demisto.results(entry) + + def to_search_attribute_object(value, filter=None, is_list=False ,valid_values=None): + + values = listify(value) if is_list else value + if valid_values: + for val in values: + if val not in valid_values: + raise ValueError('{} is not a valid value'.format(val)) + + attribute = { + 'value': values + } + if filter: + attribute['filter'] = filter + return attribute + + + def format_search_attributes(from_email=None, from_email_not_in=None, recipients=None, + recipients_not_in=None, subject=None, from_accepted_date_time=None, to_accepted_date_time=None, + rejection_reason=None, sender_ip=None, status=None, status_not_in=None, last_modified_date_time=None, domains=None): + + search_attributes = {} + + #handle from_email attribute + if from_email and from_email_not_in: + raise ValueError('Only one of the followings can be specified: from_email, from_email_not_in') + if from_email: + search_attributes['fromEmail'] = to_search_attribute_object(from_email, filter='in', is_list=True) + elif from_email_not_in: + search_attributes['fromEmail'] = to_search_attribute_object(from_email_not_in, filter='not in', is_list=True) + + #handle recipients attributes + if recipients and recipients_not_in: + raise ValueError('Only one of the followings can be specified: recipients, recipients_not_in') + if recipients: + search_attributes['recipients'] = to_search_attribute_object(recipients, filter='in', is_list=True) + elif recipients_not_in: + search_attributes['recipients'] = to_search_attribute_object(recipients_not_in, filter='not in', is_list=True) + + #handle status attributes + if status and status_not_in: + raise ValueError('Only one of the followings can be specified: status, status_not_in') + if status: + search_attributes['status'] = to_search_attribute_object(status, filter='in', is_list=True, valid_values=STATUS_VALUES) + elif status_not_in: + search_attributes['status'] = to_search_attribute_object(status, filter='in', is_list=True, valid_values=STATUS_VALUES) + + if subject: + search_attributes['subject'] = to_search_attribute_object(subject, filter='in', is_list=True) + if rejection_reason: + search_attributes['rejectionReason'] = to_search_attribute_object(rejection_reason, is_list=True, valid_values=REJECTION_REASONS) + if sender_ip: + search_attributes['senderIP'] = to_search_attribute_object(sender_ip, filter='in', is_list=True) + if domains: + search_attributes['domains'] = to_search_attribute_object(domains, is_list=True) + if from_accepted_date_time and to_accepted_date_time: + search_attribute['period'] = { + 'range': { + 'fromAcceptedDateTime': from_accepted_date_time, + 'toAcceptedDateTime': to_accepted_date_time + } + } + if last_modified_date_time: + # try to parse '>timestamp' | '>=timestamp' | '', context_data['senderHeader'].replace('\\"','')) + context_data['from'] = match.group() if match else context_data['senderHeader'] + + if context_data.get('recipientHeader') is None: + context_data['recipients'] = [] + return context_data + + recipients = [] + for recipient_header in context_data.get('recipientHeader', []): + match = re.search('<(.*)>', recipient_header) + recipient_address = match.group() if match else recipient_header + recipients.append(recipient_address) + context_data['recipients'] = ','.join(recipients) + + return context_data + + def search_messages_request(attributes={}, has_attachments=None, max_message_size=None): + + url = '{}/messages/trace'.format(BASE_PATH) + body = { + 'attributes': attributes, + 'type': 'MessageAttributes', + 'size': max_message_size or 20 + } + if has_attachments is not None: + body['hasAttachments'] = has_attachments + response = http_request( + 'POST', + url, + body=body, + headers=HTTP_HEADERS + ) + # no results + if response['meta']['total'] == 0: + return [] + return response['data'] + + def search_messages_command(): + + args = demisto.args() + if args.has_key('size'): + # parse to int + args['size'] = int(args['size']) + if args.get('has_attachments') is not None: + # parse to boolean + args['hasAttachments'] = args['hasAttachments'] == 'true' + + search_attributes = format_search_attributes( + from_email=args.get('from_email'), + from_email_not_in=args.get('from_email_not_in'), + recipients=args.get('recipients'), + recipients_not_in=args.get('recipients_not_in'), + subject=args.get('subject'), + from_accepted_date_time=args.get('from_accepted_date_time'), + to_accepted_date_time=args.get('to_accepted_date_time'), + rejection_reason=args.get('rejection_reason'), + sender_ip=args.get('sender_ip'), + status=args.get('status'), + status_not_in=args.get('status_not_in'), + last_modified_date_time=args.get('last_modified_date_time'), + domains=args.get('domains') + ) + + #raw data + messages_raw = search_messages_request(search_attributes, args.get('hasAttachments'), args.get('size')) + + # create context data + messages_context = [message_context_data(message) for message in messages_raw] + + # create readable data + messages_readable_data = [readable_message_data(message) for message in messages_context] + messages_md_headers = [ + 'Message ID', + 'Accepted Time', + 'From', + 'Recipients', + 'Subject', + 'Message Status' + ] + md_table = tableToMarkdown( + 'FireEye ETP - Search Messages', + messages_readable_data, + headers=messages_md_headers + ) + + entry = { + 'Type': entryTypes['note'], + 'Contents': messages_raw, + 'ContentsFormat': formats['json'], + 'ReadableContentsFormat': formats['markdown'], + 'HumanReadable': md_table, + 'EntryContext': { + "FireEyeETP.Messages(obj.id==val.id)": messages_context + } + } + demisto.results(entry) + + def get_message_request(message_id): + + url = '{}/messages/{}'.format(BASE_PATH, message_id) + response = http_request( + 'GET', + url + ) + if response['meta']['total'] == 0: + return {} + return response['data'][0] + + def get_message_command(): + + # get raw data + raw_message = get_message_request(demisto.args()['message_id']) + + if raw_message: + # create context data + context_data = message_context_data(raw_message) + + # create readable data + message_readable_data = readable_message_data(context_data) + messages_md_headers = [ + 'Message ID', + 'Accepted Time', + 'From', + 'Recipients', + 'Subject', + 'Message Status' + ] + md_table = tableToMarkdown( + 'FireEye ETP - Get Message', + message_readable_data, + headers=messages_md_headers + ) + + entry = { + 'Type': entryTypes['note'], + 'Contents': raw_message, + 'ContentsFormat': formats['json'], + 'ReadableContentsFormat': formats['markdown'], + 'HumanReadable': md_table, + 'EntryContext': { + "FireEyeETP.Messages(obj.id==val.id)": context_data + } + } + demisto.results(entry) + # no results + else: + entry = { + 'Type': entryTypes['note'], + 'Contents': {}, + 'ContentsFormat': formats['text'], + 'ReadableContentsFormat': formats['markdown'], + 'HumanReadable': '### FireEye ETP - Get Message \n no results' + } + demisto.results(entry) + + def alert_readable_data_summery(alert): + return { + 'Alert ID': alert['id'], + 'Alert Timestamp': alert['alert']['timestamp'], + 'From': alert['email']['headers']['from'], + 'Recipients': '{}|{}'.format(alert['email']['headers']['to'], alert['email']['headers']['cc']), + 'Subject': alert['email']['headers']['subject'], + 'MD5': alert['alert'].get('malware_md5'), + 'URL/Attachment': alert['email']['attachment'], + 'Email Status': alert['email']['status'], + 'Email Accepted': alert['email']['timestamp']['accepted'], + 'Threat Intel': alert['ati'] + } + + def alert_readable_data(alert): + return { + 'Alert ID': alert['id'], + 'Alert Timestamp': alert['alert']['timestamp'], + 'From': alert['email']['headers']['from'], + 'Recipients': '{}|{}'.format(alert['email']['headers']['to'], alert['email']['headers']['cc']), + 'Subject': alert['email']['headers']['subject'], + 'MD5': alert['alert'].get('malware_md5'), + 'URL/Attachment': alert['email']['attachment'], + 'Email Status': alert['email']['status'], + 'Email Accepted': alert['email']['timestamp']['accepted'], + 'Sevirity': alert['alert']['severity'] + } + + def malware_readable_data(malware): + return { + 'Name': malware['name'], + 'Domain': malware.get('domain'), + 'Downloaded At': malware['downloaded_at'], + 'Executed At': malware['executed_at'], + 'Type': malware['stype'], + 'Submitted At': malware['submitted_at'], + 'SID': malware['sid'] + } + + def alert_context_data(alert): + context_data = copy.deepcopy(alert) + # remove 'attributes' level + context_data.update(context_data.pop('attributes', {})) + return context_data + + def get_alerts_request(legacy_id=None, from_last_modified_on=None, etp_message_id=None, size=None, raw_response=False): + + url = '{}/alerts'.format(BASE_PATH) + + # constract the body for the request + body = {} + attributes = {} + if legacy_id: + attributes['legacy_id'] = legacy_id + if etp_message_id: + attributes['etp_message_id'] = etp_message_id + if attributes: + body['attribute'] = attributes + if size: + body['size'] = size + if from_last_modified_on: + body['fromLastModifiedOn'] = from_last_modified_on + + response = http_request( + 'POST', + url, + body=body, + headers=HTTP_HEADERS + ) + if raw_response: + return response + if response['meta']['total'] == 0: + return [] + return response['data'] + + def get_alerts_command(): + + args = demisto.args() + + if args.has_key('size'): + args['size'] = int(args['size']) + + if args.has_key('legacy_id'): + args['legacy_id'] = int(args['legacy_id']) + + # get raw data + alerts_raw = get_alerts_request( + legacy_id=args.get('legacy_id'), + from_last_modified_on=args.get('from_last_modified_on'), + etp_message_id=args.get('etp_message_id'), + size=args.get('size') + ) + + # create context data + alerts_context = [alert_context_data(alert) for alert in alerts_raw] + + #create readable data + alerts_readable_data = [alert_readable_data_summery(alert) for alert in alerts_context] + alerts_summery_headers = [ + 'Alert ID', + 'Alert Timestamp', + 'Email Accepted', + 'From', + 'Recipients', + 'Subject', + 'MD5', + 'URL/Attachment', + 'Email Status', + 'Threat Intel' + ] + md_table = tableToMarkdown( + 'FireEye ETP - Get Alerts', + alerts_readable_data, + headers=alerts_summery_headers + ) + entry = { + 'Type': entryTypes['note'], + 'Contents': alerts_raw, + 'ContentsFormat': formats['json'], + 'ReadableContentsFormat': formats['markdown'], + 'HumanReadable': md_table, + 'EntryContext': { + "FireEyeETP.Alerts(obj.id==val.id)": alerts_context + } + } + demisto.results(entry) + + def get_alert_request(alert_id): + url = '{}/alerts/{}'.format(BASE_PATH, alert_id) + response = http_request( + 'GET', + url + ) + if response['meta']['total'] == 0: + return {} + return response['data'][0] + + def get_alert_command(): + + # get raw data + alert_raw = get_alert_request(demisto.args()['alert_id']) + + if alert_raw: + # create context data + alert_context = alert_context_data(alert_raw) + + # create readable data + readable_data = alert_readable_data(alert_context) + alert_md_table = tableToMarkdown( + 'Alert Details', + readable_data + ) + malware_data = [malware_readable_data(malware) for malware in alert_context['alert']['explanation']['malware_detected']['malware']] + malware_md_table = tableToMarkdown( + 'Malware Details', + malware_data + ) + + entry = { + 'Type': entryTypes['note'], + 'Contents': alert_raw, + 'ContentsFormat': formats['json'], + 'ReadableContentsFormat': formats['markdown'], + 'HumanReadable': '## FireEye ETP - Get Alert\n{}\n{}'.format(alert_md_table, malware_md_table), + 'EntryContext': { + "FireEyeETP.Alerts(obj.id==val.id)": alert_context + } + } + demisto.results(entry) + # no results + else: + entry = { + 'Type': entryTypes['note'], + 'Contents': {}, + 'ContentsFormat': formats['json'], + 'ReadableContentsFormat': formats['markdown'], + 'HumanReadable': '### FireEye ETP - Get Alert\nno results', + + } + demisto.results(entry) + + + def parse_string_in_iso_format_to_datetime(iso_format_string): + alert_last_modified = None + try: + alert_last_modified = datetime.strptime(iso_format_string, "%Y-%m-%dT%H:%M:%S.%f") + except ValueError: + try: + alert_last_modified = datetime.strptime(iso_format_string, "%Y-%m-%dT%H:%M:%S") + except ValueError: + alert_last_modified = datetime.strptime(iso_format_string, "%Y-%m-%dT%H:%M") + return alert_last_modified + + def parse_alert_to_incident(alert): + + context_data = alert_context_data(alert) + incident = { + 'name': context_data['email']['headers']['subject'], + 'rawJSON': json.dumps(context_data) + } + return incident + + def fetch_incidents(): + + last_run = demisto.getLastRun() + week_ago = datetime.now() - timedelta(days=7) + iso_format = "%Y-%m-%dT%H:%M:%S.%f" + + if not last_run.has_key('last_modified'): + # parse datetime to iso format string yyy-mm-ddThh:mm:ss.fff + last_run['last_modified'] = week_ago.strftime(iso_format)[:-3] + if not last_run.has_key('last_created'): + last_run['last_created'] = week_ago.strftime(iso_format) + + alerts_raw_response = get_alerts_request( + from_last_modified_on = last_run['last_modified'], + size = 100, + raw_response=True + ) + # end if no results returned + if not alerts_raw_response or not alerts_raw_response.has_key('data'): + return + + alerts = alerts_raw_response['data'] + last_alert_created = parse_string_in_iso_format_to_datetime(last_run['last_created']) + alert_creation_limit = parse_string_in_iso_format_to_datetime(last_run['last_created']) + incidents = [] + + for alert in alerts: + # filter by message status if specified + if MESSAGE_STATUS and alert['attributes']['email']['status'] != MESSAGE_STATUS: + continue + # filter alerts created before 'last_created' + current_alert_created = parse_string_in_iso_format_to_datetime(alert['attributes']['alert']['timestamp']) + if current_alert_created < alert_creation_limit: + continue + # append alert to incident + incidents.append(parse_alert_to_incident(alert)) + # set last created + if current_alert_created > last_alert_created: + last_alert_created = current_alert_created + + last_run['last_modified'] = alerts_raw_response['meta']['fromLastModifiedOn']['end'] + last_run['last_created'] = last_alert_created.strftime(iso_format) + + demisto.incidents(incidents) + demisto.setLastRun(last_run) + + ''' + EXECUTION + ''' + + try: + if demisto.command() == 'test-module': + alerts = get_alerts_request(size=1) + # request was succesful + demisto.results('ok') + if demisto.command() == 'fetch-incidents': + fetch_incidents() + if demisto.command() == 'fireeye-etp-search-messages': + search_messages_command() + if demisto.command() == 'fireeye-etp-get-message': + get_message_command() + if demisto.command() == 'fireeye-etp-get-alerts': + get_alerts_command() + if demisto.command() == 'fireeye-etp-get-alert': + get_alert_command() + except ValueError as e: + LOG(e.message) + LOG.print_log() + return_error_entry(e.message) + type: python + commands: + - name: fireeye-etp-search-messages + arguments: + - name: from_email + description: 'List of ''From'' email-addresses, max limit of entries is 10. ' + - name: from_email_not_in + description: 'List of ''From'' email-addresses not to be included, max limit + of entries is 10. ' + - name: recipients + description: List of 'To'/'Cc' email-addresses, max limit of entries is 10. + - name: recipients_not_in + description: 'list of ''To''/''Cc'' email-addresses not to be included, max + limit of entries is 10. ' + - name: subject + description: List of strings, max limit of entries is 10. + - name: from_accepted_date_time + description: ' The time stamp of the email-accepted date to specify the beginning + of the date range to search, e.g. 2017-10- 24T10:48:51.000Z . Specify ''to_accepted_date_time'' as + well to set the complete date range for the search.' + - name: to_accepted_date_time + description: ' The time stamp of the email-accepted date to specify the end + of the date range to search, e.g. 2017-10- 24T10:48:51.000Z . Specify ''from_accepted_date_time'' as + well to set the complete date range for the search.' + - name: rejection_reason + description: 'list of ETP rejection reason codes ( "ETP102", "ETP103", "ETP104", + "ETP200", "ETP201", "ETP203", "ETP204", "ETP205", "ETP300", "ETP301", "ETP302", + "ETP401", "ETP402", "ETP403", "ETP404", "ETP405") ' + - name: sender_ip + description: List of sender IP addresses, max limit of entries is 10. + - name: status + description: List of email status values( "accepted", "deleted", "delivered", + "delivered (retroactive)", "dropped", "dropped oob", "dropped (oob retroactive)", + "permanent failure", "processing", "quarantined", "rejected", "temporary failure"). + - name: status_not_in + description: List of email status values not to include( "accepted", "deleted", + "delivered", "delivered (retroactive)", "dropped", "dropped oob", "dropped + (oob retroactive)", "permanent failure", "processing", "quarantined", "rejected", + "temporary failure"). + - name: last_modified_date_time + description: 'Date corresponding to last modified date, along with one of the + following operators: ">", "<", ">=", "<=". E.g. use value "<2017-10-24T18:00:00.000Z" + to search for messages that were last modified after the specified time stamp.' + - name: domain + description: List of domain names. + - name: has_attachments + auto: PREDEFINED + predefined: + - "true" + - "false" + description: Boolean value to indicate if the message has attachments. + - name: max_message_size + description: The default value is 20kb and maximum value is 100kb. + outputs: + - contextPath: FireEyeETP.Message.acceptedDateTime + description: Message accepted date. + - contextPath: FireEyeETP.Message.countryCode + description: Sender country code. + - contextPath: FireEyeETP.Message.domain + description: Domain. + - contextPath: FireEyeETP.Message.emailSize + description: Email size in kb. + - contextPath: FireEyeETP.Message.lastModifiedDateTime + description: Message last modified date. + - contextPath: FireEyeETP.Message.recipientHeader + description: List of message recipients header (includes the display name of + the user). + - contextPath: FireEyeETP.Message.recipients + description: List of message recipients. + - contextPath: FireEyeETP.Message.senderHeader + description: Message sender header (includes the display name of the user). + - contextPath: FireEyeETP.Message.sender + description: Message sender address. + - contextPath: FireEyeETP.Message.senderSMTP + description: Message sender SMTP. + - contextPath: FireEyeETP.Message.senderIP + description: Message sender IP. + - contextPath: FireEyeETP.Message.status + description: Message status. + - contextPath: FireEyeETP.Message.subject + description: Message subject + - contextPath: FireEyeETP.Message.verdicts.AS + description: pass/fail verdict for AS. + - contextPath: FireEyeETP.Message.verdicts.AV + description: pass/fail verdict for AV + - contextPath: FireEyeETP.Message.verdicts.AT + description: pass/fail verdict for AT + - contextPath: FireEyeETP.Message.verdicts.PV + description: pass/fail verdict for PV + - contextPath: FireEyeETP.Message.id + description: Message ID. + description: Search for messages that include specified message attributes that + are accessible in he ETP portal. + - name: fireeye-etp-get-message + arguments: + - name: message_id + required: true + description: The message ID. + outputs: + - contextPath: FireEyeETP.Message.acceptedDateTime + description: Message accepted date. + - contextPath: FireEyeETP.Message.countryCode + description: Sender country code. + - contextPath: FireEyeETP.Message.domain + description: Domain. + - contextPath: FireEyeETP.Message.emailSize + description: Email size in kb. + - contextPath: FireEyeETP.Message.lastModifiedDateTime + description: Message last modified date. + - contextPath: FireEyeETP.Message.recipientHeader + description: List of message recipients header (includes the display name of + the user). + - contextPath: FireEyeETP.Message.recipients + description: List of message recipients. + - contextPath: FireEyeETP.Message.senderHeader + description: Message sender header (includes the display name of the user). + - contextPath: FireEyeETP.Message.sender + description: Message sender address. + - contextPath: FireEyeETP.Message.senderSMTP + description: Message sender SMTP. + - contextPath: FireEyeETP.Message.senderIP + description: Message sender IP. + - contextPath: FireEyeETP.Message.status + description: Message status. + - contextPath: FireEyeETP.Message.subject + description: Message subject + - contextPath: FireEyeETP.Message.verdicts.AS + description: pass/fail verdict for AS. + - contextPath: FireEyeETP.Message.verdicts.AV + description: pass/fail verdict for AV + - contextPath: FireEyeETP.Message.verdicts.AT + description: pass/fail verdict for AT + - contextPath: FireEyeETP.Message.verdicts.PV + description: pass/fail verdict for PV + - contextPath: FireEyeETP.Message.id + description: Message ID. + description: Get the data of a specific message. + - name: fireeye-etp-get-alerts + arguments: + - name: legacy_id + description: Alert ID as shown in ETP Web Portal. + - name: from_last_modified_on + description: Datetime in yyy-mm-ddThh:mm:ss.fff format. Default last 90 days. + - name: etp_message_id + description: Email message id. + - name: size + description: Number of alerts intended in response. Default 20. Valid range + 1-100 . + outputs: + - contextPath: FireEyeETP.Alerts.meta.read + description: Email read flag. + - contextPath: FireEyeETP.Alerts.meta.last_modified_on + description: Last modified timestamp. + - contextPath: FireEyeETP.Alerts.meta.legacy_id + description: 'Alert ID as shown in ETP Web Portal ' + - contextPath: FireEyeETP.Alerts.alert.product + description: Product alerted + - contextPath: FireEyeETP.Alerts.alert.timestamp + description: Alert timestamp + - contextPath: FireEyeETP.Alerts.alert.malware_md5 + description: md5 of file attached + - contextPath: FireEyeETP.Alerts.email.status + description: The email status. + - contextPath: FireEyeETP.Alerts.email.source_ip + description: Email source IP. + - contextPath: FireEyeETP.Alerts.email.smtp.rcpt_to + description: Recipient SMTP. + - contextPath: FireEyeETP.Alerts.email.smtp.mail_from + description: Sender SMTP. + - contextPath: FireEyeETP.Alerts.email.etp_message_id + description: The message ID. + - contextPath: FireEyeETP.Alerts.email.headers.cc + description: Email 'cc' recipients. + - contextPath: FireEyeETP.Alerts.email.headers.to + description: Email recipients. + - contextPath: FireEyeETP.Alerts.email.headers.from + description: Email sender. + - contextPath: FireEyeETP.Alerts.email.headers.subject + description: Email subject. + - contextPath: FireEyeETP.Alerts.email.attachment + description: File name or URL pointing to file. + - contextPath: FireEyeETP.Alerts.email.timestamp.accepted + description: Email accepted time. + - contextPath: FireEyeETP.Alerts.id + description: The alert ID. + description: Get summary format information about the alerts. + - name: fireeye-etp-get-alert + arguments: + - name: alert_id + required: true + description: The alert ID. + outputs: + - contextPath: FireEyeETP.Alerts.meta.read + description: Email read flag. + - contextPath: FireEyeETP.Alerts.meta.last_modified_on + description: Last modified timestamp. + - contextPath: FireEyeETP.Alerts.meta.legacy_id + description: 'Alert ID as shown in ETP Web Portal ' + - contextPath: FireEyeETP.Alerts.meta.acknowledged + description: Acknowledged + - contextPath: FireEyeETP.Alerts.alert.product + description: Product generate the alert. + - contextPath: FireEyeETP.Alerts.alert.alert_type + description: Alert type code. + - contextPath: FireEyeETP.Alerts.alert.severity + description: Severity code. + - contextPath: FireEyeETP.Alerts.alert.explanation.analysis + description: Analysis + - contextPath: FireEyeETP.Alerts.alert.explanation.anomaly + description: Anomaly + - contextPath: FireEyeETP.Alerts.alert.explanation.malware_detected.malware.domain + description: Malware domain + - contextPath: FireEyeETP.Alerts.alert.explanation.malware_detected.malware.downloaded_at + description: Malware downloaded at timestamp + - contextPath: FireEyeETP.Alerts.alert.explanation.malware_detected.malware.executed_at + description: Malware executed at timestamp + - contextPath: FireEyeETP.Alerts.alert.explanation.malware_detected.malware.name + description: Malware name + - contextPath: FireEyeETP.Alerts.alert.explanation.malware_detected.malware.sid + description: Malware sid + - contextPath: FireEyeETP.Alerts.alert.explanation.malware_detected.malware.stype + description: Malware type + - contextPath: FireEyeETP.Alerts.alert.explanation.malware_detected.malware.submitted_at + description: Malware submitted at + - contextPath: FireEyeETP.Alerts.alert.explanation.protocol + description: Protocol + - contextPath: FireEyeETP.Alerts.alert.explanation.timestamp + description: Explanation timestamp + - contextPath: FireEyeETP.Alerts.alert.timestamp + description: Alert timestamp. + - contextPath: FireEyeETP.Alerts.alert.action + description: Alert acrion + - contextPath: FireEyeETP.Alerts.alert.name + description: Alert name. + - contextPath: FireEyeETP.Alerts.email.status + description: The email status. + - contextPath: FireEyeETP.Alerts.email.source_ip + description: Email source IP. + - contextPath: FireEyeETP.Alerts.email.smtp.rcpt_to + description: Recipient SMTP. + - contextPath: FireEyeETP.Alerts.email.smtp.mail_from + description: Sender SMTP. + - contextPath: FireEyeETP.Alerts.email.etp_message_id + description: FE ETP unique message ID. + - contextPath: FireEyeETP.Alerts.email.headers.cc + description: Email cc recipients. + - contextPath: FireEyeETP.Alerts.email.headers.to + description: Email recipients. + - contextPath: FireEyeETP.Alerts.email.headers.from + description: 'Email sender ' + - contextPath: FireEyeETP.Alerts.email.headers.subject + description: Email subject + - contextPath: FireEyeETP.Alerts.email.attachment + description: File name or URL pointing to file + - contextPath: FireEyeETP.Alerts.email.timestamp.accepted + description: Email eccepted time + - contextPath: FireEyeETP.Alerts.id + description: The alert unique ID + description: Detailed information from any particular alert. Alerts more than + 90 days old are not available. + isfetch: true + runonce: false