Firebase Web kennenlernen

1. Übersicht

In diesem Codelab lernen Sie die Grundlagen von Firebase kennen, um interaktive Webanwendungen zu erstellen. Sie erstellen eine App für die RSVP-Funktion und das Gästebuch einer Veranstaltung mit mehreren Firebase-Produkten.

Screenshot dieses Schritts

Aufgaben in diesem Lab

  • Nutzer mit Firebase Authentication und FirebaseUI authentifizieren
  • Daten mit Cloud Firestore synchronisieren
  • Firebase-Sicherheitsregeln schreiben, um eine Datenbank zu sichern.

Voraussetzungen

  • Einen Browser Ihrer Wahl, z. B. Chrome.
  • Zugriff auf stackblitz.com (kein Konto oder Anmeldung erforderlich)
  • Ein Google-Konto, z. B. ein Gmail-Konto. Wir empfehlen das E-Mail-Konto, das Sie bereits für Ihr GitHub-Konto verwenden. So können Sie erweiterte Funktionen in StackBlitz verwenden.
  • Beispielcode des Codelabs. Im nächsten Schritt erfahren Sie, wie Sie den Code abrufen.

2. Startcode abrufen

In diesem Codelab erstellen Sie eine App mit StackBlitz, einem Online-Editor, in den mehrere Firebase-Workflows eingebunden sind. Stackblitz erfordert keine Softwareinstallation oder ein spezielles StackBlitz-Konto.

Mit StackBlitz können Sie Projekte mit anderen teilen. Andere Personen, die die URL Ihres StackBlitz-Projekts kennen, können Ihren Code sehen und Ihr Projekt abspalten, aber sie können Ihr StackBlitz-Projekt nicht bearbeiten.

  1. Den Startcode finden Sie unter dieser URL: https://stackblitz.com/edit/firebase-gtk-web-start
  2. Klicken Sie oben auf der StackBlitz-Seite auf Fork:

Screenshot dieses Schritts

Sie haben jetzt eine Kopie des Startcodes als eigenes StackBlitz-Projekt, das einen eindeutigen Namen und eine eindeutige URL hat. Alle Ihre Dateien und Änderungen werden in diesem StackBlitz-Projekt gespeichert.

3. Termininformationen bearbeiten

Die Ausgangsmaterialien für dieses Codelab bieten eine Struktur für die Webanwendung, einschließlich einiger Stylesheets und einiger HTML-Container für die App. Später in diesem Codelab verknüpfen Sie diese Container mit Firebase.

Machen Sie sich zuerst mit der StackBlitz-Oberfläche vertraut.

  1. Öffnen Sie in StackBlitz die Datei index.html.
  2. Suchen Sie event-details-container und description-container und versuchen Sie dann, einige Termindetails zu bearbeiten.

Während Sie den Text bearbeiten, werden die neuen Ereignisdetails durch das automatische Aktualisieren der Seite in StackBlitz angezeigt. Cool, oder?

<!-- ... -->

<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>

<!-- ... -->

Die Vorschau Ihrer App sollte in etwa so aussehen:

App-Vorschau

Screenshot dieses Schritts

4. Firebase-Projekt erstellen und einrichten

Die Anzeige der Veranstaltungsinformationen ist für Ihre Gäste sehr hilfreich, aber die bloße Anzeige der Veranstaltungen ist für niemanden wirklich nützlich. Wir fügen dieser App einige dynamische Funktionen hinzu. Dazu müssen Sie Firebase mit Ihrer App verknüpfen. Um mit Firebase zu arbeiten, müssen Sie zuerst ein Firebase-Projekt erstellen und einrichten.

Firebase-Projekt erstellen

  1. Melden Sie sich in Firebase an.
  2. Klicken Sie in der Firebase Console auf Projekt hinzufügen oder Projekt erstellen und nennen Sie Ihr Firebase-Projekt Firebase-Web-Codelab.

    Screenshot dieses Schritts

  3. Klicken Sie sich durch die Optionen zur Projekterstellung. Akzeptieren Sie die Firebase-Nutzungsbedingungen, wenn Sie dazu aufgefordert werden. Klicken Sie auf dem Google Analytics-Bildschirm auf „Nicht aktivieren“, da Sie Analytics für diese App nicht verwenden werden.

Weitere Informationen zu Firebase-Projekten

Firebase-Produkte in der Console aktivieren und einrichten

Die von Ihnen erstellte App verwendet mehrere Firebase-Produkte, die für Web-Apps verfügbar sind:

  • Mit der Firebase-Authentifizierung und der Firebase-UI können sich Ihre Nutzer ganz einfach in Ihrer App anmelden.
  • Cloud Firestore speichert strukturierte Daten in der Cloud und benachrichtigt Sie sofort, wenn sich Daten ändern.
  • Firebase-Sicherheitsregeln zum Schutz Ihrer Datenbank

