Gatekeeper inqaba-security/gatekeeper
v1.x

Events & Schema

Every signal Gatekeeper collects becomes a SecurityEvent, serialized to an Elastic Common Schema (ECS) 8.x JSON document. ECS is the wire format for all sinks: Wazuh ingests it natively as JSON, it maps cleanly onto Microsoft Sentinel custom tables, and analysts get the same field names everywhere.

Anatomy of an event#

{
    "@timestamp": "2026-07-11T09:14:23.187Z",
    "ecs": { "version": "8.11.0" },
    "event": {
        "id": "9c2f6f0a-6f4e-4d0b-9c1e-1c1a2b3c4d5e",
        "kind": "event",
        "module": "gatekeeper",
        "dataset": "gatekeeper.security",
        "category": ["intrusion_detection", "threat"],
        "type": ["info"],
        "action": "honeypot_route_hit",
        "outcome": "failure",
        "severity": 7
    },
    "message": "Honeypot route accessed",
    "service": { "name": "shop", "environment": "production" },
    "host": { "name": "web-01" },
    "source": {
        "ip": "203.0.113.9",
        "geo": {
            "country_iso_code": "NO",
            "city_name": "Oslo",
            "location": { "lat": 59.91, "lon": 10.75 }
        }
    },
    "user_agent": { "original": "Mozilla/5.0 (compatible; scanner)" },
    "url": { "path": "/wp-login.php", "full": "https://shop.example/wp-login.php" },
    "http": { "request": { "method": "GET" } },
    "threat": {
        "framework": "MITRE ATT&CK",
        "tactic": { "id": ["TA0043"], "name": ["Reconnaissance"] },
        "technique": { "id": ["T1595.003"], "name": ["Active Scanning: Wordlist Scanning"] }
    },
    "labels": { "siem_event_type": "honeypot_route_hit", "siem_severity": "high" },
    "laravel": {
        "context": { "honeypot_path": "wp-login.php", "auto_blocked": true }
    }
}

Key field groups:

Fields Purpose
event.* What happened: action, category, outcome, numeric severity, unique ID
source.ip, source.geo.* Who did it and from where (geo added by GeoIP enrichment)
user.id, user.name The authenticated user involved, if any
url.*, http.request.method, user_agent.original The request being made
threat.* MITRE ATT&CK mapping for the behaviour
service.*, host.name Which app/environment/host emitted it
laravel.context Event-specific detail (thresholds crossed, probed IDs, trigger reasons, your custom context)

Severity levels#

Gatekeeper uses six levels, mapped onto each destination's convention:

Severity ECS event.severity CEF Syslog
debug 1 0 7
info 2 2 6
low 3 4 5
medium 5 6 4
high 7 8 3
critical 9 10 2

Two severity filters exist:

  • events.minimum_severity (SIEM_MIN_SEVERITY) — global floor; events below it are dropped before shipping.
  • Per-sink minimum_severity — e.g. Slack defaults to high, so the channel only receives pageable alerts while the full stream flows to the SIEM.

Event catalog#

event.action Severity MITRE Source
login_succeeded info T1078 Valid Accounts auth listener
login_failed low T1110 Brute Force auth listener
logout info auth listener
user_registered info auth listener
password_reset_requested low auth listener
password_reset low auth listener
auth_lockout high T1110 Brute Force auth listener
email_verified info auth listener
access_denied medium your code (EventType::AccessDenied)
honeypot_route_hit high T1595.003 Wordlist Scanning honeypot routes
honeypot_form_triggered medium siem.honeypot middleware
brute_force_detected critical T1110 Brute Force siem.abuse middleware
scanning_detected high T1595.003 Wordlist Scanning siem.abuse middleware
rate_limit_abuse medium T1595 Active Scanning siem.abuse middleware
endpoint_abuse high T1595 Active Scanning siem.abuse middleware
suspicious_input high T1190 Exploit Public-Facing App siem.scan middleware
resource_enumeration_detected high T1119 Automated Collection siem.enum middleware
blocked_ip_attempt low siem.block middleware
ip_blocked medium blocklist
egress_new_destination medium T1071 Application Layer Protocol egress monitoring
egress_spike_detected high T1496 Resource Hijacking egress monitoring
egress_limit_exceeded high T1496 Resource Hijacking egress monitoring
egress_error_spike medium T1499 Endpoint DoS egress monitoring
anything your choice Siem::log() / Siem::event()

Authentication monitoring#

Gatekeeper subscribes to Laravel's native auth events automatically — no code changes needed. Whatever fires Illuminate\Auth\Events\* (the standard guards, Fortify, Breeze, Jetstream) is covered:

Laravel event Gatekeeper event
Login login_succeeded (guard + remember flag in context)
Failed login_failed (attempted identifier in context; password never captured)
Logout logout
Registered user_registered
PasswordReset password_reset
Lockout auth_lockout
Verified email_verified

Each is individually toggleable under events.authentication, and the whole subscriber can be disabled with SIEM_EVENTS_AUTH=false.

Event flow#

  1. A monitor (listener, middleware, honeypot, or your code) builds a SecurityEvent.
  2. The manager applies the global severity floor, scrubs context through the redactor, and serializes to ECS.
  3. For each active sink that accepts the event's severity, a ShipEvent job is dispatched to the siem queue.
  4. On the worker, the document is GeoIP-enriched and handed to the sink. Failures retry 3 times with backoff (5s / 30s / 120s), then fall back to the local Laravel log with the full event attached.