In diesem Dokument werden die Grundlagen des Abrufens von Daten sowie das Sortieren und Filtern von Firebase-Daten behandelt.
Hinweis
Sie müssen Ihre App eingerichtet haben und auf die Datenbank zugreifen können. Weitere Informationen finden Sie im Get Started
-Leitfaden.
Daten abrufen
Firebase-Daten werden entweder durch einen einmaligen Aufruf von GetValue()
oder durch Anhängen an einen ValueListener
an einer FirebaseDatabase
-Referenz abgerufen. Der Wert-Listener wird einmal für den anfänglichen Status der Daten und dann bei jeder Änderung der Daten aufgerufen.
DatabaseReference abrufen
Zum Schreiben von Daten in die Datenbank benötigen Sie eine Instanz von DatabaseReference
:
// Get the root reference location of the database. firebase::database::DatabaseReference dbref = database->GetReference();
Daten einmal lesen
Mit der Methode GetValue()
können Sie einmalig einen statischen Snapshot des Inhalts an einem bestimmten Pfad lesen. Das Aufgabenergebnis enthält einen Snapshot mit allen Daten an diesem Speicherort, einschließlich untergeordneter Daten. Wenn keine Daten vorhanden sind, ist der zurückgegebene Snapshot null
.
firebase::Future<firebase::database::DataSnapshot> result = dbRef.GetReference("Leaders").GetValue();
Die Anfrage wurde gestellt, aber wir müssen warten, bis die Future abgeschlossen ist, bevor wir den Wert lesen können. Da Spiele in der Regel in einer Schleife ausgeführt werden und weniger auf Rückrufen basieren als andere Anwendungen, wird der Abschluss in der Regel abgefragt.
// In the game loop that polls for the result... if (result.status() != firebase::kFutureStatusPending) { if (result.status() != firebase::kFutureStatusComplete) { LogMessage("ERROR: GetValue() returned an invalid result."); // Handle the error... } else if (result.error() != firebase::database::kErrorNone) { LogMessage("ERROR: GetValue() returned error %d: %s", result.error(), result.error_message()); // Handle the error... } else { firebase::database::DataSnapshot snapshot = result.result(); // Do something with the snapshot... } }
Hier sehen Sie einige grundlegende Fehlerprüfungen. Weitere Informationen zur Fehlerprüfung und dazu, wie Sie feststellen können, wann das Ergebnis bereit ist, finden Sie in der firebase::Future-Referenz.
Auf Ereignisse warten
Sie können Listener hinzufügen, um Änderungen an Daten zu abonnieren:
ValueListener
Basisklasse
Rückruf | Typische Verwendung |
---|---|
OnValueChanged |
Änderungen am gesamten Inhalt eines Pfads lesen und überwachen. |
OnChildListener
Basisklasse
OnChildAdded
| Listen von Elementen abrufen oder auf Ergänzungen einer Liste von Elementen warten
Empfohlene Verwendung mit OnChildChanged und OnChildRemoved , um Änderungen an Listen zu überwachen. |
OnChildChanged |
Änderungen an den Elementen in einer Liste beobachten Verwenden Sie OnChildAdded und OnChildRemoved , um Änderungen an Listen zu beobachten. |
OnChildRemoved |
Auf das Entfernen von Elementen aus einer Liste reagieren Verwenden Sie OnChildAdded und OnChildChanged , um Änderungen an Listen zu beobachten. |
OnChildMoved |
Auf Änderungen der Reihenfolge von Elementen in einer sortierten Liste reagieren
OnChildMoved -Callbacks folgen immer auf OnChildChanged -Callbacks, da sich die Reihenfolge des Elements ändert (basierend auf der aktuellen „order-by“-Methode). |
Klasse „ValueListener“
Mit den OnValueChanged
-Callbacks können Sie Änderungen am Inhalt eines bestimmten Pfads abonnieren. Dieser Callback wird einmal ausgelöst, wenn der Listener angehängt wird, und dann jedes Mal, wenn sich die Daten ändern, einschließlich untergeordneter Elemente. An den Callback wird ein Snapshot mit allen Daten an diesem Speicherort, einschließlich untergeordneter Daten, übergeben. Wenn keine Daten vorhanden sind, ist der zurückgegebene Snapshot null
.
Im folgenden Beispiel ruft ein Spiel die Ergebnisse einer Bestenliste aus der Datenbank ab:
class LeadersValueListener : public firebase::database::ValueListener { public: void OnValueChanged( const firebase::database::DataSnapshot& snapshot) override { // Do something with the data in snapshot... } void OnCancelled(const firebase::database::Error& error_code, const char* error_message) override { LogMessage("ERROR: LeadersValueListener canceled: %d: %s", error_code, error_message); } }; // Elsewhere in the code... LeadersValueListener* listener = new LeadersValueListener(); firebase::Future<firebase::database::DataSnapshot> result = dbRef.GetReference("Leaders").AddValueListener(listener);
Das Ergebnis Future<DataSnapshot>
enthält die Daten am angegebenen Speicherort in der Datenbank zum Zeitpunkt des Ereignisses. Wenn Sie value()
für einen Snapshot aufrufen, wird ein Variant
mit den Daten zurückgegeben.
In diesem Beispiel wird auch die Methode OnCancelled
überschrieben, um zu prüfen, ob der Lesevorgang abgebrochen wurde. Ein Lesevorgang kann beispielsweise abgebrochen werden, wenn der Client keine Berechtigung zum Lesen von einem Firebase-Datenbankspeicherort hat. Die database::Error
gibt an, warum der Fehler aufgetreten ist.
Klasse „ChildListener“
Untergeordnete Ereignisse werden als Reaktion auf bestimmte Vorgänge ausgelöst, die für die untergeordneten Elemente eines Knotens ausgeführt werden, z. B. wenn ein neues untergeordnetes Element über die Methode PushChild()
hinzugefügt oder ein untergeordnetes Element über die Methode UpdateChildren()
aktualisiert wird. Jede dieser Methoden kann nützlich sein, um Änderungen an einem bestimmten Knoten in einer Datenbank zu beobachten. Ein Spiel kann diese Methoden beispielsweise zusammen verwenden, um die Aktivität in den Kommentaren einer Spielsitzung zu überwachen, wie unten dargestellt:
class SessionCommentsChildListener : public firebase::database::ChildListener { public: void OnChildAdded(const firebase::database::DataSnapshot& snapshot, const char* previous_sibling) override { // Do something with the data in snapshot ... } void OnChildChanged(const firebase::database::DataSnapshot& snapshot, const char* previous_sibling) override { // Do something with the data in snapshot ... } void OnChildRemoved( const firebase::database::DataSnapshot& snapshot) override { // Do something with the data in snapshot ... } void OnChildMoved(const firebase::database::DataSnapshot& snapshot, const char* previous_sibling) override { // Do something with the data in snapshot ... } void OnCancelled(const firebase::database::Error& error_code, const char* error_message) override { LogMessage("ERROR: SessionCommentsChildListener canceled: %d: %s", error_code, error_message); } }; // elsewhere .... SessionCommentsChildListener* listener = new SessionCommentsChildListener(); firebase::Future<firebase::database::DataSnapshot> result = dbRef.GetReference("GameSessionComments").AddChildListener(listener);
Der OnChildAdded
-Callback wird in der Regel verwendet, um eine Liste von Elementen in einer Firebase-Datenbank abzurufen. Der OnChildAdded
-Callback wird einmal für jedes vorhandene untergeordnete Element und dann jedes Mal aufgerufen, wenn dem angegebenen Pfad ein neues untergeordnetes Element hinzugefügt wird. Dem Listener wird ein Snapshot mit den Daten des neuen untergeordneten Elements übergeben.
Der OnChildChanged
-Callback wird immer dann aufgerufen, wenn ein untergeordneter Knoten geändert wird.
Das gilt auch für alle Änderungen an untergeordneten Knoten des untergeordneten Knotens. Sie wird in der Regel in Verbindung mit den Aufrufen OnChildAdded
und OnChildRemoved
verwendet, um auf Änderungen an einer Liste von Elementen zu reagieren. Der an den Listener übergebene Snapshot enthält die aktualisierten Daten für das untergeordnete Element.
Der OnChildRemoved
-Callback wird ausgelöst, wenn ein direkt untergeordnetes Element entfernt wird.
Sie wird in der Regel in Verbindung mit den Callbacks OnChildAdded
und OnChildChanged
verwendet. Der an den Callback übergebene Snapshot enthält die Daten für das entfernte untergeordnete Element.
Der OnChildMoved
-Callback wird immer dann ausgelöst, wenn der OnChildChanged
-Aufruf durch eine Aktualisierung erfolgt, die eine Neuordnung des untergeordneten Elements zur Folge hat. Sie wird mit Daten verwendet, die mit OrderByChild
oder OrderByValue
sortiert sind.
Daten sortieren und filtern
Mit der Klasse Realtime Database Query
können Sie Daten abrufen, die nach Schlüssel, Wert oder Wert eines untergeordneten Elements sortiert sind. Sie können das sortierte Ergebnis auch nach einer bestimmten Anzahl von Ergebnissen oder einem Bereich von Schlüsseln oder Werten filtern.
Daten sortieren
Wenn Sie sortierte Daten abrufen möchten, geben Sie zuerst eine der Order-by-Methoden an, um die Reihenfolge der Ergebnisse festzulegen:
Methode | Nutzung |
---|---|
OrderByChild() |
Sortiert die Ergebnisse nach dem Wert eines angegebenen untergeordneten Schlüssels. |
OrderByKey()
| Ergebnisse nach untergeordneten Schlüsseln sortieren. |
OrderByValue() |
Ergebnisse nach untergeordneten Werten sortieren. |
Sie können jeweils nur eine Order-by-Methode verwenden. Wenn Sie eine „order-by“-Methode mehrmals in derselben Abfrage aufrufen, wird ein Fehler ausgegeben.
Das folgende Beispiel zeigt, wie Sie ein Abo für eine nach Punktzahl sortierte Bestenliste abschließen können.
firebase::database::Query query = dbRef.GetReference("Leaders").OrderByChild("score"); // To get the resulting DataSnapshot either use query.GetValue() and poll the // future, or use query.AddValueListener() and register to handle the // OnValueChanged callback.
Dadurch wird ein firebase::Query
definiert, das in Kombination mit einem ValueListener den Client mit der Bestenliste in der Datenbank synchronisiert, sortiert nach der Punktzahl der einzelnen Einträge.
Weitere Informationen zum effizienten Strukturieren Ihrer Daten finden Sie unter Datenbank strukturieren.
Der Aufruf der Methode OrderByChild()
gibt den untergeordneten Schlüssel an, nach dem die Ergebnisse sortiert werden sollen. In diesem Fall werden die Ergebnisse nach dem Wert von "score"
in jedem untergeordneten Element sortiert. Weitere Informationen zur Sortierung anderer Datentypen finden Sie unter Sortierung von Abfragedaten.
Daten filtern
Um Daten zu filtern, können Sie beim Erstellen einer Abfrage eine beliebige der Limit- oder Bereichsmethoden mit einer Order-by-Methode kombinieren.
Methode | Nutzung |
---|---|
LimitToFirst() |
Legt die maximale Anzahl der Elemente fest, die ab dem Anfang der sortierten Ergebnisliste zurückgegeben werden sollen. |
LimitToLast() |
Legt die maximale Anzahl der Elemente fest, die vom Ende der sortierten Ergebnisliste zurückgegeben werden sollen. |
StartAt() |
Gibt Elemente zurück, die größer oder gleich dem angegebenen Schlüssel oder Wert sind, je nach gewählter „order-by“-Methode. |
EndAt() |
Gibt Elemente zurück, die kleiner oder gleich dem angegebenen Schlüssel oder Wert sind, je nach ausgewählter Sortierungsmethode. |
EqualTo() |
Gibt Elemente zurück, die dem angegebenen Schlüssel oder Wert entsprechen, je nach gewählter Sortiermethode. |
Im Gegensatz zu den Order-by-Methoden können Sie mehrere Limit- oder Range-Funktionen kombinieren.
Sie können beispielsweise die Methoden StartAt()
und EndAt()
kombinieren, um die Ergebnisse auf einen bestimmten Wertebereich zu beschränken.
Auch wenn es nur eine Übereinstimmung für die Anfrage gibt, ist der Snapshot weiterhin eine Liste, die nur ein Element enthält.
Anzahl der Ergebnisse begrenzen
Mit den Methoden LimitToFirst()
und LimitToLast()
können Sie eine maximale Anzahl von untergeordneten Elementen festlegen, die für einen bestimmten Callback synchronisiert werden sollen. Wenn Sie beispielsweise mit LimitToFirst()
ein Limit von 100 festlegen, erhalten Sie anfangs nur bis zu 100 OnChildAdded
-Callbacks. Wenn Sie weniger als 100 Elemente in Ihrer Firebase-Datenbank gespeichert haben, wird für jedes Element ein OnChildAdded
-Callback ausgelöst.
Wenn sich Elemente ändern, erhalten Sie OnChildAdded
-Callbacks für Elemente, die in die Abfrage aufgenommen werden, und OnChildRemoved
-Callbacks für Elemente, die aus der Abfrage entfernt werden. Die Gesamtzahl bleibt dabei immer bei 100.
Der folgende Code gibt beispielsweise den höchsten Punktestand einer Bestenliste zurück:
firebase::database::Query query = dbRef.GetReference("Leaders").OrderByChild("score").LimitToLast(1); // To get the resulting DataSnapshot either use query.GetValue() and poll the // future, or use query.AddValueListener() and register to handle the // OnValueChanged callback.
Nach Schlüssel oder Wert filtern
Mit StartAt()
, EndAt()
und EqualTo()
können Sie beliebige Start-, End- und Äquivalenzpunkte für Abfragen auswählen. Das kann nützlich sein, wenn Sie Daten paginieren oder Elemente mit untergeordneten Elementen mit einem bestimmten Wert suchen möchten.
So werden Abfragedaten sortiert
In diesem Abschnitt wird erläutert, wie Daten mit den einzelnen Order-by-Methoden in der Klasse Query
sortiert werden.
OrderByChild
Wenn Sie OrderByChild()
verwenden, werden Daten, die den angegebenen untergeordneten Schlüssel enthalten, so sortiert:
- Kinder mit einem
null
-Wert für den angegebenen untergeordneten Schlüssel werden zuerst angezeigt. - Als Nächstes folgen untergeordnete Elemente mit dem Wert
false
für den angegebenen untergeordneten Schlüssel. Wenn mehrere untergeordnete Elemente den Wertfalse
haben, werden sie lexikografisch nach Schlüssel sortiert. - Als Nächstes folgen untergeordnete Elemente mit dem Wert
true
für den angegebenen untergeordneten Schlüssel. Wenn mehrere untergeordnete Elemente den Werttrue
haben, werden sie lexikografisch nach Schlüssel sortiert. - Als Nächstes folgen untergeordnete Elemente mit einem numerischen Wert, sortiert in aufsteigender Reihenfolge. Wenn mehrere untergeordnete Elemente denselben numerischen Wert für den angegebenen untergeordneten Knoten haben, werden sie nach Schlüssel sortiert.
- Strings folgen auf Zahlen und werden lexikografisch in aufsteigender Reihenfolge sortiert. Wenn mehrere untergeordnete Elemente denselben Wert für den angegebenen untergeordneten Knoten haben, werden sie lexikografisch nach Schlüssel sortiert.
- Objekte werden zuletzt angezeigt und lexikografisch nach Schlüssel in aufsteigender Reihenfolge sortiert.
OrderByKey
Wenn Sie OrderByKey()
zum Sortieren Ihrer Daten verwenden, werden die Daten in aufsteigender Reihenfolge nach Schlüssel zurückgegeben.
- Untergeordnete Elemente mit einem Schlüssel, der als 32-Bit-Ganzzahl geparst werden kann, werden zuerst in aufsteigender Reihenfolge sortiert.
- Als Nächstes folgen Kinder mit einem Stringwert als Schlüssel, die lexikografisch in aufsteigender Reihenfolge sortiert sind.
OrderByValue
Bei Verwendung von OrderByValue()
werden untergeordnete Elemente nach ihrem Wert sortiert. Die Sortierkriterien sind dieselben wie in OrderByChild()
, mit der Ausnahme, dass der Wert des Knotens anstelle des Werts eines angegebenen untergeordneten Schlüssels verwendet wird.