Conteggio dei documenti con query di aggregazione
Una query di aggregazione elabora i dati di più voci di indice per restituire un singolo valore di riepilogo.
Firestore supporta la query di aggregazione count()
. count()
consente di determinare il numero di documenti in una raccolta o query. Il server calcola il conteggio e trasmette solo il risultato, un singolo numero intero, di nuovo alla tua app, risparmiando sia le letture dei documenti fatturati che i byte trasferiti, rispetto all'esecuzione della query completa.
Le query di aggregazione si basano sulla configurazione dell'indice esistente che le tue query utilizzano già e scalano proporzionalmente in base al numero di voci dell'indice scansionate. Ciò significa che le aggregazioni di set di dati di piccole e medie dimensioni vengono eseguite entro 20-40 ms, anche se la latenza aumenta con il numero di elementi conteggiati.
Utilizza l'aggregazione count()
Fai riferimento ai dati di esempio che abbiamo configurato in Ottenere i dati.
La seguente aggregazione count()
restituisce il numero totale di città nella
raccolta cities
.
Versione 9 web
const coll = collection(db, "cities"); const snapshot = await getCountFromServer(coll); console.log('count: ', snapshot.data().count);
Swift
let query = db.collection("cities") let countQuery = query.count do { let snapshot = try await countQuery.getAggregation(source: .server) print(snapshot.count) } catch { print(error); }
Objective-C
FIRCollectionReference *query = [self.db collectionWithPath:@"cities"]; [query.count aggregationWithSource:FIRAggregateSourceServer completion:^(FIRAggregateQuerySnapshot *snapshot, NSError *error) { if (error != nil) { NSLog(@"Error fetching count: %@", error); } else { NSLog(@"Cities count: %@", snapshot.count); } }];
Java
Android
Query query = db.collection("cities"); AggregateQuery countQuery = query.count(); countQuery.get(AggregateSource.SERVER).addOnCompleteListener(new OnCompleteListener<AggregateQuerySnapshot>() { @Override public void onComplete(@NonNull Task<AggregateQuerySnapshot> task) { if (task.isSuccessful()) { // Count fetched successfully AggregateQuerySnapshot snapshot = task.getResult(); Log.d(TAG, "Count: " + snapshot.getCount()); } else { Log.d(TAG, "Count failed: ", task.getException()); } } });
Kotlin+KTX
Android
val query = db.collection("cities") val countQuery = query.count() countQuery.get(AggregateSource.SERVER).addOnCompleteListener { task -> if (task.isSuccessful) { // Count fetched successfully val snapshot = task.result Log.d(TAG, "Count: ${snapshot.count}") } else { Log.d(TAG, "Count failed: ", task.getException()) } }
Java
Android
CollectionReference collection = db.collection("cities"); AggregateQuery countQuery = collection.count(); countQuery.get(AggregateSource.SERVER).addOnCompleteListener(task -> { if (task.isSuccessful()) { AggregateQuerySnapshot snapshot = task.getResult(); Log.d(TAG, "Count: " + snapshot.getCount()); } else { Log.d(TAG, "Count failed: ", task.getException()); } });
Java
CollectionReference collection = db.collection("cities"); AggregateQuerySnapshot snapshot = collection.count().get().get(); System.out.println("Count: " + snapshot.getCount());
Node.js
const collectionRef = db.collection('cities'); const snapshot = await collectionRef.count().get(); console.log(snapshot.data().count);
L'aggregazione count()
prende in considerazione eventuali filtri nella query ed eventuali
clausole limit
. Ad esempio, la seguente aggregazione restituisce il conteggio del
numero di città in cui state
è uguale a CA
.
Versione 9 web
const coll = collection(db, "cities"); const q = query(coll, where("state", "==", "CA")); const snapshot = await getCountFromServer(q); console.log('count: ', snapshot.data().count);
Swift
let query = db.collection("cities").whereField("state", isEqualTo: "CA") let countQuery = query.count do { let snapshot = try await countQuery.getAggregation(source: .server) print(snapshot.count) } catch { print(error); }
Objective-C
FIRQuery *query = [[self.db collectionWithPath:@"cities"] queryWhereField:@"state" isEqualTo:@"CA"]; [query.count aggregationWithSource:FIRAggregateSourceServer completion:^(FIRAggregateQuerySnapshot *snapshot, NSError *error) { if (error != nil) { NSLog(@"Error fetching count: %@", error); } else { NSLog(@"Cities count: %@", snapshot.count); } }];
Java
Android
Query query = db.collection("cities").whereEqualTo("state", "CA"); AggregateQuery countQuery = query.count(); countQuery.get(AggregateSource.SERVER).addOnCompleteListener(new OnCompleteListener<AggregateQuerySnapshot>() { @Override public void onComplete(@NonNull Task<AggregateQuerySnapshot> task) { if (task.isSuccessful()) { // Count fetched successfully AggregateQuerySnapshot snapshot = task.getResult(); Log.d(TAG, "Count: " + snapshot.getCount()); } else { Log.d(TAG, "Count failed: ", task.getException()); } } });
Kotlin+KTX
Android
val query = db.collection("cities").whereEqualTo("state", "CA") val countQuery = query.count() countQuery.get(AggregateSource.SERVER).addOnCompleteListener { task -> if (task.isSuccessful) { // Count fetched successfully val snapshot = task.result Log.d(TAG, "Count: ${snapshot.count}") } else { Log.d(TAG, "Count failed: ", task.getException()) } }
Java
Android
CollectionReference collection = db.collection("cities"); Query query = collection.whereEqualTo("state", "CA"); AggregateQuery countQuery = query.count(); countQuery.get(AggregateSource.SERVER).addOnCompleteListener(task -> { if (task.isSuccessful()) { AggregateQuerySnapshot snapshot = task.getResult(); Log.d(TAG, "Count: " + snapshot.getCount()); } else { Log.d(TAG, "Count failed: ", task.getException()); } });
Java
CollectionReference collection = db.collection("cities"); Query query = collection.whereEqualTo("state", "CA"); AggregateQuerySnapshot snapshot = query.count().get().get(); System.out.println("Count: " + snapshot.getCount());
Node.js
const collectionRef = db.collection('cities'); const query = collectionRef.where('state', '==', 'CA'); const snapshot = await query.count().get(); console.log(snapshot.data().count);
Le regole di sicurezza di Firestore funzionano allo stesso modo sulle query di aggregazione di count()
rispetto alle normali query che restituiscono documenti. In altre parole, se e solo se le regole consentono ai client di eseguire determinate query del gruppo di raccolta o raccolta, i clienti possono eseguire l'aggregazione count()
anche su tali query. Scopri di più su come le regole di sicurezza di Firestore interagiscono con le query.
Limitazioni
Tieni presente le seguenti limitazioni per la query di aggregazione count()
:
Al momento, le query di aggregazione di
count()
sono supportate solo tramite la risposta diretta del server. Le query vengono pubblicate solo dal backend Firestore, ignorando la cache locale e gli aggiornamenti presenti nel buffer. Questo comportamento è identico a quello delle operazioni eseguite all'interno delle transazioni di Firestore. Al momento non puoi utilizzare le querycount()
con listener in tempo reale e query offline.Se l'aggregazione di
count()
non può risolversi entro 60 secondi, restituisce un erroreDEADLINE_EXCEEDED
. Le prestazioni dipendono dalla configurazione dell'indice e dalle dimensioni del set di dati.Se l'operazione non può essere completata entro il termine di 60 secondi, una possibile soluzione è utilizzare i contatori per set di dati di grandi dimensioni.
L'aggregazione
count()
legge dalle voci dell'indice e conteggia solo i campi indicizzati.L'aggiunta di una clausola
OrderBy
alla query limita il numero alle entità in cui esiste la proprietà di ordinamento.
Prezzi
I prezzi di count()
dipendono dal numero di voci di indice corrispondenti alla query. Ti viene addebitato un numero ridotto di letture per un numero elevato di voci corrispondenti.
Visualizza informazioni sui prezzi più dettagliate.