Einige dieser Produkte erfordern eine spezielle Konfiguration oder müssen über die Firebase Console aktiviert werden.

E-Mail-Anmeldung für Firebase Authentication aktivieren

Damit sich Nutzer in der Web-App anmelden können, verwenden Sie in diesem Codelab die Anmeldemethode E-Mail-Adresse/Passwort:

  1. Klicken Sie im linken Bereich der Firebase Console auf Build > Authentifizierung. Klicken Sie dann auf Jetzt starten. Sie befinden sich jetzt im Dashboard „Authentifizierung“. Dort können Sie registrierte Nutzer sehen, Anmeldeanbieter konfigurieren und Einstellungen verwalten.

    Screenshot dieses Schritts

  2. Wählen Sie den Tab Anmeldemethode aus (oder klicken Sie hier, um direkt dorthin zu gelangen).

    Screenshot dieses Schritts

  3. Klicke in den Anbieteroptionen auf E-Mail-Adresse/Passwort, setze den Schalter auf Aktivieren und klicke dann auf Speichern.

    Screenshot dieses Schritts

Cloud Firestore einrichten

Die Webanwendung verwendet Cloud Firestore, um Chatnachrichten zu speichern und neue Chatnachrichten zu empfangen.

So richten Sie Cloud Firestore in Ihrem Firebase-Projekt ein:

  1. Maximieren Sie im linken Bereich der Firebase Console Build und wählen Sie dann Firestore-Datenbank aus.
  2. Klicken Sie auf Datenbank erstellen.
  3. Lassen Sie die Datenbank-ID auf (default).
  4. Wählen Sie einen Speicherort für die Datenbank aus und klicken Sie auf Weiter.
    Bei einer echten App sollten Sie einen Standort in der Nähe Ihrer Nutzer auswählen.
  5. Klicken Sie auf Im Testmodus starten. Lies dir den Haftungsausschluss zu den Sicherheitsregeln durch.
    Später in diesem Codelab kannst du Sicherheitsregeln hinzufügen, um deine Daten zu schützen. Apps dürfen nicht veröffentlicht oder veröffentlicht werden, ohne Sicherheitsregeln für Ihre Datenbank hinzuzufügen.
  6. Klicken Sie auf Erstellen.

5. Firebase hinzufügen und konfigurieren

Nachdem Sie Ihr Firebase-Projekt erstellt und einige Dienste aktiviert haben, müssen Sie dem Code mitteilen, dass Sie Firebase verwenden möchten und welches Firebase-Projekt verwendet werden soll.

Firebase-Bibliotheken hinzufügen

Damit Ihre App Firebase verwenden kann, müssen Sie die Firebase-Bibliotheken hinzufügen. Wie das geht, wird in der Firebase-Dokumentation beschrieben. Sie können die Bibliotheken beispielsweise aus dem CDN von Google hinzufügen oder sie lokal mit npm installieren und dann in Ihrer App verpacken, wenn Sie Browserify verwenden.

StackBlitz bietet eine automatische Bündelung, sodass Sie die Firebase-Bibliotheken mit Importanweisungen hinzufügen können. Sie verwenden die modularen Versionen (v9) der Bibliotheken, die die Gesamtgröße der Webseite durch ein Verfahren namens „Tree Shaking“ reduzieren. Weitere Informationen zu den modularen SDKs findest du in der Dokumentation.

Für diese App verwenden Sie die Firebase Authentication-, FirebaseUI- und Cloud Firestore-Bibliotheken. In diesem Codelab sind die folgenden Importanweisungen bereits oben in der Datei index.js enthalten. Aus jeder Firebase-Bibliothek werden in Zukunft weitere Methoden importiert:

// 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';

Firebase-Web-App zum Firebase-Projekt hinzufügen

  1. Rufen Sie in der Firebase Console die Übersichtsseite Ihres Projekts auf, indem Sie oben links auf Projektübersicht klicken.
  2. Klicken Sie in der Mitte der Übersichtsseite des Projekts auf das Web-Symbol Symbol der Webanwendung, um eine neue Firebase Web-App zu erstellen.

    Screenshot dieses Schritts

  3. Registrieren Sie die App unter dem Alias Web-App.
  4. Klicken Sie für dieses Codelab NICHT auf das Kästchen neben Auch Firebase Hosting für diese App einrichten, da Sie vorerst den Vorschaubereich von StackBlitz verwenden.
  5. Klicken Sie auf App registrieren.

    Screenshot dieses Schritts

  6. Kopieren Sie das Firebase-Konfigurationsobjekt in die Zwischenablage.

    Screenshot dieses Schritts

  7. Klicken Sie auf Continue to console (Weiter zur Console). Fügen Sie Ihrer App das Firebase-Konfigurationsobjekt hinzu:
  8. Wechseln Sie in StackBlitz zur Datei index.js.
  9. Suchen Sie die Kommentarzeile für Add Firebase project configuration object here und fügen Sie das Konfigurations-Snippet direkt unter dem Kommentar ein.
  10. Fügen Sie den Funktionsaufruf initializeApp hinzu, um Firebase mit Ihrer individuellen Firebase-Projektkonfiguration einzurichten.
    // ...
    // 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.firebasestorage.app",
      messagingSenderId: "random-unique-string",
      appId: "random-unique-string",
    };
    
    // Initialize Firebase
    initializeApp(firebaseConfig);
    

