1. Przegląd
W tym laboratorium kodowania poznasz podstawy Firebase do tworzenia interaktywnych aplikacji internetowych. Stworzysz aplikację do czatu RSVP i księgi gości, korzystając z kilku produktów Firebase.
Czego się nauczysz
- Uwierzytelniaj użytkowników za pomocą Firebase Authentication i FirebaseUI.
- Synchronizuj dane za pomocą Cloud Firestore.
- Napisz reguły bezpieczeństwa Firebase, aby zabezpieczyć bazę danych.
Co będziesz potrzebował
- Wybrana przeglądarka, na przykład Chrome.
- Dostęp do stackblitz.com (nie jest wymagane konto ani logowanie).
- Konto Google, takie jak konto Gmail. Zalecamy konto e-mail, którego już używasz na swoim koncie GitHub. Pozwala to na korzystanie z zaawansowanych funkcji w StackBlitz.
- Przykładowy kod Codelab. Zobacz następny krok, aby dowiedzieć się, jak uzyskać kod.
2. Zdobądź kod startowy
W tym laboratorium kodowania tworzysz aplikację za pomocą StackBlitz , edytora online, który ma kilka zintegrowanych przepływów pracy Firebase. Stackblitz nie wymaga instalacji oprogramowania ani specjalnego konta StackBlitz.
StackBlitz pozwala dzielić się projektami z innymi. Inne osoby, które mają adres URL Twojego projektu StackBlitz, mogą zobaczyć Twój kod i rozwidlić Twój projekt, ale nie mogą edytować Twojego projektu StackBlitz.
- Przejdź do tego adresu URL, aby uzyskać kod początkowy: https://stackblitz.com/edit/firebase-gtk-web-start
- U góry strony StackBlitz kliknij Fork :
Masz teraz kopię kodu początkowego jako swój własny projekt StackBlitz, który ma unikalną nazwę wraz z unikalnym adresem URL. Wszystkie twoje pliki i zmiany są zapisywane w tym projekcie StackBlitz.
3. Edytuj informacje o wydarzeniu
Materiały początkowe dla tego laboratorium kodu zapewniają pewną strukturę aplikacji internetowej, w tym niektóre arkusze stylów i kilka kontenerów HTML dla aplikacji. W dalszej części tego laboratorium kodowania podłączysz te kontenery do Firebase.
Na początek zapoznajmy się trochę z interfejsem StackBlitz.
- W StackBlitz otwórz plik
index.html
. - Zlokalizuj
event-details-container
idescription-container
, a następnie spróbuj edytować niektóre szczegóły wydarzenia.
Gdy edytujesz tekst, automatyczne przeładowanie strony w StackBlitz wyświetla szczegóły nowego wydarzenia. Fajne, tak?
<!-- ... -->
<div id="app">
<img src="..." />
<section id="event-details-container">
<h1>Firebase Meetup</h1>
<p><i class="material-icons">calendar_today</i> October 30</p>
<p><i class="material-icons">location_city</i> San Francisco</p>
</section>
<hr>
<section id="firebaseui-auth-container"></section>
<section id="description-container">
<h2>What we'll be doing</h2>
<p>Join us for a day full of Firebase Workshops and Pizza!</p>
</section>
</div>
<!-- ... -->
Podgląd Twojej aplikacji powinien wyglądać mniej więcej tak:
Podgląd aplikacji
4. Utwórz i skonfiguruj projekt Firebase
Wyświetlanie informacji o wydarzeniu jest świetne dla Twoich gości, ale samo pokazywanie wydarzeń nie jest zbyt przydatne dla nikogo. Dodajmy dynamiczną funkcjonalność do tej aplikacji. W tym celu musisz podłączyć Firebase do swojej aplikacji. Aby rozpocząć korzystanie z Firebase, musisz utworzyć i skonfigurować projekt Firebase.
Utwórz projekt Firebase
- Zaloguj się do Firebase .
- W konsoli Firebase kliknij Dodaj projekt (lub Utwórz projekt ), a następnie nazwij swój projekt Firebase Firebase-Web-Codelab .
- Kliknij opcje tworzenia projektu. Zaakceptuj warunki Firebase, jeśli pojawi się monit. Na ekranie Google Analytics kliknij „Nie włączaj”, ponieważ nie będziesz używać Analytics w tej aplikacji.
Aby dowiedzieć się więcej o projektach Firebase, zobacz Omówienie projektów Firebase .
Włącz i skonfiguruj produkty Firebase w konsoli
Aplikacja, którą tworzysz, korzysta z kilku produktów Firebase, które są dostępne dla aplikacji internetowych:
- Uwierzytelnianie Firebase i interfejs użytkownika Firebase , aby łatwo umożliwić użytkownikom logowanie się do Twojej aplikacji.
- Cloud Firestore do zapisywania uporządkowanych danych w chmurze i otrzymywania natychmiastowych powiadomień o zmianie danych.
- Reguły bezpieczeństwa Firebase w celu zabezpieczenia bazy danych.
Niektóre z tych produktów wymagają specjalnej konfiguracji lub muszą być włączone za pomocą konsoli Firebase.
Włącz logowanie przez e-mail dla uwierzytelniania Firebase
Aby umożliwić użytkownikom logowanie się do aplikacji internetowej, użyjesz metody logowania za pomocą adresu e-mail/hasła w tym laboratorium kodu:
- W panelu po lewej stronie konsoli Firebase kliknij Build > Authentication . Następnie kliknij Rozpocznij . Jesteś teraz na pulpicie nawigacyjnym uwierzytelniania, gdzie możesz zobaczyć zarejestrowanych użytkowników, skonfigurować dostawców logowania i zarządzać ustawieniami.
- Wybierz zakładkę Metoda logowania (lub kliknij tutaj, aby przejść bezpośrednio do zakładki).
- Kliknij E-mail/Hasło w opcjach dostawcy, przestaw przełącznik w położenie Włącz , a następnie kliknij Zapisz .
Skonfiguruj Cloud Firestore
Aplikacja internetowa używa Cloud Firestore do zapisywania wiadomości na czacie i odbierania nowych wiadomości na czacie.
Oto jak skonfigurować Cloud Firestore:
- W panelu po lewej stronie konsoli Firebase kliknij Build > Firestore Database . Następnie kliknij Utwórz bazę danych .
- Kliknij Utwórz bazę danych .
- Wybierz opcję Uruchom w trybie testowym . Przeczytaj zastrzeżenie dotyczące zasad bezpieczeństwa. Tryb testowy zapewnia, że możesz swobodnie pisać do bazy danych podczas programowania. Kliknij Dalej .
- Wybierz lokalizację dla swojej bazy danych (możesz po prostu użyć domyślnej). Pamiętaj jednak, że tej lokalizacji nie można później zmienić.
- Kliknij Gotowe .
5. Dodaj i skonfiguruj Firebase
Teraz, gdy masz już utworzony projekt Firebase i włączone niektóre usługi, musisz powiedzieć kodowi, że chcesz używać Firebase, a także jakiego projektu Firebase użyć.
Dodaj biblioteki Firebase
Aby Twoja aplikacja mogła korzystać z Firebase, musisz dodać do niej biblioteki Firebase. Można to zrobić na wiele sposobów, zgodnie z opisem w dokumentacji Firebase . Na przykład możesz dodać biblioteki z CDN Google lub zainstalować je lokalnie za pomocą npm, a następnie spakować je w swojej aplikacji, jeśli używasz Browserify.
StackBlitz zapewnia automatyczne łączenie, dzięki czemu możesz dodawać biblioteki Firebase za pomocą instrukcji importu. Będziesz używać modułowych (v9) wersji bibliotek, które pomagają zmniejszyć ogólny rozmiar strony internetowej poprzez proces zwany „potrząsaniem drzewem”. Więcej informacji o modułowych zestawach SDK można znaleźć w dokumentacji .
Aby utworzyć tę aplikację, używasz bibliotek Firebase Authentication, FirebaseUI i Cloud Firestore. W przypadku tego laboratorium kodów następujące instrukcje importu znajdują się już na początku pliku index.js
, a w miarę postępów będziemy importować więcej metod z każdej biblioteki Firebase:
// Import stylesheets
import './style.css';
// Firebase App (the core Firebase SDK) is always required
import { initializeApp } from 'firebase/app';
// Add the Firebase products and methods that you want to use
import {} from 'firebase/auth';
import {} from 'firebase/firestore';
import * as firebaseui from 'firebaseui';
Dodaj aplikację internetową Firebase do swojego projektu Firebase
- Wróć do konsoli Firebase i przejdź do strony przeglądu swojego projektu, klikając Przegląd projektu w lewym górnym rogu.
- Na środku strony przeglądu projektu kliknij ikonę sieci
aby utworzyć nową aplikację internetową Firebase.
- Zarejestruj aplikację pod pseudonimem Web App .
- W przypadku tego laboratorium kodowania NIE zaznaczaj pola wyboru Skonfiguruj także hosting Firebase dla tej aplikacji . Na razie będziesz korzystać z okienka podglądu StackBlitz.
- Kliknij Zarejestruj aplikację .
- Skopiuj obiekt konfiguracyjny Firebase do schowka.
- Kliknij Kontynuuj, aby wyświetlić konsolę . Dodaj obiekt konfiguracyjny Firebase do swojej aplikacji:
- Wróć do StackBlitz i przejdź do pliku
index.js
. - Znajdź
Add Firebase project configuration object here
, a następnie wklej fragment kodu konfiguracji tuż pod komentarzem. - Dodaj wywołanie funkcji
initializeApp
, aby skonfigurować Firebase przy użyciu unikalnej konfiguracji projektu Firebase.// ... // Add Firebase project configuration object here const firebaseConfig = { apiKey: "random-unique-string", authDomain: "your-projectId.firebaseapp.com", databaseURL: "https://your-projectId.firebaseio.com", projectId: "your-projectId", storageBucket: "your-projectId.appspot.com", messagingSenderId: "random-unique-string", appId: "random-unique-string", }; // Initialize Firebase initializeApp(firebaseConfig);
6. Dodaj logowanie użytkownika (RSVP)
Po dodaniu Firebase do aplikacji możesz skonfigurować przycisk RSVP, który rejestruje osoby korzystające z uwierzytelniania Firebase .
Uwierzytelniaj użytkowników za pomocą logowania przez e-mail i interfejsu FirebaseUI
Będziesz potrzebował przycisku RSVP, który poprosi użytkownika o zalogowanie się za pomocą adresu e-mail. Możesz to zrobić, podłączając FirebaseUI do przycisku RSVP. FirebaseUI to biblioteka, która zapewnia wstępnie zbudowany interfejs użytkownika na górze Firebase Auth.
FirebaseUI wymaga konfiguracji (zobacz opcje w dokumentacji ), która robi dwie rzeczy:
- Informuje FirebaseUI, że chcesz użyć metody logowania za pomocą adresu e-mail/hasła .
- Obsługuje wywołanie zwrotne pomyślnego logowania i zwraca wartość false, aby uniknąć przekierowania. Nie chcesz, aby strona była odświeżana, ponieważ tworzysz aplikację internetową z jedną stroną.
Dodaj kod, aby zainicjować FirebaseUI Auth
- W StackBlitz przejdź do pliku
index.js
. - U góry znajdź instrukcję importu
firebase/auth
, a następnie dodajgetAuth
iEmailAuthProvider
, na przykład:// ... // Add the Firebase products and methods that you want to use import { getAuth, EmailAuthProvider } from 'firebase/auth'; import {} from 'firebase/firestore';
- Zapisz odwołanie do obiektu auth zaraz po
initializeApp
, na przykład:initializeApp(firebaseConfig); auth = getAuth();
- Zwróć uwagę, że konfiguracja FirebaseUI jest już podana w kodzie startowym. Jest już skonfigurowany do korzystania z dostawcy uwierzytelniania poczty e-mail.
- Na dole funkcji
main()
windex.js
dodaj instrukcję inicjalizacji FirebaseUI, na przykład:async function main() { // ... // Initialize the FirebaseUI widget using Firebase const ui = new firebaseui.auth.AuthUI(auth); } main();
Dodaj przycisk RSVP do kodu HTML
- W StackBlitz przejdź do pliku
index.html
. - Dodaj kod HTML przycisku RSVP w
event-details-container
jak pokazano w poniższym przykładzie.
Uważaj, aby użyć tych samych wartościid
, jak pokazano poniżej, ponieważ w przypadku tego modułu kodu w plikuindex.js
znajdują się już zaczepy dla tych określonych identyfikatorów.
Zauważ, że w plikuindex.html
znajduje się kontener o identyfikatorzefirebaseui-auth-container
. To jest identyfikator, który przekażesz do FirebaseUI w celu przechowywania danych logowania.
Podgląd aplikacji<!-- ... --> <section id="event-details-container"> <!-- ... --> <!-- ADD THE RSVP BUTTON HERE --> <button id="startRsvp">RSVP</button> </section> <hr> <section id="firebaseui-auth-container"></section> <!-- ... -->
- Ustaw odbiornik na przycisku RSVP i wywołaj funkcję startową FirebaseUI. To mówi FirebaseUI, że chcesz zobaczyć okno logowania.
Dodaj następujący kod na końcu funkcjimain()
windex.js
:async function main() { // ... // Listen to RSVP button clicks startRsvpButton.addEventListener("click", () => { ui.start("#firebaseui-auth-container", uiConfig); }); } main();
Przetestuj logowanie do aplikacji
- W oknie podglądu StackBlitz kliknij przycisk RSVP, aby zalogować się do aplikacji.
- W tym laboratorium kodowania możesz użyć dowolnego adresu e-mail, nawet fałszywego adresu e-mail, ponieważ nie konfigurujesz etapu weryfikacji adresu e-mail dla tego modułu.
- Jeśli zobaczysz komunikat o błędzie informujący
auth/operation-not-allowed
lubThe given sign-in provider is disabled for this Firebase project
, upewnij się, że jako dostawca logowania w konsoli Firebase włączono e-mail/hasło .
- Przejdź do pulpitu nawigacyjnego Uwierzytelnianie w konsoli Firebase. Na karcie Użytkownicy powinny być widoczne informacje o koncie wprowadzone w celu zalogowania się do aplikacji.
Dodaj stan uwierzytelniania do interfejsu użytkownika
Następnie upewnij się, że interfejs użytkownika odzwierciedla fakt, że jesteś zalogowany.
Użyjesz wywołania zwrotnego odbiornika stanu uwierzytelniania Firebase, które zostanie powiadomione za każdym razem, gdy zmieni się stan logowania użytkownika. Jeśli aktualnie jest zalogowany użytkownik, aplikacja zmieni przycisk „RSVP” na przycisk „wyloguj”.
- W StackBlitz przejdź do pliku
index.js
. - U góry znajdź instrukcję importu
firebase/auth
, a następnie dodajsignOut
ionAuthStateChanged
, na przykład:// ... // Add the Firebase products and methods that you want to use import { getAuth, EmailAuthProvider, signOut, onAuthStateChanged } from 'firebase/auth'; import {} from 'firebase/firestore';
- Dodaj następujący kod na dole funkcji
main()
:async function main() { // ... // Listen to the current Auth state onAuthStateChanged(auth, user => { if (user) { startRsvpButton.textContent = 'LOGOUT'; } else { startRsvpButton.textContent = 'RSVP'; } }); } main();
- W słuchaczu przycisków sprawdź, czy jest obecny użytkownik i wyloguj go. Aby to zrobić, zastąp bieżący
startRsvpButton.addEventListener
następującym:// ... // Called when the user clicks the RSVP button startRsvpButton.addEventListener('click', () => { if (auth.currentUser) { // User is signed in; allows user to sign out signOut(auth); } else { // No user is signed in; allows user to sign in ui.start('#firebaseui-auth-container', uiConfig); } });
Teraz przycisk w Twojej aplikacji powinien wyświetlać LOGOUT i powinien przełączyć się z powrotem na RSVP po kliknięciu.
Podgląd aplikacji
7. Napisz wiadomości do Cloud Firestore
Świadomość, że użytkownicy przychodzą, jest świetna, ale dajmy gościom coś innego do roboty w aplikacji. Co by było, gdyby mogli zostawiać wiadomości w księdze gości? Mogą powiedzieć, dlaczego nie mogą się doczekać przyjazdu lub kogo mają nadzieję spotkać.
Do przechowywania wiadomości czatu, które użytkownicy piszą w aplikacji, użyjesz Cloud Firestore .
Model danych
Cloud Firestore to baza danych NoSQL, a dane przechowywane w bazie danych są podzielone na kolekcje, dokumenty, pola i podkolekcje. Każdą wiadomość z czatu będziesz przechowywać jako dokument w kolekcji najwyższego poziomu zwanej guestbook
.
Dodaj wiadomości do Firestore
W tej sekcji dodasz funkcję umożliwiającą użytkownikom pisanie nowych wiadomości do bazy danych. Najpierw dodajesz kod HTML elementów interfejsu użytkownika (pole wiadomości i przycisk wysyłania). Następnie dodajesz kod, który łączy te elementy z bazą danych.
Aby dodać elementy interfejsu użytkownika pola wiadomości i przycisku wysyłania:
- W StackBlitz przejdź do pliku
index.html
. - Znajdź
guestbook-container
, a następnie dodaj następujący kod HTML, aby utworzyć formularz z polem wprowadzania wiadomości i przyciskiem wyślij.<!-- ... --> <section id="guestbook-container"> <h2>Discussion</h2> <form id="leave-message"> <label>Leave a message: </label> <input type="text" id="message"> <button type="submit"> <i class="material-icons">send</i> <span>SEND</span> </button> </form> </section> <!-- ... -->
Podgląd aplikacji
Kliknięcie przez użytkownika przycisku WYŚLIJ spowoduje uruchomienie poniższego fragmentu kodu. Dodaje zawartość pola wprowadzania wiadomości do kolekcji guestbook
w bazie danych. W szczególności metoda addDoc
dodaje treść wiadomości do nowego dokumentu (z automatycznie wygenerowanym identyfikatorem) do kolekcji guestbook
.
- W StackBlitz przejdź do pliku
index.js
. - U góry znajdź instrukcję importu
firebase/firestore
, a następnie dodajgetFirestore
,addDoc
icollection
, na przykład:// ... // Add the Firebase products and methods that you want to use import { getAuth, EmailAuthProvider, signOut, onAuthStateChanged } from 'firebase/auth'; import { getFirestore, addDoc, collection } from 'firebase/firestore';
- Teraz zapiszemy odniesienie do obiektu
db
Firestore zaraz poinitializeApp
:initializeApp(firebaseConfig); auth = getAuth(); db = getFirestore();
- Na dole funkcji
main()
dodaj następujący kod.
Pamiętaj, żeauth.currentUser.uid
jest odniesieniem do automatycznie wygenerowanego unikalnego identyfikatora, który Firebase Authentication nadaje wszystkim zalogowanym użytkownikom.async function main() { // ... // Listen to the form submission form.addEventListener('submit', async e => { // Prevent the default form redirect e.preventDefault(); // Write a new message to the database collection "guestbook" addDoc(collection(db, 'guestbook'), { text: input.value, timestamp: Date.now(), name: auth.currentUser.displayName, userId: auth.currentUser.uid }); // clear message input field input.value = ''; // Return false to avoid redirect return false; }); } main();
Pokaż księgę gości tylko zalogowanym użytkownikom
Nie chcesz, aby każdy mógł zobaczyć czat gości. Aby zabezpieczyć czat, możesz zezwolić tylko zalogowanym użytkownikom na przeglądanie księgi gości. To powiedziawszy, w przypadku własnych aplikacji będziesz chciał również zabezpieczyć swoją bazę danych za pomocą Reguł bezpieczeństwa Firebase . (Więcej informacji na temat zasad bezpieczeństwa znajduje się w dalszej części laboratorium kodowania).
- W StackBlitz przejdź do pliku
index.js
. - Edytuj odbiornik
onAuthStateChanged
, aby ukryć i pokazać księgę gości.// ... // Listen to the current Auth state onAuthStateChanged(auth, user => { if (user) { startRsvpButton.textContent = 'LOGOUT'; // Show guestbook to logged-in users guestbookContainer.style.display = 'block'; } else { startRsvpButton.textContent = 'RSVP'; // Hide guestbook for non-logged-in users guestbookContainer.style.display = 'none'; } });
Testuj wysyłanie wiadomości
- Upewnij się, że jesteś zalogowany w aplikacji.
- Wpisz wiadomość, np. „Hej, tam!”, a następnie kliknij WYŚLIJ .
Ta czynność powoduje zapisanie wiadomości w bazie danych Cloud Firestore. Jednak nie zobaczysz jeszcze komunikatu w rzeczywistej aplikacji internetowej, ponieważ nadal musisz zaimplementować pobieranie danych. Zrobisz to dalej.
Ale możesz zobaczyć nowo dodaną wiadomość w konsoli Firebase.
W konsoli Firebase, na pulpicie nawigacyjnym Bazy danych Firestore , powinieneś zobaczyć kolekcję guestbook
z nowo dodaną wiadomością. Jeśli będziesz nadal wysyłać wiadomości, Twoja księga gości będzie zawierała wiele dokumentów, takich jak ten:
Konsola Firebase
8. Czytaj wiadomości
Synchronizuj wiadomości
To cudowne, że goście mogą pisać wiadomości do bazy danych, ale nie widzą ich jeszcze w aplikacji.
Aby wyświetlać komunikaty, musisz dodać odbiorniki uruchamiające się, gdy dane się zmieniają, a następnie utworzyć element interfejsu użytkownika, który wyświetla nowe komunikaty.
Dodasz kod, który nasłuchuje nowo dodanych wiadomości z aplikacji. Najpierw dodaj sekcję w kodzie HTML, aby wyświetlać wiadomości:
- W StackBlitz przejdź do pliku
index.html
. - W
guestbook-container
dodaj nową sekcję z identyfikatoremguestbook
.<!-- ... --> <section id="guestbook-container"> <h2>Discussion</h2> <form><!-- ... --></form> <section id="guestbook"></section> </section> <!-- ... -->
Następnie zarejestruj słuchacza, który nasłuchuje zmian dokonanych w danych:
- W StackBlitz przejdź do pliku
index.js
. - U góry znajdź instrukcję importu
firebase/firestore
, a następnie dodajquery
,orderBy
ionSnapshot
, na przykład:// ... import { getFirestore, addDoc, collection, query, orderBy, onSnapshot } from 'firebase/firestore';
- Na dole funkcji
main()
dodaj następujący kod, aby przejść przez wszystkie dokumenty (wiadomości księgi gości) w bazie danych. Aby dowiedzieć się więcej o tym, co dzieje się w tym kodzie, przeczytaj informacje poniżej fragmentu kodu.async function main() { // ... // Create query for messages const q = query(collection(db, 'guestbook'), orderBy('timestamp', 'desc')); onSnapshot(q, snaps => { // Reset page guestbook.innerHTML = ''; // Loop through documents in database snaps.forEach(doc => { // Create an HTML entry for each document and add it to the chat const entry = document.createElement('p'); entry.textContent = doc.data().name + ': ' + doc.data().text; guestbook.appendChild(entry); }); }); } main();
Aby nasłuchiwać wiadomości w bazie danych, utworzono zapytanie dotyczące określonej kolekcji za pomocą funkcji collection
. Powyższy kod nasłuchuje zmian w kolekcji guestbook
, w której przechowywane są wiadomości czatu. Wiadomości są również sortowane według daty, przy użyciu orderBy('timestamp', 'desc')
w celu wyświetlenia najnowszych wiadomości na górze.
Funkcja onSnapshot
przyjmuje dwa parametry: zapytanie do użycia i funkcję wywołania zwrotnego. Funkcja wywołania zwrotnego jest wyzwalana w przypadku jakichkolwiek zmian w dokumentach pasujących do zapytania. Może tak się stać, jeśli wiadomość zostanie usunięta, zmodyfikowana lub dodana. Aby uzyskać więcej informacji, zapoznaj się z dokumentacją Cloud Firestore .
Przetestuj synchronizację wiadomości
Cloud Firestore automatycznie i błyskawicznie synchronizuje dane z klientami zapisanymi do bazy danych.
- Wiadomości utworzone wcześniej w bazie danych powinny zostać wyświetlone w aplikacji. Zapraszam do pisania nowych wiadomości; powinny pojawić się natychmiast.
- Jeśli otworzysz swój obszar roboczy w wielu oknach lub kartach, wiadomości będą synchronizowane w czasie rzeczywistym między kartami.
- (Opcjonalnie) Możesz spróbować ręcznie usunąć, zmodyfikować lub dodać nowe wiadomości bezpośrednio w sekcji Baza danych konsoli Firebase; wszelkie zmiany powinny pojawić się w interfejsie użytkownika.
Gratulacje! Czytasz dokumenty Cloud Firestore w swojej aplikacji!
Podgląd aplikacji
9. Skonfiguruj podstawowe zasady bezpieczeństwa
Początkowo skonfigurowałeś Cloud Firestore do używania trybu testowego, co oznacza, że Twoja baza danych jest otwarta do odczytu i zapisu. Należy jednak używać trybu testowego tylko na bardzo wczesnych etapach rozwoju. Najlepszym rozwiązaniem jest skonfigurowanie reguł bezpieczeństwa dla bazy danych podczas opracowywania aplikacji. Bezpieczeństwo powinno być integralną częścią struktury i zachowania aplikacji.
Reguły bezpieczeństwa pozwalają kontrolować dostęp do dokumentów i zbiorów w Twojej bazie danych. Elastyczna składnia reguł umożliwia tworzenie reguł pasujących do wszystkiego, od wszystkich zapisów do całej bazy danych po operacje na określonym dokumencie.
Możesz napisać reguły bezpieczeństwa dla Cloud Firestore w konsoli Firebase:
- W sekcji Kompilacja konsoli Firebase kliknij opcję Baza danych Firestore , a następnie wybierz kartę Reguły (lub kliknij tutaj , aby przejść bezpośrednio do karty Reguły ).
- Powinny zostać wyświetlone następujące domyślne reguły bezpieczeństwa z limitem czasu publicznego dostępu za kilka tygodni od dzisiaj.
Zidentyfikuj kolekcje
Najpierw zidentyfikuj kolekcje, w których aplikacja zapisuje dane.
- Usuń istniejącą klauzulę
match /{document=**}
, aby Twoje reguły wyglądały tak:rules_version = '2'; service cloud.firestore { match /databases/{database}/documents { } }
- W
match /databases/{database}/documents
zidentyfikuj kolekcję, którą chcesz zabezpieczyć:rules_version = '2'; service cloud.firestore { match /databases/{database}/documents { match /guestbook/{entry} { // You'll add rules here in the next step. } }
Dodaj reguły bezpieczeństwa
Ponieważ identyfikator UID uwierzytelnienia został użyty jako pole w każdym dokumencie księgi gości, można uzyskać identyfikator UID uwierzytelnienia i sprawdzić, czy każdy, kto próbuje pisać w dokumencie, ma pasujący identyfikator UID uwierzytelnienia.
- Dodaj reguły odczytu i zapisu do swojego zestawu reguł, jak pokazano poniżej:
rules_version = '2'; service cloud.firestore { match /databases/{database}/documents { match /guestbook/{entry} { allow read: if request.auth.uid != null; allow create: if request.auth.uid == request.resource.data.userId; } } }
- Kliknij Opublikuj , aby wdrożyć nowe reguły. Teraz w księdze gości tylko zalogowani użytkownicy mogą czytać wiadomości (dowolną!), ale możesz tworzyć wiadomości tylko przy użyciu swojego identyfikatora użytkownika. Nie zezwalamy również na edytowanie ani usuwanie wiadomości.
Dodaj reguły sprawdzania poprawności
- Dodaj sprawdzanie poprawności danych, aby upewnić się, że w dokumencie znajdują się wszystkie oczekiwane pola:
rules_version = '2'; service cloud.firestore { match /databases/{database}/documents { match /guestbook/{entry} { allow read: if request.auth.uid != null; allow create: if request.auth.uid == request.resource.data.userId && "name" in request.resource.data && "text" in request.resource.data && "timestamp" in request.resource.data; } } }
- Kliknij Opublikuj , aby wdrożyć nowe reguły.
Zresetuj słuchaczy
Ponieważ Twoja aplikacja umożliwia teraz logowanie się tylko uwierzytelnionym użytkownikom, powinieneś przenieść zapytanie firestore
księgi gości do odbiornika uwierzytelniania. W przeciwnym razie wystąpią błędy uprawnień, a aplikacja zostanie rozłączona po wylogowaniu użytkownika.
- W StackBlitz przejdź do pliku
index.js
. - Przeciągnij kolekcję księgi gości na odbiorniku
onSnapshot
do nowej funkcji o nazwiesubscribeGuestbook
. Przypisz także wyniki funkcjionSnapshot
do zmiennejguestbookListener
.
Odbiornik FirestoreonSnapshot
zwraca funkcję anulowania subskrypcji, której można później użyć do anulowania odbiornika migawek.// ... // Listen to guestbook updates function subscribeGuestbook() { const q = query(collection(db, 'guestbook'), orderBy('timestamp', 'desc')); guestbookListener = onSnapshot(q, snaps => { // Reset page guestbook.innerHTML = ''; // Loop through documents in database snaps.forEach(doc => { // Create an HTML entry for each document and add it to the chat const entry = document.createElement('p'); entry.textContent = doc.data().name + ': ' + doc.data().text; guestbook.appendChild(entry); }); }); }
- Dodaj nową funkcję poniżej o nazwie
unsubscribeGuestbook
. Sprawdź, czy zmiennaguestbookListener
nie jest pusta, a następnie wywołaj funkcję, aby anulować słuchacza.// ... // Unsubscribe from guestbook updates function unsubscribeGuestbook() { if (guestbookListener != null) { guestbookListener(); guestbookListener = null; } }
Na koniec dodaj nowe funkcje do wywołania zwrotnego onAuthStateChanged
.
- Dodaj
subscribeGuestbook()
na doleif (user)
. - Dodaj
unsubscribeGuestbook()
na dole instrukcjielse
.// ... // Listen to the current Auth state onAuthStateChanged(auth, user => { if (user) { startRsvpButton.textContent = 'LOGOUT'; // Show guestbook to logged-in users guestbookContainer.style.display = 'block'; // Subscribe to the guestbook collection subscribeGuestbook(); } else { startRsvpButton.textContent = 'RSVP'; // Hide guestbook for non-logged-in users guestbookContainer.style.display = 'none'; // Unsubscribe from the guestbook collection unsubscribeGuestbook(); } });
10. Dodatkowy krok: przećwicz to, czego się nauczyłeś
Zapisz status RSVP uczestnika
W tej chwili Twoja aplikacja umożliwia ludziom rozpoczęcie czatu tylko wtedy, gdy są zainteresowani wydarzeniem. Ponadto jedynym sposobem, aby dowiedzieć się, czy ktoś nadchodzi, jest opublikowanie go na czacie. Zorganizujmy się i dajmy znać, ile osób przyjdzie.
Dodasz przełącznik, aby zarejestrować osoby, które chcą wziąć udział w wydarzeniu, a następnie zliczyć, ile osób przyjdzie.
- W StackBlitz przejdź do pliku
index.html
. - W
guestbook-container
dodaj zestaw przycisków YES i NO , na przykład:<!-- ... --> <section id="guestbook-container"> <h2>Are you attending?</h2> <button id="rsvp-yes">YES</button> <button id="rsvp-no">NO</button> <h2>Discussion</h2> <!-- ... --> </section> <!-- ... -->
Podgląd aplikacji
Następnie zarejestruj słuchacza na kliknięcia przycisków. Jeśli użytkownik kliknie TAK , użyj identyfikatora UID uwierzytelniania, aby zapisać odpowiedź w bazie danych.
- W StackBlitz przejdź do pliku
index.js
. - U góry znajdź instrukcję importu
firebase/firestore
, a następnie dodajdoc
,setDoc
iwhere
, na przykład:// ... // Add the Firebase products and methods that you want to use import { getFirestore, addDoc, collection, query, orderBy, onSnapshot, doc, setDoc, where } from 'firebase/firestore';
- Na dole funkcji
main()
dodaj następujący kod, aby odsłuchać status RSVP:async function main() { // ... // Listen to RSVP responses rsvpYes.onclick = async () => { }; rsvpNo.onclick = async () => { }; } main();
- Następnie utwórz nową kolekcję o nazwie
attendees
, a następnie zarejestruj odniesienie do dokumentu, jeśli kliknięto przycisk RSVP. Ustaw to odwołanie natrue
lubfalse
w zależności od klikniętego przycisku.
Najpierw dlarsvpYes
:
Następnie to samo dla// ... // Listen to RSVP responses rsvpYes.onclick = async () => { // Get a reference to the user's document in the attendees collection const userRef = doc(db, 'attendees', auth.currentUser.uid); // If they RSVP'd yes, save a document with attendi()ng: true try { await setDoc(userRef, { attending: true }); } catch (e) { console.error(e); } };
rsvpNo
, ale z wartościąfalse
:rsvpNo.onclick = async () => { // Get a reference to the user's document in the attendees collection const userRef = doc(db, 'attendees', auth.currentUser.uid); // If they RSVP'd yes, save a document with attending: true try { await setDoc(userRef, { attending: false }); } catch (e) { console.error(e); } };
Zaktualizuj swoje zasady bezpieczeństwa
Ponieważ masz już skonfigurowane pewne reguły, nowe dane, które dodajesz za pomocą przycisków, zostaną odrzucone.
Zezwalaj na dodawanie elementów do kolekcji attendees
Musisz zaktualizować reguły, aby umożliwić dodawanie do kolekcji attendees
.
- W przypadku kolekcji
attendees
, ponieważ użyłeś UID uwierzytelnienia jako nazwy dokumentu, możesz go pobrać i sprawdzić, czyuid
użytkownika przesyłającego jest taki sam jak dokument, który piszą. Zezwolisz wszystkim na odczytanie listy uczestników (ponieważ nie ma tam żadnych prywatnych danych), ale tylko twórca powinien mieć możliwość jej aktualizacji.rules_version = '2'; service cloud.firestore { match /databases/{database}/documents { // ... // match /attendees/{userId} { allow read: if true; allow write: if request.auth.uid == userId; } } }
- Kliknij Opublikuj , aby wdrożyć nowe reguły.
Dodaj reguły sprawdzania poprawności
- Dodaj kilka reguł sprawdzania poprawności danych, aby upewnić się, że w dokumencie znajdują się wszystkie oczekiwane pola:
rules_version = '2'; service cloud.firestore { match /databases/{database}/documents { // ... // match /attendees/{userId} { allow read: if true; allow write: if request.auth.uid == userId && "attending" in request.resource.data; } } }
- Nie zapomnij kliknąć Opublikuj , aby wdrożyć swoje reguły!
(Opcjonalnie) Możesz teraz przeglądać wyniki kliknięć przycisków. Przejdź do pulpitu nawigacyjnego Cloud Firestore w konsoli Firebase.
Przeczytaj status RSVP
Teraz, gdy już zarejestrowałeś odpowiedzi, zobaczmy, kto przyjdzie i odzwierciedl to w interfejsie użytkownika.
- W StackBlitz przejdź do pliku
index.html
. - W
description-container
dodaj nowy element z identyfikatoremnumber-attending
.<!-- ... --> <section id="description-container"> <!-- ... --> <p id="number-attending"></p> </section> <!-- ... -->
Następnie zarejestruj słuchacza do kolekcji attendees
i policz liczbę odpowiedzi TAK :
- W StackBlitz przejdź do pliku
index.js
. - Na dole funkcji
main()
dodaj następujący kod, aby odsłuchać status RSVP i policzyć kliknięcia TAK .async function main() { // ... // Listen for attendee list const attendingQuery = query( collection(db, 'attendees'), where('attending', '==', true) ); const unsubscribe = onSnapshot(attendingQuery, snap => { const newAttendeeCount = snap.docs.length; numberAttending.innerHTML = newAttendeeCount + ' people going'; }); } main();
Na koniec zaznaczmy przycisk odpowiadający aktualnemu statusowi.
- Utwórz funkcję, która sprawdza, czy bieżący identyfikator UID uwierzytelniania ma wpis w kolekcji
attendees
, a następnie ustaw klasę przycisku naclicked
.// ... // Listen for attendee list function subscribeCurrentRSVP(user) { const ref = doc(db, 'attendees', user.uid); rsvpListener = onSnapshot(ref, doc => { if (doc && doc.data()) { const attendingResponse = doc.data().attending; // Update css classes for buttons if (attendingResponse) { rsvpYes.className = 'clicked'; rsvpNo.className = ''; } else { rsvpYes.className = ''; rsvpNo.className = 'clicked'; } } }); }
- Zróbmy też funkcję do anulowania subskrypcji. Zostanie to użyte, gdy użytkownik się wyloguje.
// ... function unsubscribeCurrentRSVP() { if (rsvpListener != null) { rsvpListener(); rsvpListener = null; } rsvpYes.className = ''; rsvpNo.className = ''; }
- Wywołaj funkcje z odbiornika uwierzytelniania.
// ... // Listen to the current Auth state // Listen to the current Auth state onAuthStateChanged(auth, user => { if (user) { startRsvpButton.textContent = 'LOGOUT'; // Show guestbook to logged-in users guestbookContainer.style.display = 'block'; // Subscribe to the guestbook collection subscribeGuestbook(); // Subcribe to the user's RSVP subscribeCurrentRSVP(user); } else { startRsvpButton.textContent = 'RSVP'; // Hide guestbook for non-logged-in users guestbookContainer.style.display = 'none' ; // Unsubscribe from the guestbook collection unsubscribeGuestbook(); // Unsubscribe from the guestbook collection unsubscribeCurrentRSVP(); } });
- Spróbuj zalogować się jako wielu użytkowników i obserwuj wzrost liczby z każdym dodatkowym kliknięciem przycisku TAK .
Podgląd aplikacji
11. Gratulacje!
Użyłeś Firebase do zbudowania interaktywnej aplikacji internetowej działającej w czasie rzeczywistym!
Co omówiliśmy
- Uwierzytelnianie Firebase
- FirebaseUI
- Cloud Firestore
- Zasady bezpieczeństwa Firebase
Następne kroki
- Chcesz dowiedzieć się więcej o przepływie pracy programisty w Firebase? Zapoznaj się z laboratorium kodowania emulatora Firebase, aby dowiedzieć się, jak przetestować i uruchomić aplikację całkowicie lokalnie.
- Chcesz dowiedzieć się więcej o innych produktach Firebase? Może chcesz przechowywać pliki graficzne przesyłane przez użytkowników? Lub wysyłać powiadomienia do użytkowników? Sprawdź Web Codelab Firebase, aby uzyskać więcej informacji na temat wielu innych produktów Firebase dla Internetu.
- Chcesz dowiedzieć się więcej o Cloud Firestore? Może chcesz dowiedzieć się o podkolekcjach i transakcjach? Przejdź do internetowego laboratorium kodu Cloud Firestore, aby zapoznać się z laboratorium kodu, które bardziej szczegółowo omawia Cloud Firestore. Lub sprawdź tę serię YouTube, aby poznać Cloud Firestore !
Ucz się więcej
- Witryna Firebase: firebase.google.com
- Kanał Firebase na YouTube
Jak poszło?
Chcielibyśmy poznać Twoją opinię! Proszę wypełnić (bardzo) krótki formularz tutaj .