Querying KiiObjects
You can run a conditional query for KiiObjects in a bucket. For example: a query that gets up to 10 KiiObjects that have a value of more than 10 for a key named "count" in descending order.
See Query Examples for various query examples.
Executing a KiiObject query
Defining a query condition
You can define a query condition using the following methods of the KiiClause
class:
Method | Query condition |
---|---|
equals() | Match when the field value is equal to the specified value. |
notEquals() | Match when the field value is not equal to the specified value. The condition does not match if the specified field does not exist. |
greaterThan() | Match when the field value is greater than the specified value. |
greaterThanOrEqual() | Match when the field value is greater than or equal to the specified value. |
lessThan() | Match when the field value is less than the specified value. |
lessThanOrEqual() | Match when the field value is less than or equal to the specified value. |
inWithIntValue(), inWithLongValue(), inWithDoubleValue(), inWithStringValue() | Match when the field value is equal to one of the specified values. Up to 200 values can be specified. The method needs to match with the type of the JSON field. |
startsWith() | Match when the field value (String) starts with the specified string. |
geoBox() | Match when the field value (GeoPoint) is inside the specified GeoBox (rectangular area). |
geoDistance() | Match when the field value (GeoPoint) is inside the specified GeoDistance (circular area). |
hasField() | Match when the field has the specified field type (currently supported types are FieldType.String , FieldType.Integer , FieldType.Decimal , and FieldType.Boolean ). |
You can concatenate multiple query conditions using the following methods of the KiiClause
class:
Method | How to concatenate |
---|---|
and() | Concatenate query conditions with an "AND" operator. |
or() | Concatenate query conditions with an "OR" operator. |
not() | Concatenate query conditions with a "NOT" operator. The argument is a KiiClause instance. It can be a single-condition clause or a multiple-condition clause concatenated by the and() or or() method. |
See the Javadoc to learn more about KiiClause
class.
Querying with a not()
clause can decrease performance but you might be able to transform the clause to avoid a not operator. See Transforming a not clause for more information.
Creating a query instance and executing a query
To execute a query, you first need to create a query instance. This is done by creating a KiiQuery
instance with a KiiClause
instance that contains a query condition. If you create a KiiQuery
instance without a KiiClause
instance, the query will return all KiiObjects in the target bucket (this is equivalent to an "all" query).
You can fine-tune a query instance by calling the following methods.
- sortByAsc(): sorts query results in ascending order by the specified field.
- sortByDesc(): sorts query results in descending order by the specified field.
- setLimit(): sets the maximum number of KiiObjects returned as query results on the best-effort basis. The maximum value is 200.
The detailed specification of the query feature is as below:
The
sortByAsc()
andsortByDesc()
methods can be applied to only one field.If neither
sortByAsc()
norsortByDesc()
method is specified, the query results will be in arbitrary order. If thesetLimit()
method is not executed, the maximum number of KiiObjects returned by a query may be up to 200 by default.The
setLimit()
method is on a best-effort basis. For example, Kii Cloud does not guarantee to return all 40 KiiObjects when the limit is set to 40 and there are more than 40 KiiObjects that satisfy the query condition (this could happen for performance optimization purposes).If you are going to have more than 200 query results, you will need to use the pagination to divide them into several pages.
The
sortByAsc()
andsortByDesc()
methods sort query results by an integer field in numerical order and by a string field in dictionary order.Query and sort do not work properly if the type of the field values is not consistent among KiiObjects.
Strings are queried in a case-sensitive manner. For example, if you query with a string of "alice", "Alice" stored in a KiiObject will not be returned.
Query and sort might not work as expected for real number fields. Real numbers whose fractional part is zero are treated as integers. Therefore, for example, 1.0 will be indexed as an integer 1 while 1.1 will be indexed as a real number 1.1. You cannot get the expected result because the difference between the different types of values will not be correctly evaluated. If you need to query or sort KiiObjects with a real number field, convert real numbers to integers by multiplying them with 10, 100, and so forth. Then save the converted integers in an integer field to use when you run a query.
Only the first-level fields within the JSON expression can be queried. You cannot get fields at the subsequent levels because fields at those levels are not indexed.
When you are using an "in" method (e.g.,
inWithIntValue()
), make sure to use the correct method that matches with the type of the JSON field to be queried. For example, theinWithStringValue()
method does not get{"id" : 123}
(you need to use the method for the numeric value such as theinWithIntValue()
method). You cannot use theinWithDoubleValue()
method for a field that can have a decimal or an integer.Queryable fields must have the field name up to 250 characters and a value (String) up to 190 characters. Key-value pairs that exceed these limits will not be returned by any query using the field.
To execute a query for KiiObjects, use the query()
method of the target bucket with a query instance.
See the Javadoc to learn more about the KiiQuery
class.
The performance of query and sort operations can deteriorate if there are numerous KiiObjects. See Performance for more information.
Using predefined keys for query
In addition to key-value pairs created by your mobile app, you can use predefined keys for query.
Predefined keys include various fields such as the KiiObject ID and created time. For the list of predefined keys, see Predefined keys.
Getting query results
Query results will be returned in a KiiQueryResult
instance. Its contents can be obtained by calling the getResult()
method. This will give you a list of KiiObjects
that match the query condition.
If the results are split across multiple pages (e.g. The limit is set to 10 and the query returned 30 KiiObjects), the list of KiiObjects
returned by the getResult()
method will contain only the first 10 KiiObjects. To get the next 10 KiiObjects, use the pagination feature as follows:
- Call the
getNextQueryResult()
method to get the next result set. - Call the
getResult()
method to get the next 10KiiObjects
.
The SDK might indicate that there are more KiiObjects when actually there are not any, that is to say, the SDK might return true for the result.hasNext()
method. It might happen when the number of KiiObjects returned from the server at a time and the number of KiiObjects that meet the query condition are the same. You should be aware that an empty result might be returned when an attempt is made to get a next page.
You need to handle the paging by yourself if you want to show a fixed amount of query results at a time, for example on the Web. The query results can be obtained only in the forward direction, and the number of results may not be constant because the query mechanism works on the best-effort basis. You might want to get the number of KiiObjects first and uses this number to control the paging.
See the Javadoc to learn more about the KiiQueryResult
class.