6. Nutzeranmeldung hinzufügen (RSVP)

Nachdem Sie Firebase zur App hinzugefügt haben, können Sie eine Antwortschaltfläche einrichten, über die Nutzer mithilfe von Firebase Authentication registriert werden.

Nutzer mit der E-Mail-Anmeldung und FirebaseUI authentifizieren

Sie benötigen eine Schaltfläche zum Antworten, über die der Nutzer aufgefordert wird, sich mit seiner E-Mail-Adresse anzumelden. Dazu verbinden Sie FirebaseUI mit einer RSVP-Schaltfläche. FirebaseUI ist eine Bibliothek, die eine vorgefertigte UI auf Firebase Auth bietet.

FirebaseUI erfordert eine Konfiguration (siehe Optionen in der Dokumentation), die zwei Dinge bewirkt:

  • Hiermit wird FirebaseUI mitgeteilt, dass Sie die Anmeldemethode E-Mail/Passwort verwenden möchten.
  • Hier wird der Callback für eine erfolgreiche Anmeldung verarbeitet und „false“ zurückgegeben, um eine Weiterleitung zu vermeiden. Die Seite soll nicht aktualisiert werden, weil Sie eine einseitige Webanwendung erstellen.

Code zum Initialisieren von FirebaseUI Auth hinzufügen

  1. Rufen Sie in StackBlitz die Datei index.js auf.
  2. Suchen Sie oben nach der Importanweisung für firebase/auth und fügen Sie getAuth und EmailAuthProvider hinzu:
    // ...
    // Add the Firebase products and methods that you want to use
    import { getAuth, EmailAuthProvider } from 'firebase/auth';
    
    import {} from 'firebase/firestore';
    
  3. Speichere einen Verweis auf das Authentifizierungsobjekt direkt nach initializeApp, z. B. so:
    initializeApp(firebaseConfig);
    auth = getAuth();
    
  4. Die FirebaseUI-Konfiguration ist bereits im Startcode enthalten. Die Verwendung des E-Mail-Authentifizierungsanbieters ist bereits eingerichtet.
  5. Fügen Sie am Ende der Funktion main() in index.js die FirebaseUI-Initialisierungsanweisung hinzu:
    async function main() {
      // ...
    
      // Initialize the FirebaseUI widget using Firebase
      const ui = new firebaseui.auth.AuthUI(auth);
    }
    main();
    
    

HTML-Code eine RSVP-Schaltfläche hinzufügen

  1. Rufen Sie in StackBlitz die Datei index.html auf.
  2. Fügen Sie das HTML für eine RSVP-Schaltfläche in das event-details-container ein, wie im Beispiel unten gezeigt.

    Achten Sie darauf, dieselben id-Werte wie unten gezeigt zu verwenden, da es in diesem Codelab bereits Hooks für diese spezifischen IDs in der Datei index.js gibt.

    In der Datei index.html gibt es einen Container mit der ID firebaseui-auth-container. Dies ist die ID, die Sie an FirebaseUI übergeben, um Ihre Anmeldung zu speichern.
    <!-- ... -->
    
    <section id="event-details-container">
        <!-- ... -->
        <!-- ADD THE RSVP BUTTON HERE -->
        <button id="startRsvp">RSVP</button>
    </section>
    <hr>
    <section id="firebaseui-auth-container"></section>
    <!-- ... -->
    
    App-Vorschau

    Screenshot dieses Schritts

  3. Richten Sie einen Listener für die Schaltfläche zum Antworten ein und rufen Sie die FirebaseUI-Startfunktion auf. Dadurch wird FirebaseUI mitgeteilt, dass das Anmeldefenster angezeigt werden soll.

    Fügen Sie in index.js am Ende der main()-Funktion den folgenden Code ein:
    async function main() {
      // ...
    
      // Listen to RSVP button clicks
      startRsvpButton.addEventListener("click",
       () => {
            ui.start("#firebaseui-auth-container", uiConfig);
      });
    }
    main();
    

