feat(harfanglab): exhaustive alert OCSF mappers (get_alerts + upgraded get_security_events)
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,71 @@
|
|||||||
|
name: "HarfangLab Alerts → OCSF"
|
||||||
|
description: "Maps a HarfangLab EDR alert (/api/data/alert/alert/Alert/, results_path = results) to OCSF. The matched process is the actor (actor.*). Detail sub-objects are only present for their event kind; absent paths are skipped at ingestion."
|
||||||
|
field_mappings:
|
||||||
|
title: "rule_name"
|
||||||
|
severity: "level = 'critical' ? 5 : (level = 'high' ? 4 : (level = 'medium' ? 3 : 2))"
|
||||||
|
description: "alert_type"
|
||||||
|
# results_path = results; source_path is JSONata over ONE alert object.
|
||||||
|
# Paths absent from a given alert are skipped at ingestion, so extra entries are safe.
|
||||||
|
ocsf:
|
||||||
|
# ── Endpoint ──────────────────────────────────────────────────────
|
||||||
|
- { source_path: "agent.hostname", ocsf_field: "src_endpoint.hostname" }
|
||||||
|
- { source_path: "agent.domainname", ocsf_field: "src_endpoint.domain" }
|
||||||
|
- { source_path: "agent.osproducttype", ocsf_field: "src_endpoint.os.name" }
|
||||||
|
- { source_path: "agent.ostype", ocsf_field: "src_endpoint.os.type" }
|
||||||
|
- { source_path: "agent.osversion", ocsf_field: "device.os.version" }
|
||||||
|
- { source_path: "agent.agentid", ocsf_field: "device.uid" }
|
||||||
|
# ── Finding ───────────────────────────────────────────────────────
|
||||||
|
- { source_path: "id", ocsf_field: "finding_info.uid" }
|
||||||
|
- { source_path: "alert_unique_id", ocsf_field: "metadata.uid" }
|
||||||
|
- { source_path: "rule_name", ocsf_field: "finding_info.title" }
|
||||||
|
- { source_path: "msg", ocsf_field: "finding_info.desc" }
|
||||||
|
- { source_path: "alert_time", ocsf_field: "finding_info.created_time" }
|
||||||
|
- { source_path: "detection_date", ocsf_field: "finding_info.first_seen_time" }
|
||||||
|
- { source_path: "last_update", ocsf_field: "finding_info.modified_time" }
|
||||||
|
- { source_path: "ingestion_date", ocsf_field: "metadata.logged_time" }
|
||||||
|
- { source_path: "alert_type", ocsf_field: "finding_info.analytic.type" }
|
||||||
|
- { source_path: "rule_id", ocsf_field: "finding_info.analytic.uid" }
|
||||||
|
- { source_path: "rule_content", ocsf_field: "finding_info.analytic.desc" }
|
||||||
|
- { source_path: "detection_origin", ocsf_field: "finding_info.analytic.category" }
|
||||||
|
- { source_path: "status", ocsf_field: "status" }
|
||||||
|
- { source_path: "maturity", ocsf_field: "status_detail" }
|
||||||
|
- { source_path: "score", ocsf_field: "risk_score" }
|
||||||
|
- { source_path: "confidence_int", ocsf_field: "confidence_score" }
|
||||||
|
- { source_path: "threat_key", ocsf_field: "finding_info.uid_alt" } # threat aggregation key
|
||||||
|
- { source_path: "mitre_cells", ocsf_field: "attacks" } # ["TAxxxx:Tyyyy", ...] best-effort
|
||||||
|
- { source_path: "tags", ocsf_field: "metadata.labels" }
|
||||||
|
- { source_path: "log_type", ocsf_field: "metadata.log_name" }
|
||||||
|
# ── Matched process — the actor ───────────────────────────────────
|
||||||
|
- { source_path: "process.process_name", ocsf_field: "actor.process.name" }
|
||||||
|
- { source_path: "process.image_name", ocsf_field: "actor.process.file.path" }
|
||||||
|
- { source_path: "process.commandline", ocsf_field: "actor.process.cmd_line" }
|
||||||
|
- { source_path: "process.username", ocsf_field: "actor.user.name" }
|
||||||
|
- { source_path: "process.integrity_level", ocsf_field: "actor.process.integrity" }
|
||||||
|
- { source_path: "process.pid", ocsf_field: "actor.process.pid" }
|
||||||
|
- { source_path: "process.hashes.sha256", ocsf_field: "actor.process.file.hashes.sha256" }
|
||||||
|
- { source_path: "process.hashes.sha1", ocsf_field: "actor.process.file.hashes.sha1" }
|
||||||
|
- { source_path: "process.hashes.md5", ocsf_field: "actor.process.file.hashes.md5" }
|
||||||
|
- { source_path: "process.parent_image", ocsf_field: "actor.process.parent_process.name" }
|
||||||
|
- { source_path: "process.parent_commandline", ocsf_field: "actor.process.parent_process.cmd_line" }
|
||||||
|
# ── Event details: network connection ─────────────────────────────
|
||||||
|
- { source_path: "details_connection.SourceIp", ocsf_field: "src_endpoint.ip" }
|
||||||
|
- { source_path: "details_connection.SourcePort", ocsf_field: "src_endpoint.port" }
|
||||||
|
- { source_path: "details_connection.DestinationIp", ocsf_field: "dst_endpoint.ip" }
|
||||||
|
- { source_path: "details_connection.DestinationPort", ocsf_field: "dst_endpoint.port" }
|
||||||
|
- { source_path: "details_connection.Protocol", ocsf_field: "connection_info.protocol_name" }
|
||||||
|
# ── Event details: DNS ────────────────────────────────────────────
|
||||||
|
- { source_path: "details_dns_resolution.requested_name", ocsf_field: "query.hostname" }
|
||||||
|
- { source_path: "details_dns_resolution.query_type", ocsf_field: "query.type" }
|
||||||
|
# ── Event details: file ───────────────────────────────────────────
|
||||||
|
- { source_path: "details_file.target_filename", ocsf_field: "file.path" }
|
||||||
|
# ── Event details: registry ───────────────────────────────────────
|
||||||
|
- { source_path: "details_registry.target_object", ocsf_field: "reg_key.path" }
|
||||||
|
- { source_path: "details_registry.registry_value_type", ocsf_field: "reg_value.type" }
|
||||||
|
- { source_path: "details_registry.data_string_added", ocsf_field: "reg_value.data" }
|
||||||
|
# ── Event details: URL request ────────────────────────────────────
|
||||||
|
- { source_path: "details_url_request.url", ocsf_field: "url.url_string" }
|
||||||
|
- { source_path: "details_url_request.host", ocsf_field: "url.hostname" }
|
||||||
|
- { source_path: "details_url_request.user_agent", ocsf_field: "http_request.user_agent" }
|
||||||
|
- { source_path: "details_url_request.verb", ocsf_field: "http_request.http_method" }
|
||||||
|
# Alert fields deliberately left unmapped: `username` (actor.user.name is taken by the
|
||||||
|
# more specific process.username), remaining details_* sub-objects (no clean OCSF home).
|
||||||
@@ -16,12 +16,25 @@ ocsf:
|
|||||||
- { source_path: "agent.agentid", ocsf_field: "device.uid" }
|
- { source_path: "agent.agentid", ocsf_field: "device.uid" }
|
||||||
# ── Finding ───────────────────────────────────────────────────────
|
# ── Finding ───────────────────────────────────────────────────────
|
||||||
- { source_path: "id", ocsf_field: "finding_info.uid" }
|
- { source_path: "id", ocsf_field: "finding_info.uid" }
|
||||||
|
- { source_path: "alert_unique_id", ocsf_field: "metadata.uid" }
|
||||||
- { source_path: "rule_name", ocsf_field: "finding_info.title" }
|
- { source_path: "rule_name", ocsf_field: "finding_info.title" }
|
||||||
|
- { source_path: "msg", ocsf_field: "finding_info.desc" }
|
||||||
- { source_path: "alert_time", ocsf_field: "finding_info.created_time" }
|
- { source_path: "alert_time", ocsf_field: "finding_info.created_time" }
|
||||||
|
- { source_path: "detection_date", ocsf_field: "finding_info.first_seen_time" }
|
||||||
- { source_path: "last_update", ocsf_field: "finding_info.modified_time" }
|
- { source_path: "last_update", ocsf_field: "finding_info.modified_time" }
|
||||||
|
- { source_path: "ingestion_date", ocsf_field: "metadata.logged_time" }
|
||||||
- { source_path: "alert_type", ocsf_field: "finding_info.analytic.type" }
|
- { source_path: "alert_type", ocsf_field: "finding_info.analytic.type" }
|
||||||
|
- { source_path: "rule_id", ocsf_field: "finding_info.analytic.uid" }
|
||||||
|
- { source_path: "rule_content", ocsf_field: "finding_info.analytic.desc" }
|
||||||
|
- { source_path: "detection_origin", ocsf_field: "finding_info.analytic.category" }
|
||||||
- { source_path: "status", ocsf_field: "status" }
|
- { source_path: "status", ocsf_field: "status" }
|
||||||
- { source_path: "maturity", ocsf_field: "status_detail" }
|
- { source_path: "maturity", ocsf_field: "status_detail" }
|
||||||
|
- { source_path: "score", ocsf_field: "risk_score" }
|
||||||
|
- { source_path: "confidence_int", ocsf_field: "confidence_score" }
|
||||||
|
- { source_path: "threat_key", ocsf_field: "finding_info.uid_alt" } # threat aggregation key
|
||||||
|
- { source_path: "mitre_cells", ocsf_field: "attacks" } # ["TAxxxx:Tyyyy", ...] best-effort
|
||||||
|
- { source_path: "tags", ocsf_field: "metadata.labels" }
|
||||||
|
- { source_path: "log_type", ocsf_field: "metadata.log_name" }
|
||||||
# ── Matched process — the actor ───────────────────────────────────
|
# ── Matched process — the actor ───────────────────────────────────
|
||||||
- { source_path: "process.process_name", ocsf_field: "actor.process.name" }
|
- { source_path: "process.process_name", ocsf_field: "actor.process.name" }
|
||||||
- { source_path: "process.image_name", ocsf_field: "actor.process.file.path" }
|
- { source_path: "process.image_name", ocsf_field: "actor.process.file.path" }
|
||||||
@@ -34,3 +47,25 @@ ocsf:
|
|||||||
- { source_path: "process.hashes.md5", ocsf_field: "actor.process.file.hashes.md5" }
|
- { source_path: "process.hashes.md5", ocsf_field: "actor.process.file.hashes.md5" }
|
||||||
- { source_path: "process.parent_image", ocsf_field: "actor.process.parent_process.name" }
|
- { source_path: "process.parent_image", ocsf_field: "actor.process.parent_process.name" }
|
||||||
- { source_path: "process.parent_commandline", ocsf_field: "actor.process.parent_process.cmd_line" }
|
- { source_path: "process.parent_commandline", ocsf_field: "actor.process.parent_process.cmd_line" }
|
||||||
|
# ── Event details: network connection ─────────────────────────────
|
||||||
|
- { source_path: "details_connection.SourceIp", ocsf_field: "src_endpoint.ip" }
|
||||||
|
- { source_path: "details_connection.SourcePort", ocsf_field: "src_endpoint.port" }
|
||||||
|
- { source_path: "details_connection.DestinationIp", ocsf_field: "dst_endpoint.ip" }
|
||||||
|
- { source_path: "details_connection.DestinationPort", ocsf_field: "dst_endpoint.port" }
|
||||||
|
- { source_path: "details_connection.Protocol", ocsf_field: "connection_info.protocol_name" }
|
||||||
|
# ── Event details: DNS ────────────────────────────────────────────
|
||||||
|
- { source_path: "details_dns_resolution.requested_name", ocsf_field: "query.hostname" }
|
||||||
|
- { source_path: "details_dns_resolution.query_type", ocsf_field: "query.type" }
|
||||||
|
# ── Event details: file ───────────────────────────────────────────
|
||||||
|
- { source_path: "details_file.target_filename", ocsf_field: "file.path" }
|
||||||
|
# ── Event details: registry ───────────────────────────────────────
|
||||||
|
- { source_path: "details_registry.target_object", ocsf_field: "reg_key.path" }
|
||||||
|
- { source_path: "details_registry.registry_value_type", ocsf_field: "reg_value.type" }
|
||||||
|
- { source_path: "details_registry.data_string_added", ocsf_field: "reg_value.data" }
|
||||||
|
# ── Event details: URL request ────────────────────────────────────
|
||||||
|
- { source_path: "details_url_request.url", ocsf_field: "url.url_string" }
|
||||||
|
- { source_path: "details_url_request.host", ocsf_field: "url.hostname" }
|
||||||
|
- { source_path: "details_url_request.user_agent", ocsf_field: "http_request.user_agent" }
|
||||||
|
- { source_path: "details_url_request.verb", ocsf_field: "http_request.http_method" }
|
||||||
|
# Alert fields deliberately left unmapped: `username` (actor.user.name is taken by the
|
||||||
|
# more specific process.username), remaining details_* sub-objects (no clean OCSF home).
|
||||||
|
|||||||
Reference in New Issue
Block a user