Firebase Security Rules · The Short Guide
Firebase Security Rules are the entire security boundary between your users and your database. Firestore and Storage each have their own rules file. The default `allow read, write: if true;` from the getting-started guide is the single biggest source of Firebase data leaks. Deny by default, then open specific paths gated on `request.auth` claims.
Common misconfigurations
- `allow read, write: if true;` · The getting-started snippet meant for local emulator testing. Search your `firestore.rules` for `if true` before every deploy.
- Test-mode Storage rules expiring · Firebase Storage rules default to allow-all for 30 days then flip to deny-all. Many teams miss both edges.
- Ownership check on write but not read · Common mistake · users can read everyone's docs but only write their own. Enforce ownership on both.
- Trusting client-provided `userId` field · Rules must compare against `request.auth.uid`, never against a field the client sets.
- Rules that don't fail closed · If no rule matches, Firestore denies. Good. Ensure you don't have a catch-all `if true` that overrides this.
Example
Deny-by-default Firestore rules for a user-owned collection
rules_version = '2';
service cloud.firestore {
match /databases/{database}/documents {
// Deny everything by default
match /{document=**} { allow read, write: if false; }
// Users can read/write their own notes
match /notes/{noteId} {
allow read: if request.auth != null
&& resource.data.ownerId == request.auth.uid;
allow create: if request.auth != null
&& request.resource.data.ownerId == request.auth.uid;
allow update, delete: if request.auth != null
&& resource.data.ownerId == request.auth.uid;
}
}
}
Frequently asked
How do I test Firebase rules?
Use the Firebase console's Rules Simulator, or run the Firebase Emulator locally with unit tests via `@firebase/rules-unit-testing`.
Are Firebase rules enough on their own?
For Firestore and Storage, yes · they are the security boundary. For Cloud Functions, you still need in-code auth checks.
What's the difference between `request.auth` and `resource.data`?
`request.auth` is the caller's identity. `resource.data` is the existing document. `request.resource.data` is the incoming write.
Scan for this issue →