Anmeldung in der App testen

  1. Klicken Sie im Vorschaufenster von StackBlitz auf die Schaltfläche „Teilnehmen“, um sich in der App anzumelden.
    • Für dieses Codelab kannst du eine beliebige E‐Mail-Adresse verwenden – auch eine gefälschte E‐Mail-Adresse, da du für dieses Codelab keinen Schritt zur E‐Mail-Bestätigung einrichtest.
    • Wenn die Fehlermeldung auth/operation-not-allowed oder The given sign-in provider is disabled for this Firebase project enthält, prüfen Sie, ob Sie E-Mail/Passwort in der Firebase Console als Anmeldeanbieter aktiviert haben.
    App-Vorschau

    Screenshot dieses Schritts

  2. Rufen Sie in der Firebase Console das Dashboard Authentifizierung auf. Auf dem Tab Nutzer sollten die Kontoinformationen angezeigt werden, die Sie für die Anmeldung in der App eingegeben haben.

    Screenshot dieses Schritts

Authentifizierungsstatus zur UI hinzufügen

Prüfen Sie als Nächstes, ob auf der Benutzeroberfläche tatsächlich zu sehen ist, dass Sie angemeldet sind.

Sie verwenden den Callback für den Firebase-Authentifizierungsstatus-Listener, der jedes Mal benachrichtigt wird, wenn sich der Anmeldestatus des Nutzers ändert. Wenn gerade ein Nutzer angemeldet ist, wechselt Ihre App die Schaltfläche „Teilnehmen“ in eine Schaltfläche „Abmelden“.

  1. Rufen Sie in StackBlitz die Datei index.js auf.
  2. Suchen Sie oben nach der Importanweisung für firebase/auth und fügen Sie signOut und onAuthStateChanged hinzu:
    // ...
    // Add the Firebase products and methods that you want to use
    import {
      getAuth,
      EmailAuthProvider,
      signOut,
      onAuthStateChanged
    } from 'firebase/auth';
    
    import {} from 'firebase/firestore';
    
  3. Fügen Sie am Ende der Funktion main() den folgenden Code ein:
    async function main() {
      // ...
    
      // Listen to the current Auth state
      onAuthStateChanged(auth, user => {
        if (user) {
          startRsvpButton.textContent = 'LOGOUT';
        } else {
          startRsvpButton.textContent = 'RSVP';
        }
      });
    }
    main();
    
  4. Prüfen Sie im Schaltflächen-Listener, ob ein aktueller Nutzer vorhanden ist, und melden Sie ihn ab. Ersetzen Sie dazu die aktuelle startRsvpButton.addEventListener durch Folgendes:
    // ...
    // 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);
      }
    });
    

Auf der Schaltfläche in der App sollte nun Abmelden angezeigt werden und wieder Antworten angezeigt, wenn darauf geklickt wird.

App-Vorschau

Screenshot dieses Schritts

7. Nachrichten in Cloud Firestore schreiben

Es ist toll, dass Nutzer kommen, aber wir sollten den Gästen noch etwas anderes in der App bieten. Was wäre, wenn sie Nachrichten in einem Gästebuch hinterlassen könnten? Sie können mitteilen, warum sie sich auf die Veranstaltung freuen oder wen sie dort treffen möchten.

Zum Speichern der Chatnachrichten, die Nutzer in der App schreiben, verwenden Sie Cloud Firestore.

Datenmodell

Cloud Firestore ist eine NoSQL-Datenbank. In der Datenbank gespeicherte Daten werden in Sammlungen, Dokumente, Felder und untergeordnete Sammlungen unterteilt. Jede Nachricht des Chats wird als Dokument in einer Sammlung auf oberster Ebene namens guestbook gespeichert.

Grafik des Firestore-Datenmodells, die eine Gästebuchsammlung mit mehreren Nachrichtendokumenten zeigt

Nachrichten in Firestore hinzufügen

In diesem Abschnitt fügen Sie die Funktion für Nutzer hinzu, mit der sie neue Nachrichten in die Datenbank schreiben können. Fügen Sie zuerst das HTML für die UI-Elemente (Nachrichtenfeld und Schaltfläche „Senden“) hinzu. Fügen Sie dann den Code hinzu, mit dem diese Elemente mit der Datenbank verbunden werden.

So fügen Sie die UI-Elemente eines Nachrichtenfelds und eine Schaltfläche zum Senden hinzu:

  1. Rufen Sie in StackBlitz die Datei index.html auf.
  2. Suchen Sie nach guestbook-container und fügen Sie den folgenden HTML-Code hinzu, um ein Formular mit dem Eingabefeld für die Nachricht und der Schaltfläche „Senden“ zu erstellen.
    <!-- ... -->
    
     <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>
    
    <!-- ... -->
    

