The attack lab: proving what the edge blocks — on your own zone


Describing a WAF is cheap; showing it is better. The Lumina demo has an admin-gated /attack-demo page whose entire job is to launch real attacks against the demo’s own public endpoints — from a real browser — and render exactly what came back: status, key headers, body preview, classified as edge block / app block / pass-through.

The story

The design insight: attack traffic must come from a real browser session, not curl. Cloudflare’s bot protection treats scripted clients differently, so a curl-based “proof” proves nothing. Firing from the page means real user-agent, real cookies, real WAF evaluation — and whatever happens next is the unedited truth. The page is admin-gated so public visitors can’t exhaust the demo’s rate-limit budget mid-demo.

The rules behind the lab are dashboard-configured custom WAF rules on the zone: scanner-probe, SQLi, XSS and path-traversal patterns; a geo-teaching rule (blocks KP/SY — the teaching card calls /api/geo, which reports what request.cf.country says about your visit); the compromised-credential rule on /api/auth/login (previous post); and a rate-limiting rule on checkout.

What the demo shows

The five attack cards. Each fires a real request:

  • Scanner probe — an /admin.config.php-shaped probe → edge block page (🛡️)
  • SQL injection — a classic ' OR 1=1 -- payload against a search endpoint → 🛡️
  • XSS — a <script> payload → 🛡️
  • Path traversal — ../../etc/passwd → 🛡️
  • Credential stuffing run — five sequential sign-ins with four breached password pairs (no Turnstile token) + the valid roster password as the fifth: 🛡️ ×4 at the edge, then the valid pair passes the edge and is stopped by the app layer only. The rule blocks exactly the leaked passwords — nothing else.

The rate-limit card fires a burst: the first requests get the app’s JSON 403, then the edge rate-limiting rule kicks in mid-burst and the responses flip to edge 429s — the app-protects-first, edge-mops-up pattern visible in one run.

Flip a rule, re-run. Toggle the leaked-credentials rule off in the dashboard → the five pairs now reach the app (⚙️ JSON 401s after real siteverify spend). Flip it back → edge blocks again. Same attacks, two control layers, no code change.

The DDoS simulation. A separate, zero-dependency flood script (scripts/ddos-sim.mjs) sends marker-tagged traffic (?blockme=…) mixed with a clean baseline against the zone you own. With an HTTP DDoS override rule enabled (Security → DDoS → Overrides, matching the marker), the marker traffic flips to edge 403 with a cf-mitigated: block header while the clean baseline stays 200; the verdict prints in the terminal and the event lands in Security → Events (service ddosL7). Safety gates: hostname confirmation prompt, hard request/duration caps, tagged User-Agents for log filtering, graceful Ctrl+C — and the runbook says plainly: run only against zones you own, with WARP disconnected first so the flood actually leaves your machine.

warp-cli disconnect
node scripts/ddos-sim.mjs      # prompts for hostname; ~300 rps × 3 min default
warp-cli connect

The teaching point the lab makes honest: the DDoS managed ruleset fires on volume — the lab’s single flood-card probe and ×20 burst pass by design, while hundreds of requests per second tip it over.

Evidence: what to capture

  • /attack-demo (signed in) with all cards visible → 13-attack-demo.png
  • Scanner / SQLi / XSS / traversal cards showing 🛡️ edge blocks → 13-edge-blocks.png
  • The credential-stuffing run: 🛡️ ×4 + ⚙️ ×1 → 13-stuffing-run.png
  • Rule-off contrast: all five pairs reaching the app → 13-stuffing-rule-off.png
  • Rate-limit burst showing app 403 → edge 429 flip → 13-rate-limit-flip.png
  • Geo teaching card showing your country + the KP/SY rule → 13-geo-card.png
  • Security → Events showing the block entries (rule IDs visible) → 13-security-events.png
  • DDoS run: terminal verdict MITIGATED + the cf-mitigated: block marker vs clean 200 → 13-ddos-verdict.png
  • Security → DDoS → Overrides showing the marker rule → 13-ddos-override.png

Key takeaways

  • Attack demos must run from real browsers — scripted curl is filtered before the WAF ever judges your payload.
  • Layered rules tell layered stories: edge blocks are free; app blocks cost CPU. Show both.
  • A credential rule’s precision (blocks exactly the leaked passwords) is more convincing than any feature list.
  • DDoS protection is volume-based; simulate responsibly on zones you own, with caps and tagged traffic.