Podczas tworzenia aplikacji możesz zablokować dostęp do swojego Baza danych Cloud Firestore. Jednak przed wdrożeniem potrzebnych jest zgłębianie szczegółów Cloud Firestore Security Rules Oprócz tworzenia prototypów za pomocą emulatora Cloud Firestore oraz testowanie ogólnych funkcji i działania aplikacji, można pisać testy jednostkowe, które sprawdzają działanie Cloud Firestore Security Rules.
Krótkie wprowadzenie
Kilka podstawowych zastosowań testowych z prostymi regułami znajdziesz w krótkim wprowadzeniu.
Poznaj Cloud Firestore Security Rules
Wdróż Firebase Authentication oraz Cloud Firestore Security Rules dla usług bezserwerowych uwierzytelniania, autoryzacji i weryfikacji danych podczas korzystania bibliotek klienta internetowego.
Cloud Firestore Security Rules obejmuje 2 elementy:
- Instrukcja
match
identyfikująca dokumenty w bazie danych. - Wyrażenie
allow
kontrolujące dostęp do tych dokumentów.
Firebase Authentication weryfikuje dane logowania użytkowników i stanowi podstawę systemów dostępu opartych na użytkownikach i rolach.
Każde żądanie bazy danych z biblioteki klienta mobilnego/internetowego Cloud Firestore jest oceniane pod kątem Twoich reguł zabezpieczeń przed odczytaniem lub zapisem danych. Jeśli reguły odmawiają dostępu do dowolnej ze wskazanych ścieżek dokumentów, cała sekwencja nie powiodło się.
Więcej informacji o usłudze Cloud Firestore Security Rules znajdziesz w artykule Pierwsze kroki z Cloud Firestore Security Rules.
Zainstaluj emulator
Aby zainstalować emulator Cloud Firestore, użyj interfejsu wiersza poleceń Firebase i uruchom to polecenie:
firebase setup:emulators:firestore
Uruchamianie emulatora
Zacznij od zainicjowania projektu Firebase w katalogu roboczym. To jest często jest to pierwszy krok podczas korzystania z interfejsu wiersza poleceń Firebase.
firebase init
Uruchom emulator za pomocą tego polecenia. Emulator będzie działać do zakończenia procesu:
firebase emulators:start --only firestore
W wielu przypadkach należy uruchomić emulator, uruchomić zestaw testów, a potem go zamknąć. Możesz to łatwo zrobić za pomocą
Polecenie emulators:exec
:
firebase emulators:exec --only firestore "./my-test-script.sh"
Po uruchomieniu emulator będzie próbował uruchomić się na porcie domyślnym (8080). Dostępne opcje
zmień port emulatora, modyfikując sekcję "emulators"
swojego
Plik firebase.json
:
{ // ... "emulators": { "firestore": { "port": "YOUR_PORT" } } }
Zanim uruchomisz emulator
Zanim zaczniesz korzystać z emulatora, pamiętaj o tych kwestiach:
- Na początku emulator wczyta reguły określone w polu
firestore.rules
plikufirebase.json
. Oczekuje ona nazwy lokalnego pliku, który zawiera Cloud Firestore Security Rules, i stosuje te reguły do wszystkich w projektach AI. Jeśli nie podasz lokalnej ścieżki pliku lub użyjeszloadFirestoreRules
, zgodnie z opisem poniżej, emulator traktuje wszystkie projektów z otwartymi regułami. - Choć
większość pakietów SDK Firebase
obsługuje bezpośrednio emulatory, tylko biblioteka
@firebase/rules-unit-testing
obsługuje naśmiewanie się zauth
w regułach zabezpieczeń, co znacznie ułatwia testowanie jednostkowe. Dodatkowo biblioteka obsługuje kilka funkcji związanych z konkretnym emulatorem, takich jak czyszczenie wszystkich danych, które wymieniono poniżej. - Emulatory będą też akceptować produkcyjne tokeny uwierzytelniania Firebase udostępnione za pomocą pakietów SDK klienta i odpowiednio oceniać reguły, co umożliwia bezpośrednio do emulatorów w ramach testów integracji i testów ręcznych.
Przeprowadzanie lokalnych testów jednostkowych
Przeprowadzanie lokalnych testów jednostkowych za pomocą pakietu SDK JavaScript w wersji 9
Firebase rozpowszechnia bibliotekę testowania jednostkowego reguł zabezpieczeń wraz z jej wersją SDK 9 JavaScript i jego pakiet SDK w wersji 8. Interfejsy API biblioteki są w znacznym stopniu w inny sposób. Zalecamy korzystanie z biblioteki testowej v9, która jest prostsza w obsłudze wymaga mniej konfiguracji, aby można było łączyć się z emulatorami, i bezpiecznie uniknąć przypadkowego wykorzystanie zasobów produkcyjnych. Aby zapewnić zgodność wsteczną, wprowadzamy dostępna biblioteka do testowania wersji 8.
- Częste metody testowania i funkcje pomocnicze w pakiecie SDK w wersji 9
- Metody testów w emulatorze w pakiecie SDK w wersji 9
Do interakcji z lokalnie uruchomionym emulatorem służy moduł @firebase/rules-unit-testing
. Jeśli wystąpi przekroczenie limitu czasu oczekiwania lub ECONNREFUSED
błąd, sprawdź jeszcze raz
że emulator działa.
Zdecydowanie zalecamy korzystanie z najnowszej wersji środowiska Node.js, co pozwoli Ci korzystać z
Zapis async/await
. Prawie wszystkie zachowania, które warto przetestować
obejmuje funkcje asynchroniczne, a moduł testowania jest przeznaczony do działania
Kod oparty na obietnicy.
Biblioteka testowania jednostkowego w wersji 9 zawsze wie o emulatorach i nigdy zasobów produkcyjnych.
Bibliotekę importujesz za pomocą instrukcji importu modułowego v9. Przykład:
import {
assertFails,
assertSucceeds,
initializeTestEnvironment
} from "@firebase/rules-unit-testing"
// Use `const { … } = require("@firebase/rules-unit-testing")` if imports are not supported
// Or we suggest `const testing = require("@firebase/rules-unit-testing")` if necessary.
Po zaimportowaniu testów jednostkowych ich implementacja obejmuje:
- Tworzenie i konfigurowanie obiektu
RulesTestEnvironment
z wywołanieminitializeTestEnvironment
- Konfigurowanie danych testowych bez uruchamiania reguł za pomocą wygodnej metody, która pozwala na ich tymczasowe pominięcie:
RulesTestEnvironment.withSecurityRulesDisabled
. - Konfigurowanie zestawu testów i funkcji przed testem lub po nim z wywołaniem do funkcji czyszczących dane testowe i środowisko, np.
RulesTestEnvironment.cleanup()
lubRulesTestEnvironment.clearFirestore()
. - Wdrażanie przypadków testowych, które naśladują stany uwierzytelniania za pomocą
RulesTestEnvironment.authenticatedContext
iRulesTestEnvironment.unauthenticatedContext
Typowe metody i funkcje użytkowe
Zobacz też metody testowe związane z emulatorami w pakiecie SDK w wersji 9.
initializeTestEnvironment() => RulesTestEnvironment
Ta funkcja inicjuje środowisko testowe do testowania jednostkowego reguł. Zadzwoń dla konfiguracji testu. Aby się udało, emulatory muszą być w domu.
Funkcja akceptuje opcjonalny obiekt definiujący TestEnvironmentConfig
,
który może składać się z identyfikatora projektu i ustawień konfiguracji emulatora.
let testEnv = await initializeTestEnvironment({ projectId: "demo-project-1234", firestore: { rules: fs.readFileSync("firestore.rules", "utf8"), }, });
RulesTestEnvironment.authenticatedContext({ user_id: string, tokenOptions?: TokenOptions }) => RulesTestContext
Ta metoda tworzy RulesTestContext
, który działa jak uwierzytelniony
Uwierzytelnianie użytkownika. Żądania utworzone przy użyciu zwróconego kontekstu będą miały model
Dołączono token uwierzytelniania. Opcjonalnie prześlij obiekt definiujący roszczenia niestandardowe lub zastąpienia dla danych tokena uwierzytelniania.
Używaj zwracanego obiektu test context w testach, aby uzyskać dostęp do skonfigurowanych instancji emulatora, w tym do tych skonfigurowanych za pomocą initializeTestEnvironment
.
// Assuming a Firestore app and the Firestore emulator for this example import { setDoc } from "firebase/firestore"; const alice = testEnv.authenticatedContext("alice", { … }); // Use the Firestore instance associated with this context await assertSucceeds(setDoc(alice.firestore(), '/users/alice'), { ... });
RulesTestEnvironment.unauthenticatedContext() => RulesTestContext
Ta metoda tworzy obiekt RulesTestContext
, który działa jak klient, który jest
Użytkownik nie zalogował się przez Uwierzytelnianie. Żądania utworzone za pomocą zwróconego kontekstu nie będą
tokeny uwierzytelniania Firebase.
Użyj zwróconego obiektu kontekstu testowego w testach, aby uzyskać dostęp do dowolnego emulatora
skonfigurowanych instancji, w tym tych ze skonfigurowanych przy użyciu initializeTestEnvironment
.
// Assuming a Cloud Storage app and the Storage emulator for this example import { getStorage, ref, deleteObject } from "firebase/storage"; const alice = testEnv.unauthenticatedContext(); // Use the Cloud Storage instance associated with this context const desertRef = ref(alice.storage(), 'images/desert.jpg'); await assertSucceeds(deleteObject(desertRef));
RulesTestEnvironment.withSecurityRulesDisabled()
Uruchom funkcję konfiguracji testowej z kontekstem, który działa tak, jakby reguły zabezpieczeń wyłączono.
Ta metoda korzysta z funkcji wywołania zwrotnego, która wykorzystuje funkcję omijania reguł zabezpieczeń i zwraca obietnicę. Kontekst zostanie zniszczony, gdy obietnica podejmie decyzję lub ją odrzuci.
RulesTestEnvironment.cleanup()
Ta metoda niszczy wszystkie RulesTestContexts
utworzone w środowisku testowym i
czyści bazowe zasoby, pozostawiając czyste wyjście.
Ta metoda nie zmienia w żaden sposób stanu emulatorów. Resetowanie danych między kolejnymi testami należy użyć metody jasnej danych specyficznej dla emulatora aplikacji.
assertSucceeds(pr: Promise<any>)) => Promise<any>
To jest funkcja pomocnicza testowego przypadku użycia.
Funkcja potwierdza, że podana usługa Promise opakowuje operację emulatora zostanie rozwiązany bez naruszeń reguł zabezpieczeń.
await assertSucceeds(setDoc(alice.firestore(), '/users/alice'), { ... });
assertFails(pr: Promise<any>)) => Promise<any>
To jest funkcja narzędziowa przypadku testowego.
Funkcja potwierdza, że podana usługa Promise opakowuje operację emulatora zostanie odrzucona z powodu naruszenia reguł zabezpieczeń.
await assertFails(setDoc(alice.firestore(), '/users/bob'), { ... });
Metody specyficzne dla emulatora
Zobacz też popularne metody testowania i funkcje pomocnicze w pakiecie SDK w wersji 9.
RulesTestEnvironment.clearFirestore() => Promise<void>
Ta metoda usuwa w bazie danych Firestore dane, które należą do
Uprawnienia projectId
zostały skonfigurowane dla emulatora Firestore.
RulesTestContext.firestore(settings?: Firestore.FirestoreSettings) => Firestore;
Ta metoda pobiera instancję Firestore na potrzeby tego kontekstu testowego. Zwrócone wartości Instancji pakietu SDK Firebase JS Client SDK można używać z interfejsami API pakietu SDK klienta (modułowa wersja 9) lub zgodnego z wersją 9).
Wizualizacja ocen reguł
Emulator Cloud Firestore umożliwia wizualizację żądań klientów w interfejsu użytkownika Pakietu emulatorów, w tym śledzenia oceny dla reguł zabezpieczeń Firebase.
Otwórz Firestore > Prośby, aby wyświetlić szczegółową ocenę. dla każdego żądania.
Generowanie raportów z testów
Po uruchomieniu zestawu testów możesz uzyskać dostęp do raportów o zakresie testów, które pokazują, jak oceniono każdą z reguł bezpieczeństwa.
Aby uzyskać te raporty, wyślij w emulatorze zapytanie do ujawnionego punktu końcowego, podczas gdy jego uruchomienie. W przypadku wersji przeznaczonej do wyświetlania w przeglądarce użyj tego adresu URL:
http://localhost:8080/emulator/v1/projects/<project_id>:ruleCoverage.html
Reguły są dzielone na wyrażenia i podwyrażenia, najechanie kursorem myszy, aby uzyskać więcej informacji, w tym liczbę ocen i wartości . W przypadku nieprzetworzonej wersji JSON tych danych dołącz ten adres URL w zapytaniu:
http://localhost:8080/emulator/v1/projects/<project_id>:ruleCoverage
Różnice między emulatorem a wersją produkcyjną
- Nie musisz bezpośrednio tworzyć projektu Cloud Firestore. Emulator automatycznie tworzy każdą instancję, do której uzyskano dostęp.
- Emulator Cloud Firestore nie działa w zwykłym procesie Firebase Authentication.
Zamiast tego w pakiecie Firebase Test SDK udostępniliśmy w bibliotece
rules-unit-testing
metodęinitializeTestApp()
, która przyjmuje poleauth
. Utworzono nick Firebase używając tej metody, będzie działać tak, jakby została pomyślnie uwierzytelniona jako bez względu na nazwę podmiotu. Jeśli przekażesz zasadęnull
, będzie ona działać jako nieuwierzytelniony użytkownik (na przykład regułyauth != null
zakończą się niepowodzeniem).
Rozwiązywanie znanych problemów
Podczas używania emulatora Cloud Firestore możesz napotkać te znane problemów. Aby rozwiązać problemy z nieprawidłowym działaniem, postępuj zgodnie z instrukcjami poniżej. Te notatki są tworzone podczas testowania jednostkowego reguł zabezpieczeń ale ogólne podejścia mają zastosowanie do każdego pakietu SDK Firebase.
Działanie testu jest niespójne
Jeśli testy są czasami zaliczone i kończą się niepowodzeniem, nawet jeśli nie wprowadzasz żadnych zmian
samodzielnie testujących, warto sprawdzić, czy mają prawidłową sekwencję.
Większość interakcji z emulatorem jest asynchroniczna, więc sprawdź dokładnie, czy wszystkie
dla kodu asynchronicznego należy zastosować odpowiednią sekwencję. Sekwencjonowanie możesz poprawić, wykonując jedną z tych czynności:
łańcuch obietnic lub swobodne korzystanie z notacji await
.
W szczególności sprawdź te operacje asynchroniczne:
- Ustawianie reguł zabezpieczeń, na przykład
initializeTestEnvironment
. - odczytywanie i zapisywanie danych, np.
db.collection("users").doc("alice").get()
. - Potwierdzenia działań, w tym
assertSucceeds
iassertFails
.
Testy zaliczają się tylko przy pierwszym wczytaniu emulatora
Emulator jest stanowy. Przechowuje wszystkie zapisane w niej dane w pamięci, wyłączenie emulatora spowoduje utratę danych. Jeśli masz wiele reklam testów z tym samym identyfikatorem projektu, każdy test może dostarczyć dane, które mogą wpłynąć na kolejne testy. Możesz użyć dowolnej z tych metod, aby: omiń to zachowanie:
- Używaj unikalnych identyfikatorów projektów w przypadku każdego testu. Pamiętaj, że jeśli to zrobisz,
musi wywołać funkcję
initializeTestEnvironment
w ramach każdego testu; reguły są ładowane automatycznie tylko dla domyślnego identyfikatora projektu. - Przeorganizuj testy tak, aby nie wchodziły w interakcje z wcześniej zapisanymi danymi (np. dla każdego testu użyj innej kolekcji).
- Usuń wszystkie dane zapisane podczas testu.
Konfiguracja testu jest bardzo skomplikowana
Podczas konfigurowania testu warto zmodyfikować dane w taki sposób, aby
Cloud Firestore Security Rules nie zezwalają na dostęp. Jeśli reguły powodują konfigurację testu
złożone, spróbuj użyć w konfiguracji usługi RulesTestEnvironment.withSecurityRulesDisabled
kroków, więc odczyty i zapisy nie będą wywoływać błędów PERMISSION_DENIED
.
Po tym czasie test może wykonywać operacje jako uwierzytelniony lub nieuwierzytelniony
użytkownik korzystający z funkcji RulesTestEnvironment.authenticatedContext
i unauthenticatedContext
. Pozwoli Ci to sprawdzić, czy Cloud Firestore Security Rules zezwala / nie zezwala na dostęp
poszczególne przypadki.