App-Vorschau

Screenshot dieses Schritts

Nutzer, die auf die Schaltfläche SENDEN klicken, lösen das folgende Code-Snippet aus. Der Inhalt des Eingabefelds für Nachrichten wird der Sammlung guestbook der Datenbank hinzugefügt. Die Methode addDoc fügt den Inhalt der Nachricht einem neuen Dokument (mit einer automatisch generierten ID) in der Sammlung guestbook hinzu.

  1. Rufen Sie in StackBlitz die Datei index.js auf.
  2. Suchen Sie oben nach der Importanweisung für firebase/firestore und fügen Sie getFirestore, addDoc und collection hinzu.
    // ...
    
    // 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';
    
  3. Jetzt speichern wir einen Verweis auf das Firestore-Objekt db direkt nach initializeApp:
    initializeApp(firebaseConfig);
    auth = getAuth();
    db = getFirestore();
    
  4. Fügen Sie unten in der Funktion main() den folgenden Code ein.

    Hinweis: auth.currentUser.uid ist eine Referenz auf die automatisch generierte eindeutige ID, die Firebase Authentication für alle angemeldeten Nutzer zuweist.
    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();
    

Das Gästebuch nur angemeldeten Nutzern anzeigen

Sie möchten nicht, dass irgendjemand den Chat der Gäste sieht. Sie können den Chat beispielsweise so sichern, dass nur angemeldete Nutzer das Gästebuch aufrufen können. Für Ihre eigenen Apps sollten Sie Ihre Datenbank jedoch auch mit Firebase-Sicherheitsregeln schützen. Weitere Informationen zu Sicherheitsregeln finden Sie später im Codelab.

  1. Rufen Sie in StackBlitz die Datei index.js auf.
  2. Bearbeiten Sie den onAuthStateChanged-Listener, um das Gästebuch auszublenden und einzublenden.
    // ...
    
    // 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';
      }
    });
    

Senden von Nachrichten testen

  1. Vergewissern Sie sich, dass Sie in der App angemeldet sind.
  2. Gib eine Nachricht ein, z. B. „Hallo!“ und klicke dann auf SENDEN.

Dadurch wird die Nachricht in Ihre Cloud Firestore-Datenbank geschrieben. In der eigentlichen Webanwendung wird die Nachricht jedoch noch nicht angezeigt, da Sie das Abrufen der Daten noch implementieren müssen. Das machen Sie als Nächstes.

Die neu hinzugefügte Nachricht wird jedoch in der Firebase Console angezeigt.

In der Firebase Console sollte im Dashboard Firestore-Datenbank die Sammlung guestbook mit der neu hinzugefügten Nachricht angezeigt werden. Wenn Sie immer wieder Nachrichten senden, enthält Ihre Gästebuchsammlung viele Dokumente, z. B.:

Firebase Console

Screenshot dieses Schritts

8. Nachrichten lesen

Nachrichten synchronisieren

Es ist schön, dass Gäste Nachrichten in die Datenbank schreiben können, sie werden aber noch nicht in der App angezeigt.

Wenn Sie Nachrichten anzeigen möchten, müssen Sie Listener hinzufügen, die ausgelöst werden, wenn sich Daten ändern, und dann ein UI-Element erstellen, das neue Nachrichten anzeigt.

Sie fügen Code hinzu, der auf neu hinzugefügte Nachrichten aus der App wartet. Fügen Sie zuerst einen Abschnitt in den HTML-Code ein, um Nachrichten anzuzeigen:

  1. Rufen Sie in StackBlitz die Datei index.html auf.
  2. Fügen Sie in guestbook-container einen neuen Abschnitt mit der ID guestbook hinzu.
    <!-- ... -->
    
      <section id="guestbook-container">
       <h2>Discussion</h2>
    
       <form><!-- ... --></form>
    
       <section id="guestbook"></section>
    
     </section>
    
    <!-- ... -->
    

Registrieren Sie als Nächstes den Listener, der auf Änderungen an den Daten achtet:

  1. Rufen Sie in StackBlitz die Datei index.js auf.
  2. Suchen Sie oben nach der Importanweisung firebase/firestore und fügen Sie query, orderBy und onSnapshot hinzu:
    // ...
    import {
      getFirestore,
      addDoc,
      collection,
      query,
      orderBy,
      onSnapshot
    } from 'firebase/firestore';
    
  3. Fügen Sie am Ende der Funktion main() den folgenden Code hinzu, um alle Dokumente (Gästebuchnachrichten) in der Datenbank zu durchlaufen. Weitere Informationen zu diesem Code finden Sie in der Tabelle unter dem Snippet.
    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();
    

