description: Pipeline for parsing IIS error logs. Requires the geoip plugin.
processors:
- grok:
    field: message
    patterns:
    - '%{TIMESTAMP_ISO8601:iis.error.time} %{IPORHOST:source.address} %{NUMBER:source.port:long}
      %{IPORHOST:destination.address} %{IPORHOST:destination.port:long} (?:HTTP/%{NUMBER:http.version}|-)
      (?:%{WORD:http.request.method}|-) (?:-|%{NOTSPACE:url.original}) (?:%{NUMBER}|-)
      (?:%{NUMBER:http.response.status_code:long}|-) (?:%{NUMBER}|-) (?:-|%{NOTSPACE:iis.error.reason_phrase})
      (?:-|%{NOTSPACE:iis.error.queue_name})'
    - '%{TIMESTAMP_ISO8601:iis.error.time} %{IPORHOST:source.address} %{NUMBER:source.port:long}
      %{IPORHOST:destination.address} %{IPORHOST:destination.port:long} (?:HTTP/%{NUMBER:http.version}|-)
      (?:%{WORD:http.request.method}|-) (?:-|%{NOTSPACE:url.original}) (?:%{NUMBER:http.response.status_code:long}|-)
      (?:%{NUMBER}|-) (?:-|%{NOTSPACE:iis.error.reason_phrase}) (?:-|%{NOTSPACE:iis.error.queue_name})'
    ignore_missing: true
- remove:
    field: message
- rename:
    field: '@timestamp'
    target_field: event.created
- date:
    field: iis.error.time
    target_field: '@timestamp'
    formats:
    - yyyy-MM-dd HH:mm:ss
- remove:
    field: iis.error.time
- grok:
    field: destination.address
    patterns:
    - '%{NOZONEIP:destination.ip}'
    pattern_definitions:
      NOZONEIP: '[^%]*'
- grok:
    field: source.address
    patterns:
    - '%{NOZONEIP:source.ip}'
    pattern_definitions:
      NOZONEIP: '[^%]*'
- geoip:
    field: source.ip
    target_field: source.geo
    ignore_failure: true
- geoip:
    database_file: GeoLite2-ASN.mmdb
    field: source.ip
    target_field: source.as
    properties:
    - asn
    - organization_name
    ignore_missing: true
- rename:
    field: source.as.asn
    target_field: source.as.number
    ignore_missing: true
- rename:
    field: source.as.organization_name
    target_field: source.as.organization.name
    ignore_missing: true
- set:
    field: event.kind
    value: event
- append:
    field: event.category
    value: web
- append:
    field: event.category
    value: network
    if: "ctx?.source?.ip != null && ctx?.destination?.ip != null"
- append:
    field: event.type
    value: connection
    if: "ctx?.source?.ip != null && ctx?.destination?.ip != null"
- append:
    field: related.ip
    value: "{{source.ip}}"
    if: "ctx?.source?.ip != null"
- append:
    field: related.ip
    value: "{{destination.ip}}"
    if: "ctx?.destination?.ip != null"
- set:
    field: event.outcome
    value: success
    if: "ctx?.http?.response?.status_code != null && ctx.http.response.status_code < 400"
- set:
    field: event.outcome
    value: failure
    if: "ctx?.http?.response?.status_code != null && ctx.http.response.status_code >= 400"
on_failure:
- set:
    field: error.message
    value: '{{ _ingest.on_failure_message }}'
