Cloud Firestore Security Rules umożliwiają kontrolowanie dostępu do dokumentów i kolekcji w bazie danych. Elastyczna składnia reguł umożliwia tworzenie reguł pasujących do dowolnych elementów, od wszystkich zapisów w całej bazie danych po operacje na konkretnym dokumencie.
W tym przewodniku opisujemy podstawową składnię i strukturę reguł zabezpieczeń. Połącz tę składnię z warunkami reguł zabezpieczeń, aby utworzyć kompletne zestawy reguł.
Deklaracja dotycząca usługi i bazy danych
Cloud Firestore Security Rules zawsze zaczynaj od tego oświadczenia:
service cloud.firestore {
// The {database} wildcard allows the rules to reference any database,
// but these rules are only active on databases where they are explicitly deployed.
match /databases/{database}/documents {
// ...
}
}Deklaracja service cloud.firestore ogranicza zakres reguł do Cloud Firestore, co zapobiega konfliktom między Cloud Firestore Security Rules a regułami innych usług, takich jak Cloud Storage.
Deklaracja match /databases/{database}/documents określa, że reguły powinny pasować do dowolnej bazy danych Cloud Firestore w projekcie. Projekt może zawierać maksymalnie 100 baz danych, ale tylko pierwsza utworzona baza danych jest oznaczana jako domyślna.
Cloud Firestore Security Rules są stosowane oddzielnie do każdej bazy danych w projekcie. Oznacza to, że jeśli utworzysz kilka baz danych, musisz zarządzać regułami i wdrażać je w każdej z nich osobno. Szczegółowe instrukcje wdrażania aktualizacji znajdziesz w artykule Wdrażanie aktualizacji.
Podstawowe reguły odczytu i zapisu
Reguły podstawowe składają się z instrukcji match określającej ścieżkę dokumentu i wyrażenia allow, które szczegółowo opisuje, kiedy dozwolony jest odczyt określonych danych:
service cloud.firestore { match /databases/{database}/documents { // Match any document in the 'cities' collection match /cities/{city} { allow read: if; allow write: if ; } } }
Wszystkie oświadczenia o dopasowaniu powinny wskazywać dokumenty, a nie kolekcje. Instrukcja dopasowania może wskazywać konkretny dokument, np. match /cities/SF, lub używać symboli wieloznacznych, aby wskazywać dowolny dokument w określonej ścieżce, np. match /cities/{city}.
W powyższym przykładzie instrukcja dopasowania używa składni symbolu wieloznacznego {city}.
Oznacza to, że reguła ma zastosowanie do każdego dokumentu w kolekcji cities, np. /cities/SF lub /cities/NYC. Gdy allow wyrażenia w instrukcji dopasowania zostaną obliczone, zmienna city zostanie przekształcona w nazwę dokumentu miasta, np. SF lub NYC.
Szczegółowe operacje
W niektórych sytuacjach warto podzielić operacje read i write na bardziej szczegółowe. Na przykład aplikacja może wymagać spełnienia innych warunków w przypadku tworzenia dokumentu niż w przypadku jego usuwania. Możesz też zezwolić na odczytywanie pojedynczych dokumentów, ale odrzucać duże zapytania.
Regułę read można podzielić na get i list, a regułę write – na create, update i delete:
service cloud.firestore { match /databases/{database}/documents { // A read rule can be divided into get and list rules match /cities/{city} { // Applies to single document read requests allow get: if; // Applies to queries and collection read requests allow list: if ; } // A write rule can be divided into create, update, and delete rules match /cities/{city} { // Applies to writes to nonexistent documents allow create: if ; // Applies to writes to existing documents allow update: if ; // Applies to delete operations allow delete: if ; } } }
Dane hierarchiczne
Dane w Cloud Firestore są uporządkowane w kolekcje dokumentów, a każdy dokument może rozszerzać hierarchię za pomocą podkolekcji. Ważne jest, aby zrozumieć, jak reguły zabezpieczeń działają w przypadku danych hierarchicznych.
Rozważ sytuację, w której każdy dokument w kolekcji cities zawiera podkolekcję landmarks. Reguły zabezpieczeń mają zastosowanie tylko do pasującej ścieżki, więc mechanizmy kontroli dostępu zdefiniowane w kolekcji cities nie mają zastosowania do podkolekcji landmarks. Zamiast tego napisz jawne reguły, aby kontrolować dostęp do podzbiorów:
service cloud.firestore { match /databases/{database}/documents { match /cities/{city} { allow read, write: if; // Explicitly define rules for the 'landmarks' subcollection match /landmarks/{landmark} { allow read, write: if ; } } } }
Podczas zagnieżdżania instrukcji match ścieżka wewnętrznej instrukcji match jest zawsze względna w stosunku do ścieżki zewnętrznej instrukcji match. Te zestawy reguł są zatem równoważne:
service cloud.firestore { match /databases/{database}/documents { match /cities/{city} { match /landmarks/{landmark} { allow read, write: if; } } } }
service cloud.firestore { match /databases/{database}/documents { match /cities/{city}/landmarks/{landmark} { allow read, write: if; } } }
Rekurencyjne symbole wieloznaczne
Jeśli chcesz, aby reguły miały zastosowanie do dowolnie głębokiej hierarchii, użyj rekursywnej składni symbolu wieloznacznego – {name=**}. Przykład:
service cloud.firestore {
match /databases/{database}/documents {
// Matches any document in the cities collection as well as any document
// in a subcollection.
match /cities/{document=**} {
allow read, write: if <condition>;
}
}
}
Gdy używasz rekurencyjnej składni symbolu wieloznacznego, zmienna symbolu wieloznacznego będzie zawierać cały pasujący segment ścieżki, nawet jeśli dokument znajduje się w głęboko zagnieżdżonej podkolekcji. Na przykład reguły wymienione powyżej pasują do dokumentu znajdującego się w lokalizacji /cities/SF/landmarks/coit_tower, a wartość zmiennej document to SF/landmarks/coit_tower.
Pamiętaj jednak, że działanie rekursywnych symboli wieloznacznych zależy od wersji reguł.
Wersja 1
Reguły zabezpieczeń domyślnie korzystają z wersji 1. W wersji 1 rekursywne symbole wieloznaczne
pasują do co najmniej 1 elementu ścieżki. Nie pasują do pustej ścieżki, więc
match /cities/{city}/{document=**} pasuje do dokumentów w kolekcjach podrzędnych, ale nie w kolekcji cities, natomiast match /cities/{document=**} pasuje do dokumentów w kolekcji cities i w kolekcjach podrzędnych.
Rekursywne symbole wieloznaczne muszą znajdować się na końcu oświadczenia o dopasowaniu.
Wersja 2
W wersji 2 reguł bezpieczeństwa rekursywne symbole wieloznaczne pasują do zera lub większej liczby elementów ścieżki. Symbol match/cities/{city}/{document=**} pasuje do dokumentów w dowolnych podkolekcjach, a także do dokumentów w kolekcji match/cities/{city}/{document=**}.cities
Aby włączyć wersję 2, musisz dodać rules_version = '2'; na początku reguł zabezpieczeń:
rules_version = '2'; service cloud.firestore { match /databases/{database}/documents { // Matches any document in the cities collection as well as any document // in a subcollection. match /cities/{city}/{document=**} { allow read, write: if; } } }
W każdym warunku dopasowania możesz użyć maksymalnie jednego rekursywnego symbolu wieloznacznego, ale w wersji 2 możesz go umieścić w dowolnym miejscu warunku dopasowania. Przykład:
rules_version = '2'; service cloud.firestore { match /databases/{database}/documents { // Matches any document in the songs collection group match /{path=**}/songs/{song} { allow read, write: if; } } }
Jeśli używasz zapytań dotyczących grup kolekcji, musisz używać wersji 2. Więcej informacji znajdziesz w artykule Zabezpieczanie zapytań dotyczących grup kolekcji.
Nakładające się instrukcje dopasowania
Dokument może pasować do więcej niż 1 match. Jeśli z żądaniem pasuje kilka wyrażeń allow, dostęp jest przyznawany, jeśli którykolwiek z warunków ma wartość true:
service cloud.firestore { match /databases/{database}/documents { // Matches any document in the 'cities' collection. match /cities/{city} { allow read, write: if false; } // Matches any document in the 'cities' collection or subcollections. match /cities/{document=**} { allow read, write: if true; } } }
W powyższym przykładzie wszystkie operacje odczytu i zapisu w kolekcji cities będą dozwolone, ponieważ druga reguła zawsze ma wartość true, mimo że pierwsza reguła zawsze ma wartość false.
Limity reguł zabezpieczeń
Podczas pracy z regułami zabezpieczeń pamiętaj o tych limitach:
| Limit | Szczegóły |
|---|---|
Maksymalna liczba wywołań exists(), get() i getAfter() na żądanie |
Przekroczenie któregokolwiek z tych limitów spowoduje błąd braku uprawnień. Niektóre wywołania dostępu do dokumentów mogą być buforowane, a buforowane wywołania nie są wliczane do limitów. |
Maksymalna głębokość zagnieżdżenia instrukcji match |
10 |
Maksymalna długość ścieżki w segmentach ścieżki dozwolona w zbiorze zagnieżdżonych instrukcji match |
100 |
Maksymalna liczba zmiennych przechwytywania ścieżki dozwolonych w zbiorze zagnieżdżonych instrukcji match |
20 |
| Maksymalna głębokość wywołania funkcji | 20 |
| Maksymalna liczba argumentów funkcji | 7 |
Maksymalna liczba powiązań zmiennych let na funkcję |
10 |
| Maksymalna liczba rekurencyjnych lub cyklicznych wywołań funkcji | 0 (niedozwolone) |
| Maksymalna liczba wyrażeń ocenianych w ramach jednego żądania | 1000 |
| Maksymalny rozmiar zestawu reguł | Zbiory reguł muszą spełniać 2 limity rozmiaru:
|
Dalsze kroki
- Napisz warunki niestandardowych reguł zabezpieczeń.
- Przeczytaj dokumentację reguł zabezpieczeń.