Query
QuerySnapshot, QueryDocumentSnapshot
the query snapshot contains zero or more documents.
Firestore answers to a query with a query snapshot, regardless if there are matches or not. The documents it contains, if any, are wrapped individually as a QueryDocumentSnapshot, which is an API that extends DocumentSnapshot and that is mostly the same. The difference in this scenario is that they are always non-empty.
We check if the query snapshot is empty
if (querySnaptshot.empty) {
return []
}
The (non-empty) queryDocumentSnapshots, are available at docs as an array. A queryDocumentSnapshot guarantees it contains an actual document, due to the context in which the docs array has been built, with only non-empty snapshots. For simplicity, we may call it a docSnapshot and we use the DocumentSnapshot API.
querySnaptshot.docs
const cats = querySnaptshot.docs.map((docSnapshot) => docSnapshot.data())
Query
Read data
read several documents
- we provide a Query.
- We receive a querySnapshot
getDocs(query(..))
collection(..).where(..).orderBy(..).limit(..).get()
note on getting all documents
A bare collection ref is accepted as a query, and we receive all documents. It's rarerly used as it's often better to:
specify some order/sorting criteria
limit the number of documents
getDocs(collectionRef)
collectionRef.get()
Query
we query a specific part of the collection, aka the documents that match a criteria or a set of criteria.
const q = query(collectionRef, where(..), where(..), orderBy(..), limit(..))
const q = collection(..).where(..).orderBy(..).limit(..)
where
filter documents based on a property whose value must follow a rule. It filters out the document who do not have this property.
where(propertyName, operator, value)
where("id", "==", user.id)
operator (provided as string)
<
<=
>
>=
==
!=
array-contains // the property is an array and contains the specified value
array-contains-any // the property is an array and contains at least one of the specified values. contains A or B or C ..
in // the property is equal to at least one of the specified value. is equal to A or B or C
not-in // the property must be different from all the specified values. not A and not B and not C.
orderBy
by default, ascending
sort the fetched document by a criteria
orderBy(propertyName, orderDirection)
orderBy("postCount") // ascending
orderBy("postCount", "asc")
orderBy("postCount", "desc")
limit
get at most n documents
limit(n)
limit(5)
startAt, startAfter
When doing pagingation, we either the store:
the count n of document we already fetched
the snapshot docSnapshot of the document we fetched last
startAt(n)
startAt(docSnapshot)
startAfter(n) // does not include n
startAfter(docSnapshot) // does not include docSnapshot
Run the query
We assume we will receive one or more documents, as such, we use the getDocs function
getDocs(query)
query.get()
Real time listener
we may target
a single document with its reference
several documents through a query
we provide a callback as for what to do with the query snapshot or the document snapshot.
query real time read
v9
const unsub = onSnapshot(query, (qs) => {
const documents = qs.docs.map((docSnapshot) => docSnapshot.data())
setMessages(documents)
})
document real time read
const unsub = onSnapshot(docRef, (docSnapshot) => {
console.log("Current data: ", docSnapshot.data())
})