Um Nachrichten in der Datenbank anzuhören, haben Sie mithilfe der Funktion collection eine Abfrage in einer bestimmten Sammlung erstellt. Mit dem Code oben werden die Änderungen in der Sammlung guestbook erfasst, in der die Chatnachrichten gespeichert werden. Die Nachrichten sind außerdem nach Datum sortiert. Die neuesten Nachrichten werden mithilfe von orderBy('timestamp', 'desc') ganz oben angezeigt.

Die onSnapshot-Funktion verwendet zwei Parameter: die zu verwendende Abfrage und eine Rückruffunktion. Die Callback-Funktion wird bei Änderungen an Dokumenten ausgelöst, die mit der Abfrage übereinstimmen. z. B. wenn eine Nachricht gelöscht, modifiziert oder hinzugefügt wird. Weitere Informationen finden Sie in der Cloud Firestore-Dokumentation.

Synchronisierung von Nachrichten testen

Cloud Firestore synchronisiert Daten automatisch und sofort mit Clients, die für die Datenbank abonniert sind.

  • Die Nachrichten, die Sie zuvor in der Datenbank erstellt haben, sollten in der App angezeigt werden. Sie können auch neue Nachrichten schreiben, die dann sofort angezeigt werden sollten.
  • Wenn Sie den Arbeitsbereich in mehreren Fenstern oder Tabs öffnen, werden die Nachrichten in Echtzeit synchronisiert.
  • Optional: Sie können neue Nachrichten direkt im Bereich Datenbank der Firebase Console manuell löschen, ändern oder hinzufügen. Alle Änderungen sollten in der Benutzeroberfläche angezeigt werden.

Glückwunsch! Sie lesen Cloud Firestore-Dokumente in Ihrer App.

App-Vorschau

Screenshot dieses Schritts

9. Grundlegende Sicherheitsregeln einrichten

Sie haben Cloud Firestore anfangs für die Verwendung des Testmodus eingerichtet, d. h., Ihre Datenbank ist für Lese- und Schreibvorgänge geöffnet. Sie sollten den Testmodus jedoch nur in den allerersten Entwicklungsphasen verwenden. Es empfiehlt sich, Sicherheitsregeln für Ihre Datenbank bereits bei der Entwicklung Ihrer App einzurichten. Sicherheit sollte ein wesentlicher Bestandteil der Struktur und des Verhaltens Ihrer App sein.

Mit Sicherheitsregeln können Sie den Zugriff auf Dokumente und Sammlungen in Ihrer Datenbank steuern. Die flexible Regelsyntax ermöglicht es Ihnen, Regeln zu erstellen, die alles von allen Schreibvorgängen über die gesamte Datenbank bis hin zu Vorgängen in einem bestimmten Dokument abgleichen.

Sie können Sicherheitsregeln für Cloud Firestore in der Firebase Console schreiben:

  1. Klicken Sie in der Firebase Console im Bereich Build auf Firestore-Datenbank und wählen Sie dann den Tab Regeln aus. Sie können auch auf diesen Link klicken, um direkt zum Tab Regeln zu gelangen.
  2. Sie sollten die folgenden Standardsicherheitsregeln mit einem Zeitlimit für den öffentlichen Zugriff in einigen Wochen sehen.

Screenshot dieses Schritts

Sammlungen identifizieren

Identifizieren Sie zuerst die Sammlungen, in die die App Daten schreibt.

  1. Löschen Sie die vorhandene match /{document=**}-Klausel, sodass Ihre Regeln so aussehen:
    rules_version = '2';
    service cloud.firestore {
      match /databases/{database}/documents {
      }
    }
    
  2. Wählen Sie unter match /databases/{database}/documents die Sammlung aus, die Sie schützen möchten:
    rules_version = '2';
    service cloud.firestore {
      match /databases/{database}/documents {
        match /guestbook/{entry} {
         // You'll add rules here in the next step.
      }
    }
    

Sicherheitsregeln hinzufügen

Da Sie die Authentifizierungs-UID als Feld in jedem Gästebuchdokument verwendet haben, können Sie die Authentifizierungs-UID abrufen und prüfen, ob alle Nutzer, die versuchen, in das Dokument zu schreiben, eine übereinstimmende Authentifizierungs-UID haben.

  1. Fügen Sie Ihrem Regelsatz die Lese- und Schreibregeln wie unten gezeigt hinzu:
    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;
        }
      }
    }
    
  2. Klicken Sie auf Veröffentlichen, um die neuen Regeln bereitzustellen.Im Gästebuch können jetzt nur angemeldete Nutzer Nachrichten lesen (beliebige Nachrichten), aber Sie können Nachrichten nur mit Ihrer Nutzer-ID erstellen. Nachrichten dürfen außerdem nicht bearbeitet oder gelöscht werden.

