Cloud Firestore provides powerful query functionality for specifying which documents you want to retrieve from a collection. These queries can also be used with either get()
or addSnapshotListener()
, as described in Get Data and Get Realtime Updates.
Example data
To get started, write some data about cities so we can look at different ways to read it back:
[[ citiesRef documentWithPath :@ "SF" ] setData :@{
@ "name" : @ "San Francisco" ,
@ "state" : @ "CA" ,
@ "country" : @ "USA" ,
@ "capital" : @( NO ),
@ "population" : @ 860000
}];
[[ citiesRef documentWithPath :@ "LA" ] setData :@{
@ "name" : @ "Los Angeles" ,
@ "state" : @ "CA" ,
@ "country" : @ "USA" ,
@ "capital" : @( NO ),
@ "population" : @ 3900000
}];
[[ citiesRef documentWithPath :@ "DC" ] setData :@{
@ "name" : @ "Washington D.C." ,
@ "country" : @ "USA" ,
@ "capital" : @( YES ),
@ "population" : @ 680000
}];
[[ citiesRef documentWithPath :@ "TOK" ] setData :@{
@ "name" : @ "Tokyo" ,
@ "country" : @ "Japan" ,
@ "capital" : @( YES ),
@ "population" : @ 9000000
}];
[[ citiesRef documentWithPath :@ "BJ" ] setData :@{
@ "name" : @ "Beijing" ,
@ "country" : @ "China" ,
@ "capital" : @( YES ),
@ "population" : @ 21500000
}];
Simple queries
The following query returns all cities with state CA
:
FIRCollectionReference * citiesRef = [ self . db collectionWithPath :@ "cities" ];
// Create a query against the collection.
FIRQuery * query = [ citiesRef queryWhereField :@ "state" isEqualTo :@ "CA" ];
The following query returns all the capital cities:
[[ self . db collectionWithPath :@ "cities" ] queryWhereField :@ "capital" isEqualTo : @YES ];
The where()
method takes three parameters: a field to filter on, a comparison operation, and a value. The comparison can be <
, <=
, ==
, >
, or >=
. For iOS, Android, and Java, the comparison operator is explicitly named in the method.
Some example filters:
[ citiesRef queryWhereField :@ "population" isLessThan :@ 100000 ];
[ citiesRef queryWhereField :@ "name" isGreaterThanOrEqualTo :@ "San Francisco" ];
Compound queries
You can also chain multiple where()
methods to create more specific queries (logical AND
). However, to combine the equality operator (==
) with a range comparison (<
, <=
, >
, or >=
), make sure to create a custom index.
queryWhereField :@ "name" isGreaterThanOrEqualTo :@ "Denver" ];
[[ citiesRef queryWhereField :@ "state" isEqualTo :@ "CA" ]
queryWhereField :@ "population" isLessThan :@ 1000000 ];
Additionally, you can only perform range comparisons (<
, <=
, >
, >=
) on a single field:
Valid: Range filters on only one field
queryWhereField :@ "state" isLessThanOrEqualTo :@ "IN" ];
[[ citiesRef queryWhereField :@ "state" isEqualTo :@ "CA" ]
queryWhereField :@ "population" isGreaterThan :@ 1000000 ];
Invalid: Range filters on different fields
queryWhereField :@ "population" isGreaterThan :@ 1000000 ];