Detection rules › Sigma
Credential stuffing sttack risk
Detects potential credential stuffing attacks by monitoring failed logins and Auth0 Attack Protection feature events.
MITRE ATT&CK coverage
| Tactic | Techniques |
|---|---|
| Credential Access | T1110.004 Brute Force: Credential Stuffing |
Rule body yaml
title: Credential stuffing sttack risk
name: selected_events
id: e604e40e-9db6-449d-854d-2b5323644fd7
status: experimental
description: |
Detects potential credential stuffing attacks by monitoring failed logins and Auth0 Attack Protection feature events.
author: Okta
date: 2025-10-15
modified: 2025-10-15
references:
- https://auth0.com/docs/secure/attack-protection/view-attack-protection-events
logsource:
product: auth0
detection:
selection:
data.type:
- f # Failed login
- fu # Failed login: Invalid username or email
- fp # Failed login: Incorrect password
- pwd_leak # Attempt to login with a known breached password
- limit_wc # User blocked from logging in from a specific IP
- limit_sul # User blocked from logging in from all IPs
- limit_mu # IP address block from logging in
- fcoa # Failed cross-origin authentication
condition: selection
explanation: >
This rule identifies **credential stuffing** activity by analyzing patterns of **failed logins** (f, fu, fp, fcoa)
and **Auth0 Attack Protection** events (pwd_leak, limit_wc, limit_sul, limit_mu).
The accompanying Splunk query includes three distinct detection **Signals** over 1-hour windows:
**Signal 1** (High volume of failed/attack protection events from a single IP),
**Signal 2** (Significant surge in total failed/protection events),
and **Signal 3** (Anomalous spike in unique source IP addresses, indicating a botnet).
The query also incorporates **normality** calculations for comparison and collects JA3/JA4 TLS fingerprint data for
attack traffic clustering and investigation.
The Sigma correlation feature implements Signal 1 (count per IP), but lacks normality calculation.
splunk: |
index=auth0 data.tenant_name="{your-tenant-name}"
data.type IN (f, fu, fp, pwd_leak, limit_wc, limit_sul, limit_mu, fcoa)
``` Signal 1 - any single IP triggers excessive number of failed/attack protection events ```
| bin _time span=1h
| stats values(data.security_context.ja4) as ja4
count as cnt_events_per_ip by _time data.ip
| where cnt_events_per_ip > {threshold_events_per_ip}
``` Normality for Signal 1 - average number of successful logins per IP (per hour) ```
| join [
search index=auth0 data.type = s
| stats count AS successful_logins_per_ip by data.ip
| stats avg(successful_logins_per_ip) AS avg_successful_logins_per_ip
]
``` Signal 2 - surge in failed login or attack protection events ```
```
| stats values(data.security_context.ja4) as ja4
count as cnt_total_per_event by _time data.type
| where cnt_total_per_event > {threshold_count_per_event}```
``` Normality for Signal 2 - average number successful logins (per hour) ```
```
| join [
search index=auth0 data.type = s
| stats count AS successful_logins_per_s by data.type
| stats avg(successful_logins_per_s) AS avg_successful_logins_per_s
]```
``` Signal 3 - surge of observed IPs with failed events ```
```
| stats dc(data.ip) as cnt_total_ips values(data.ip) as ip
values(data.security_context.ja4) as ja4 by _time
| where cnt_total_ips > {threshold_total_ips}```
``` Normality for Signal 3 - average number of IPs with successful logins (per hour) ```
```| join [
search index=auth0 data.type = s
| stats dc(data.ip) AS successful_logins_ips by _time
| stats avg(successful_logins_ips) AS avg_successful_logins_ips
]```
comments:
- The Splunk query above shall be tuned to reflect a valid tenant name,
and one of the three thresholds (selected) - number of events per IP, i.e. {threshold_events_per_ip};
number of failed events in total, i.e. {threshold_count_per_event};
and total number of unique IPs, i.e .{threshold_total_ips}.
- The detection can be adjusted to monitor the attack protection feature in use.
- Failed login events (f, fu, fp, fcoa) could be monitored separately from Attack Protection events
(pwd_leak, limit_wc, limit_sul, limit_mu).
- If IP enrichment data is available, consider monitoring for traffic originating from unexpected locations
(e.g., anonymizing proxies, Tor exit nodes, irrelevant countries).
- Often the abnormal rates of failed events tend to happen without much change to the rate of successful logins.
tenant_logs: |
type: (f fu fp pwd_leak limit_wc limit_sul limit_mu fcoa)
prevention:
- Require MFA for password-based authentication flows
- Migrate to passwordless or passkeys as a preferred login method
- Use Bot Protection, Suspicious IP throttling, and Breached Password Protection, and Brute Force Protection
to present CAPTCHA challenges to requests from suspicious IPs
- Apply strong password policies (e.g. disallow common passwords)
- Use 3rd party Auth0 Actions, e.g. from Auth0 Marketplace, integrations to check if an IP is associated with an anonymizing proxies
- Deny access by location using Network ACL, WAF or via the Country-based Access Control post-login Actions
- Analyze if suspicious traffic (failed events) can be attributed to specific JA3/JA4 fingerprints
and block/monitor/redirect it using the Network ACL feature.
falsepositives:
- ja3/ja4 might be attributed to legitimate traffic
level: medium
tags:
- attack.credential-access
- attack.t1110.004
---
title: Credential stuffing sttack risk - correlated rule # This correlation implements Signal 1 from the Splunk query above. Adjust for Signal 2 or Signal 3 if needed.
correlation:
type: event_count
rules:
- selected_events # Referenced here
group-by:
- data.ip
timespan: 1h
condition:
gt: 1
Stages and Predicates
Stage 0: condition
selectionStage 1: selection
selection:
data.type:
- f
- fu
- fp
- pwd_leak
- limit_wc
- limit_sul
- limit_mu
- fcoa
Indicators
Each row is a field, operator, and value that the rule matches. The corpus column counts how many other rules in the catalog look for the same combination: high numbers point to widely-used, community-vetted indicators. Blank or 1 shows that the indicator is specific to this rule.
| Field | Kind | Values |
|---|---|---|
data.type | eq |
|