Validierungsregeln hinzufügen

  1. Fügen Sie eine Datenvalidierung hinzu, um sicherzustellen, dass alle erwarteten Felder im Dokument vorhanden sind:
    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;
        }
      }
    }
    
  2. Klicken Sie auf Veröffentlichen, um die neuen Regeln bereitzustellen.

Listener zurücksetzen

Da sich in Ihrer App jetzt nur authentifizierte Nutzer anmelden können, sollten Sie die firestore-Abfrage für das Gästebuch in den Authentifizierungs-Listener verschieben. Andernfalls treten Berechtigungsfehler auf und die Verbindung zur App wird getrennt, wenn sich der Nutzer abmeldet.

  1. Rufen Sie in StackBlitz die Datei index.js auf.
  2. Übertragen Sie den onSnapshot-Listener der Gästebuchsammlung in eine neue Funktion namens subscribeGuestbook. Weisen Sie außerdem die Ergebnisse der Funktion onSnapshot der Variablen guestbookListener zu.

    Der onSnapshot-Listener von Firestore gibt eine Abmeldefunktion zurück, mit der Sie den Snapshot-Listener später abbrechen können.
    // ...
    // 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);
        });
      });
    }
    
  3. Fügen Sie darunter eine neue Funktion namens unsubscribeGuestbook hinzu. Prüfen Sie, ob die Variable guestbookListener nicht null ist, und rufen Sie dann die Funktion auf, um den Listener abzubrechen.
    // ...
    // Unsubscribe from guestbook updates
    function unsubscribeGuestbook() {
      if (guestbookListener != null) {
        guestbookListener();
        guestbookListener = null;
      }
    }
    

Fügen Sie abschließend die neuen Funktionen dem onAuthStateChanged-Callback hinzu.

  1. Fügen Sie subscribeGuestbook() unter if (user) hinzu.
  2. Fügen Sie am Ende der else-Anweisung unsubscribeGuestbook() hinzu.
    // ...
    // 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. Bonusschritt: Gelerntes anwenden

Teilnahmestatus eines Teilnehmers erfassen

Derzeit können Nutzer in Ihrer App nur dann chatten, wenn sie sich für die Veranstaltung interessieren. Außerdem wissen Sie nur dann, ob jemand kommt, wenn er es im Chat postet. Lass uns alles organisieren und die Leute wissen lassen, wie viele Leute kommen.

Sie fügen eine Ein/Aus-Schaltfläche hinzu, um Personen zu registrieren, die an der Veranstaltung teilnehmen möchten, und erfassen dann, wie viele Personen kommen.

  1. Rufen Sie in StackBlitz die Datei index.html auf.
  2. Fügen Sie in guestbook-container eine Reihe von Schaltflächen JA und NEIN hinzu. Beispiel:
    <!-- ... -->
      <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>
    <!-- ... -->
    

App-Vorschau

Screenshot dieses Schritts

Registrieren Sie als Nächstes den Listener für Schaltflächenklicks. Wenn der Nutzer auf JA klickt, speichern Sie die Antwort anhand seiner Authentifizierungs-UID in der Datenbank.

  1. Rufen Sie in StackBlitz die Datei index.js auf.
  2. Suchen Sie oben nach der Importanweisung für firebase/firestore und fügen Sie doc, setDoc und where hinzu.
    // ...
    // Add the Firebase products and methods that you want to use
    import {
      getFirestore,
      addDoc,
      collection,
      query,
      orderBy,
      onSnapshot,
      doc,
      setDoc,
      where
    } from 'firebase/firestore';
    
  3. Fügen Sie unten in der Funktion main() den folgenden Code ein, um den Antwortstatus abzurufen:
    async function main() {
      // ...
    
      // Listen to RSVP responses
      rsvpYes.onclick = async () => {
      };
      rsvpNo.onclick = async () => {
      };
    }
    main();
    
    
  4. Erstellen Sie als Nächstes eine neue Sammlung mit dem Namen attendees und registrieren Sie dann eine Dokumentreferenz, wenn auf eine der RSVP-Schaltflächen geklickt wird. Legen Sie diese Referenz auf true oder false fest, je nachdem, auf welche Schaltfläche geklickt wird.

    Zuerst für rsvpYes:
    // ...
    // 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);
      }
    };
    
    Das Gleiche für rsvpNo, aber mit dem Wert 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);
      }
    };
    

Sicherheitsregeln aktualisieren

Da Sie bereits einige Regeln eingerichtet haben, werden die neuen Daten, die Sie über die Schaltflächen hinzufügen, abgelehnt.

Zusätzliche Elemente zur Sammlung attendees hinzufügen

