Install any skill in seconds. Free to start, no credit card required.
Get Started Free →Perform systematic alert triage in Elastic Security SIEM to rapidly classify, prioritize, and investigate security alerts for SOC operations.
.claude/skills/performing-alert-triage-with-elastic-siem/SKILL.md| Test case | Without → With | Effect | Δ tokens | Δ turns |
|---|---|---|---|---|
| case-18 | ✗→✓ | ▲ Improved | — | — |
| case-02 | ✗→✓ | ▲ Improved | — | — |
| case-10 | ✗→✓ | ▲ Improved | — | — |
| case-09 | ✗→✓ | ▲ Improved | — | — |
| case-17 | ✗→✓ | ▲ Improved | — | — |
Alert triage in Elastic Security is the systematic process of reviewing, classifying, and prioritizing security alerts to determine which represent genuine threats. Elastic's AI-driven Attack Discovery feature can triage hundreds of alerts down to discrete attack chains, but skilled analyst triage remains essential. A structured triage workflow typically takes 5-10 minutes per alert cluster using Elastic's built-in tools.
When viewing an alert in Elastic Security, review the alert details panel:
Alert Details Panel:
- Rule Name and Description
- Severity and Risk Score
- MITRE ATT&CK Mapping
- Host and User Context
- Process Tree (for endpoint alerts)
- Timeline of related events| Field | Purpose | ECS Field | |---|---|---| | Rule severity | Initial priority assessment | kibana.alert.severity | | Risk score | Quantified threat level | kibana.alert.risk_score | | Host name | Affected system | host.name | | User name | Affected identity | user.name | | Process name | Executing process | process.name | | Source IP | Origin of activity | source.ip | | Destination IP | Target of activity | destination.ip | | MITRE tactic | Attack stage | threat.tactic.name |
esqlFROM logs-endpoint.events.* | WHERE host.name == "affected-host" AND @timestamp > NOW() - 1 HOUR | STATS count = COUNT(*) BY event.category, event.action | SORT count DESC
esqlFROM logs-* | WHERE user.name == "suspicious-user" AND @timestamp > NOW() - 24 HOURS | STATS count = COUNT(*), unique_hosts = COUNT_DISTINCT(host.name) BY event.category | SORT count DESC
esqlFROM .alerts-security.alerts-default | WHERE source.ip == "10.0.0.50" AND @timestamp > NOW() - 24 HOURS | STATS alert_count = COUNT(*) BY kibana.alert.rule.name, kibana.alert.severity | SORT alert_count DESC
esqlFROM logs-system.auth-* | WHERE source.ip == "10.0.0.50" AND event.outcome == "success" | STATS login_count = COUNT(*), hosts = COUNT_DISTINCT(host.name) BY user.name | WHERE hosts > 3
Check indicators against threat intelligence:
esqlFROM logs-ti_* | WHERE threat.indicator.ip == "203.0.113.50" | KEEP threat.indicator.type, threat.indicator.provider, threat.indicator.confidence, threat.feed.name
esqlFROM logs-endpoint.events.file-* | WHERE file.hash.sha256 == "abc123..." | STATS occurrences = COUNT(*) BY host.name, file.path, user.name
| Classification | Criteria | Action | |---|---|---| | True Positive | Confirmed malicious activity | Escalate to incident, begin containment | | Benign True Positive | Expected behavior matching rule | Document in alert notes, acknowledge | | False Positive | Rule triggered on benign activity | Mark as false positive, create tuning task | | Needs Investigation | Insufficient data for determination | Assign for deeper investigation |
For each triaged alert, document:
Elastic Security includes 1000+ pre-built detection rules organized by:
json{ "name": "Multiple Failed Logins Followed by Success", "type": "threshold", "query": "event.category:authentication AND event.outcome:failure", "threshold": { "field": ["source.ip", "user.name"], "value": 5, "cardinality": [ { "field": "user.name", "value": 3 } ] }, "severity": "high", "risk_score": 73, "threat": [ { "framework": "MITRE ATT&CK", "tactic": { "id": "TA0006", "name": "Credential Access" }, "technique": [ { "id": "T1110", "name": "Brute Force" } ] } ] }
Elastic's Attack Discovery automatically:
| Risk Score | Severity | Asset Criticality | Response SLA | |---|---|---|---| | 90-100 | Critical | High | 15 minutes | | 70-89 | High | High | 30 minutes | | 70-89 | High | Medium | 1 hour | | 50-69 | Medium | Any | 4 hours | | 21-49 | Low | Any | 8 hours | | 1-20 | Informational | Any | 24 hours |
| Metric | Target | Measurement | |---|---|---| | Mean Time to Triage (MTTT) | < 10 minutes | Time from alert creation to classification | | False Positive Rate | < 30% | False positives / total alerts | | Escalation Rate | 10-20% | Escalated alerts / total alerts | | Alert Coverage | > 80% | Triaged alerts / generated alerts per shift | | Reclassification Rate | < 5% | Changed classifications / total classified |
| Case | Status | Duration (ms) | Turns | Tokens | Tool calls | ||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| Without | With | Δ | Without | With | Δ | Without | With | Δ | Without | With | Δ | ||
case-18 | fail→pass | — | — | — | — | — | — | — | — | — | — | — | — |
case-02 | fail→pass | — | — | — | — | — | — | — | — | — | — | — | — |
case-01 | fail→fail | — | — | — | — | — | — | — | — | — | — | — | — |
case-12 | fail→fail | — | — | — | — | — | — | — | — | — | — | — | — |
case-16 | pass→pass | — | — | — | — | — | — | — | — | — | — | — | — |
case-10 | fail→pass | — | — | — | — | — | — | — | — | — | — | — | — |
case-09 | fail→pass | — | — | — | — | — | — | — | — | — | — | — | — |
case-04 | fail→fail | — | — | — | — | — | — | — | — | — | — | — | — |
case-05 | fail→fail | — | — | — | — | — | — | — | — | — | — | — | — |
case-17 | fail→pass | — | — | — | — | — | — | — | — | — | — | — | — |
case-11 | fail→fail | — | — | — | — | — | — | — | — | — | — | — | — |
case-13 | fail→fail | — | — | — | — | — | — | — | — | — | — | — | — |
case-07 | fail→pass | — | — | — | — | — | — | — | — | — | — | — | — |
case-14 | fail→fail | — | — | — | — | — | — | — | — | — | — | — | — |
case-22 | fail→pass | — | — | — | — | — | — | — | — | — | — | — | — |
case-21 | pass→pass | — | — | — | — | — | — | — | — | — | — | — | — |
case-03 | fail→fail | — | — | — | — | — | — | — | — | — | — | — | — |
case-23 | fail→pass | — | — | — | — | — | — | — | — | — | — | — | — |
case-06 | fail→fail | — | — | — | — | — | — | — | — | — | — | — | — |
case-08 | fail→pass | — | — | — | — | — | — | — | — | — | — | — | — |
case-15 | fail→fail | — | — | — | — | — | — | — | — | — | — | — | — |
case-19 | fail→fail | — | — | — | — | — | — | — | — | — | — | — | — |
case-20 | fail→pass | — | — | — | — | — | — | — | — | — | — | — | — |
DecimalAI ran this skill against gemini-3.6-flash twice over the same eval suite — once with the skill loaded and once without — and compared the two runs case by case. 23 cases were attempted. The headline lift of +43 percentage points is the difference between those two pass rates over the 23 comparable cases. 1 case got worse with the skill loaded, and it is included in that figure.
The per-case answers from this run were removed by the retention sweep, so the case table below shows the verdicts without the text either arm produced. The counts above were recorded at the time and are unaffected. Answers are now kept for 180 days.
Other measured skills in the registry, with their headline benchmark lift.