1. Fundamentals of Firestore Security Rules
Every incoming read, create, update, or delete request must satisfy granular boolean conditions based on user authentication tokens (request.auth) and document schemas (request.resource.data):
rules_version = '2';
service cloud.firestore {
match /databases/{database}/documents {
// Helper function to check authenticated user
function isAuthenticated() {
return request.auth != null;
}
// Helper function to verify owner
function isOwner(userId) {
return isAuthenticated() && request.auth.uid == userId;
}
match /users/{userId} {
allow read: if isAuthenticated();
allow write: if isOwner(userId);
}
}
}
2. Role-Based Access Control (RBAC) with Custom Claims
Avoid querying database collections inside rules to verify admin roles, which consumes extra billable reads. Instead, assign Firebase Auth Custom Claims on the backend (e.g. request.auth.token.role == 'admin') for zero-latency, zero-cost authorization.
3. Firebase Storage File Protection
Restrict image and document uploads by verifying MIME types and enforcing maximum file size boundaries (e.g., maximum 5MB for user profile photos):
match /b/{bucket}/o {
match /avatars/{userId}/{fileName} {
allow write: if request.auth.uid == userId
&& request.resource.size < 5 * 1024 * 1024
&& request.resource.contentType.matches('image/(jpeg|png|webp)');
}
}
4. Automated Security Testing with Firebase Emulator Suite
Write automated unit test suites using the @firebase/rules-unit-testing package to simulate unauthorized attacks and verify rule logic before CI/CD deployment.