Sie müssen die Regeln aktualisieren, damit Elemente zur Sammlung attendees hinzugefügt werden können.

  1. Da Sie für die Sammlung „attendees“ die Authentifizierungs-UID als Dokumentennamen verwendet haben, können Sie sie abrufen und prüfen, ob die uid des Einreichenden mit dem Dokument übereinstimmt, das er schreibt. Sie erlauben allen, die Teilnehmerliste zu lesen, da sie keine privaten Daten enthält. Nur der Ersteller sollte sie jedoch aktualisieren können.
    rules_version = '2';
    service cloud.firestore {
      match /databases/{database}/documents {
        // ... //
        match /attendees/{userId} {
          allow read: if true;
          allow write: if request.auth.uid == userId;
        }
      }
    }
    
  2. Klicken Sie auf Veröffentlichen, um die neuen Regeln bereitzustellen.

Validierungsregeln hinzufügen

  1. Fügen Sie einige Datenvalidierungsregeln hinzu, um sicherzustellen, dass alle erwarteten Felder im Dokument vorhanden sind:
    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;
    
        }
      }
    }
    
  2. Klicken Sie auf Veröffentlichen, um die Regeln bereitzustellen.

(Optional) Sie können sich jetzt ansehen, was passiert, wenn Sie auf die Schaltflächen klicken. Rufen Sie in der Firebase Console Ihr Cloud Firestore-Dashboard auf.

Antwortstatus lesen

Nachdem Sie die Antworten erfasst haben, sehen wir uns an, wer kommt, und spiegeln dies in der Benutzeroberfläche wider.

  1. Rufen Sie in StackBlitz die Datei index.html auf.
  2. Fügen Sie in description-container ein neues Element mit der ID number-attending hinzu.
    <!-- ... -->
    
     <section id="description-container">
         <!-- ... -->
         <p id="number-attending"></p>
     </section>
    
    <!-- ... -->
    

Registrieren Sie als Nächstes den Listener für die Sammlung attendees und zählen Sie die Anzahl der Antworten vom Typ YES:

  1. Rufen Sie in StackBlitz die Datei index.js auf.
  2. Fügen Sie unten in der Funktion main() den folgenden Code hinzu, um den RSVP-Status zu überwachen und Klicks auf JA zu zählen.
    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();
    

Legen Sie abschließend die Farbe der Schaltfläche fest, die dem aktuellen Status entspricht.

  1. Erstelle eine Funktion, die prüft, ob die aktuelle Authentifizierungs-UID einen Eintrag in der Sammlung attendees hat, und setze dann die Schaltflächenklasse auf clicked.
    // ...
    // 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';
          }
        }
      });
    }
    
  2. Außerdem erstellen wir eine Funktion zum Abbestellen. Wird verwendet, wenn sich der Nutzer abmeldet.
    // ...
    function unsubscribeCurrentRSVP() {
      if (rsvpListener != null) {
        rsvpListener();
        rsvpListener = null;
      }
      rsvpYes.className = '';
      rsvpNo.className = '';
    }
    
  3. Rufen Sie die Funktionen aus dem Authentifizierungs-Listener auf.
    // ...
    // 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();
          // Subscribe 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();
        }
      });
    
  4. Melden Sie sich als mehrere Nutzer an und sehen Sie, wie sich die Anzahl mit jedem zusätzlichen Klick auf die Schaltfläche JA erhöht.

App-Vorschau

Screenshot dieses Schritts

11. Glückwunsch!

Sie haben mit Firebase eine interaktive Echtzeit-Webanwendung erstellt.

Behandelte Themen

  • Firebase Authentication
  • FirebaseUI
  • Cloud Firestore
  • Firebase-Sicherheitsregeln

Nächste Schritte

  • Möchten Sie mehr über den Firebase-Entwickler-Workflow erfahren? Im Codelab zum Firebase-Emulator erfahren Sie, wie Sie Ihre App vollständig lokal testen und ausführen.
  • Möchten Sie mehr über andere Firebase-Produkte erfahren? Vielleicht möchten Sie Bilddateien speichern, die Nutzer hochladen. Oder Benachrichtigungen an Ihre Nutzer senden? Im Firebase Web Codelab erfahren Sie mehr über viele weitere Firebase-Produkte für das Web.
  • Sie möchten mehr über Cloud Firestore erfahren? Vielleicht möchten Sie mehr über untergeordnete Sammlungen und Transaktionen erfahren? Im Cloud Firestore-Web-Codelab erfahren Sie mehr über Cloud Firestore. In dieser YouTube-Serie erfahren Sie mehr über Cloud Firestore.

Weitere Informationen

Wie ist es gelaufen?

Dein Feedback ist gefragt! Bitte füllen Sie dieses kurze Formular aus.