Skip to content

ImadCreates/firewarden

Repository files navigation

Firewarden

npm version CI

Firewarden scanning a real firestore.rules file

Catch the open database rules that leak data in Firebase apps. Firewarden finds the insecure rule, writes the hardened version, and generates the emulator test that proves the fix.

Most data leaks in fast-built apps are not exotic. They are allow read, write: if true, one tenant reading another tenant's rows, and treating "logged in" as "allowed." Firewarden finds those before your users do.

Why

Row-level access misconfiguration is the single biggest source of data exposure in AI-built and fast-shipped apps. Existing scanners lean Supabase and stop at telling you something is wrong. Firewarden is Firestore-first, and it does the two things that actually save you time: it writes the corrected rule, and it writes the emulator test that fails on the old rule and passes on the new one. So you ship the fix with proof, not vibes.

Install

npm install -g firewarden

Use

firewarden scan ./firestore.rules

Real output, scanning Excalidraw's production firestore.rules:

firestore.rules — 1 finding

CRITICAL
  firestore.rules:5  RECURSIVE_WILDCARD_OPEN  /{document=**}
    This rule matches every document in the entire database via the recursive wildcard /{document=**} and grants blanket access. `if true` disables all access control.
    Suggested fix:
      // Firewarden suggestion, review before shipping
      // Lock the catch-all, then grant access per collection explicitly.
      match /{document=**} {
        allow read, write: if false;
      }

1 critical, 0 high, 0 medium, 0 low

Exit code is 1 when any finding is at or above --min-severity (default high), so CI fails on real problems and stays green on informational notes.

Formats and options

firewarden scan firestore.rules                        # pretty terminal report
firewarden scan firestore.rules --format json          # machine-readable Report
firewarden scan firestore.rules --format sarif         # GitHub code scanning
firewarden scan firestore.rules --min-severity critical
firewarden scan firestore.rules --write-tests          # emit emulator specs to firewarden-tests/

--write-tests writes one @firebase/rules-unit-testing (v3 API) spec per finding. Each spec fails against the vulnerable rule and passes once the rule is hardened:

firebase emulators:exec --only firestore 'npx vitest run firewarden-tests'

In CI

# .github/workflows/firewarden.yml
- run: npx firewarden scan firestore.rules --min-severity high

Or as a GitHub Action (validated end-to-end in this repo's CI):

- uses: ImadCreates/firewarden@v0.1.2
  with:
    rules: firestore.rules
    min-severity: high

Or with SARIF upload so findings annotate PRs inline:

- run: npx firewarden scan firestore.rules --format sarif > firewarden.sarif
  continue-on-error: true
- uses: github/codeql-action/upload-sarif@v3
  with:
    sarif_file: firewarden.sarif

What it checks

Detector Severity Fires on
OPEN_ACCESS critical allow read, write that is provably unconditional (if true, no condition, or a constant tautology like 1 == 1 or true || x)
PUBLIC_WRITE critical Unconditional write/create/update/delete — an open write is almost always a bug
RECURSIVE_WILDCARD_OPEN critical / medium An open allow inside match /{document=**} — critical when writes are open, medium when read-only
MISSING_TENANCY high A condition that never references the path id, an owner check, or a tenant field — one customer can read another's rows
AUTH_ONLY_NOT_AUTHZ medium Exactly request.auth != null on per-user data — authenticated is not authorized
UNVALIDATED_WRITE medium Updates scoped only by mutable document state (resource.data.orgId == ...) with no constraint on the incoming data — a writer can reassign the very field that scopes access
PUBLIC_READ low Unconditional read in a block that also accepts client writes

Precision over noise

Calibrated against real production rules files (Excalidraw, Japan's COVID-19 contact-tracing backend, Reach4Help, CustomerDB, GDG Hoverboard — all captured as regression fixtures in fixtures/realworld/):

  • Unconditional write is a bug signal; unconditional read is commonly intentional. Public reads are suppressed entirely when writes in the same block are locked (if false or absent) — that is the deliberate-public-content pattern used by every content site.
  • Firewarden never guesses. Conditions are judged by a constant evaluator: only expressions built from literals can be "provably open," and anything referencing runtime state — or calling a function whose body it cannot see — is left alone.
  • One finding per root cause. An open read, write on a wildcard is one critical finding, not three overlapping ones.

Roadmap

  • Supabase RLS scanning (tables without RLS, USING (true), service-role exposure)
  • Live probe mode (confirm exposure with the anon key)
  • Auto-fix PRs

License

MIT © Imaduddin Ahmed. Contributions welcome.

About

Scan Firebase Firestore security rules for the misconfigurations that leak data. Finds the insecure rule, writes the hardened fix, and generates the emulator test that proves it.

Topics

Resources

License

Stars

1 star

Watchers

0 watching

Forks

Packages

 
 
 

Contributors