Taxonomy

View as Markdown

Taxonomy

A taxonomy arranges the content of a stack into a hierarchy of terms that entries carry. The Taxonomy class builds one query on those terms and returns the matching entries across every content type. Use this class to

  • match entries tagged with given terms
  • match entries by the position of a term in the hierarchy
  • combine conditions on several taxonomies

Call the taxonomy method of the Stack class to get an instance. Each call returns a new Taxonomy with an empty query. Chain one or more filters, then call find.

above

above matches entries tagged with any ancestor of a term, but not with the term itself.

NameTypeDescription
taxonomy (required)String

Taxonomy field path, such as taxonomies.color.

Default: Not applicable
termUid (required)String

UID of the target term.

Default: Not applicable

Returns: Taxonomy. The same taxonomy query, for chaining.

Validation

  • There is no client-side validation. A null term UID sends an empty condition, {"<taxonomy>": {}}.
  • A null field path throws NullPointerException from the org.json package, because a JSON object rejects a null key.
  • An invalid value surfaces as an Error in the callback when find sends the request. See How find reports results and errors on the Taxonomy class page.

Additional Resource Refer to Content Delivery API Errors for the full error code list.

Behavior

  • Client-side only. above records the condition {"<taxonomy>": {"$above": "<term>"}} and sends no request.
  • For the term navy_blue, entries tagged with its parent blue match, and entries tagged only navy_blue do not.
  • above sends no depth, so the API applies its default of 10 levels, as the Above Operator reference states.
  • A second filter on the same field path replaces the condition.

Example

Basic usage: match the terms above a term, without the term itself

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Stack;
import com.contentstack.sdk.Taxonomy;
import com.contentstack.sdk.TaxonomyCallback;
import org.json.JSONArray;
import org.json.JSONObject;

public class FindAbove {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        Taxonomy taxonomy = stack.taxonomy().above("taxonomies.color", "navy_blue");

        try {
            taxonomy.find(new TaxonomyCallback() {
                @Override
                public void onResponse(JSONObject response, Error error) {
                    if (error != null) {
                        // The API rejected the request
                        System.out.println("Request failed: " + error.getErrorCode() + " " + error.getErrorMessage());
                        return;
                    }
                    JSONArray entries = response.optJSONArray("entries");
                    for (int i = 0; entries != null && i < entries.length(); i++) {
                        System.out.println(entries.getJSONObject(i).optString("title"));
                    }
                }
            });
        } catch (RuntimeException e) {
            // Thrown when the request does not complete, or the body is not JSON
            System.out.println("Request did not complete: " + e.getMessage());
        }
    }
}

and

and matches entries that satisfy every one of the given taxonomy conditions.

NameTypeDescription
listOfItems (required)List<JSONObject>

Conditions that an entry must all satisfy.

Default: Not applicable

Returns: Taxonomy. The same taxonomy query, for chaining.

Validation

  • There is no client-side validation of the conditions.
  • Throws NullPointerException if listOfItems is null, because and converts the list to a string.
  • An invalid value surfaces as an Error in the callback when find sends the request. See How find reports results and errors on the Taxonomy class page.

Additional Resource Refer to Content Delivery API Errors for the full error code list.

Behavior

  • Known issue: and sends its conditions as one JSON string, not as an array. The $and value then does not have the shape the AND Operator (Taxonomy) reference describes. To match every condition, use the and method of the Query class on one content type, as the second example shows.
  • Client-side only. and records the condition {"$and": "<conditions as text>"} and sends no request.
  • and owns the fixed $and key, so a second and call replaces the first.
  • The Query class reaches the same taxonomy conditions through /content_types/{content_type_uid}/entries, one of the two taxonomy query endpoints that the Taxonomy section of the Queries reference lists.

Example

Basic usage: pass two conditions

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Stack;
import com.contentstack.sdk.Taxonomy;
import com.contentstack.sdk.TaxonomyCallback;
import org.json.JSONArray;
import org.json.JSONObject;

import java.util.Arrays;

public class FindEntriesAndTerms {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        JSONObject color = new JSONObject().put("taxonomies.color", "black");
        JSONObject category = new JSONObject().put("taxonomies.category", "mobile");

        // See the Known issue above: the SDK sends this list as a string.
        Taxonomy taxonomy = stack.taxonomy().and(Arrays.asList(color, category));

        try {
            taxonomy.find(new TaxonomyCallback() {
                @Override
                public void onResponse(JSONObject response, Error error) {
                    if (error != null) {
                        // The API rejected the request
                        System.out.println("Request failed: " + error.getErrorCode() + " " + error.getErrorMessage());
                        return;
                    }
                    JSONArray entries = response.optJSONArray("entries");
                    for (int i = 0; entries != null && i < entries.length(); i++) {
                        System.out.println(entries.getJSONObject(i).optString("title"));
                    }
                }
            });
        } catch (RuntimeException e) {
            // Thrown when the request does not complete, or the body is not JSON
            System.out.println("Request did not complete: " + e.getMessage());
        }
    }
}

Workaround: match every condition with a Query on one content type

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Entry;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Query;
import com.contentstack.sdk.QueryResult;
import com.contentstack.sdk.QueryResultsCallBack;
import com.contentstack.sdk.ResponseType;
import com.contentstack.sdk.Stack;

import java.util.Arrays;

public class MatchAllTermsWithQuery {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        Query colorQuery = stack.contentType("<CONTENT_TYPE_UID>").query().where("taxonomies.color", "black");
        Query categoryQuery = stack.contentType("<CONTENT_TYPE_UID>").query().where("taxonomies.category", "mobile");

        // Query.and sends $and as an array of conditions.
        Query query = stack.contentType("<CONTENT_TYPE_UID>").query().and(Arrays.asList(colorQuery, categoryQuery));
        query.find(new QueryResultsCallBack() {
            @Override
            public void onCompletion(ResponseType responseType, QueryResult queryresult, Error error) {
                if (error != null) { System.out.println(error.getErrorMessage()); return; }
                for (Entry entry : queryresult.getResultObjects()) {
                    System.out.println(entry.getTitle());
                }
            }
        });
    }
}

below

below matches entries tagged with any descendant of a term, but not with the term itself.

NameTypeDescription
taxonomy (required)String

Taxonomy field path, such as taxonomies.color.

Default: Not applicable
termsUid (required)String

UID of the target term.

Default: Not applicable

Returns: Taxonomy. The same taxonomy query, for chaining.

Validation

  • There is no client-side validation. A null term UID sends an empty condition, {"<taxonomy>": {}}.
  • A null field path throws NullPointerException from the org.json package, because a JSON object rejects a null key.
  • An invalid value surfaces as an Error in the callback when find sends the request. See How find reports results and errors on the Taxonomy class page.

Additional Resource Refer to Content Delivery API Errors for the full error code list.

Behavior

  • Client-side only. below records the condition {"<taxonomy>": {"$below": "<term>"}} and sends no request.
  • For the term blue, entries tagged navy_blue or sky_blue match, and entries tagged only blue do not.
  • below sends no depth, so the API applies its default of 10 levels, as the Below Operator reference states.
  • A second filter on the same field path replaces the condition.

Example

Basic usage: match the terms below a term, without the term itself

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Stack;
import com.contentstack.sdk.Taxonomy;
import com.contentstack.sdk.TaxonomyCallback;
import org.json.JSONArray;
import org.json.JSONObject;

public class FindBelow {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        Taxonomy taxonomy = stack.taxonomy().below("taxonomies.color", "blue");

        try {
            taxonomy.find(new TaxonomyCallback() {
                @Override
                public void onResponse(JSONObject response, Error error) {
                    if (error != null) {
                        // The API rejected the request
                        System.out.println("Request failed: " + error.getErrorCode() + " " + error.getErrorMessage());
                        return;
                    }
                    JSONArray entries = response.optJSONArray("entries");
                    for (int i = 0; entries != null && i < entries.length(); i++) {
                        System.out.println(entries.getJSONObject(i).optString("title"));
                    }
                }
            });
        } catch (RuntimeException e) {
            // Thrown when the request does not complete, or the body is not JSON
            System.out.println("Request did not complete: " + e.getMessage());
        }
    }
}

equalAbove

equalAbove matches entries tagged with a term or with any of its ancestor terms.

NameTypeDescription
taxonomy (required)String

Taxonomy field path, such as taxonomies.color.

Default: Not applicable
termUid (required)String

UID of the target term.

Default: Not applicable

Returns: Taxonomy. The same taxonomy query, for chaining.

Validation

  • There is no client-side validation. A null term UID sends an empty condition, {"<taxonomy>": {}}.
  • A null field path throws NullPointerException from the org.json package, because a JSON object rejects a null key.
  • An invalid value surfaces as an Error in the callback when find sends the request. See How find reports results and errors on the Taxonomy class page.

Additional Resource Refer to Content Delivery API Errors for the full error code list.

Behavior

  • Client-side only. equalAbove records the condition {"<taxonomy>": {"$eq_above": "<term>"}} and sends no request.
  • For the term navy_blue, entries tagged navy_blue or its parent blue match.
  • equalAbove sends no depth, so the API applies its default of 10 levels, as the Equal and Above Operator reference states.
  • A second filter on the same field path replaces the condition.

Example

Basic usage: match a term and every term above it

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Stack;
import com.contentstack.sdk.Taxonomy;
import com.contentstack.sdk.TaxonomyCallback;
import org.json.JSONArray;
import org.json.JSONObject;

public class FindEqualAbove {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        Taxonomy taxonomy = stack.taxonomy().equalAbove("taxonomies.color", "navy_blue");

        try {
            taxonomy.find(new TaxonomyCallback() {
                @Override
                public void onResponse(JSONObject response, Error error) {
                    if (error != null) {
                        // The API rejected the request
                        System.out.println("Request failed: " + error.getErrorCode() + " " + error.getErrorMessage());
                        return;
                    }
                    JSONArray entries = response.optJSONArray("entries");
                    for (int i = 0; entries != null && i < entries.length(); i++) {
                        System.out.println(entries.getJSONObject(i).optString("title"));
                    }
                }
            });
        } catch (RuntimeException e) {
            // Thrown when the request does not complete, or the body is not JSON
            System.out.println("Request did not complete: " + e.getMessage());
        }
    }
}

equalAndBelow

equalAndBelow matches entries tagged with a term or with any of its descendant terms.

NameTypeDescription
taxonomy (required)String

Taxonomy field path, such as taxonomies.color.

Default: Not applicable
termsUid (required)String

UID of the target term.

Default: Not applicable

Returns: Taxonomy. The same taxonomy query, for chaining.

Validation

  • There is no client-side validation. A null term UID sends an empty condition, {"<taxonomy>": {}}.
  • A null field path throws NullPointerException from the org.json package, because a JSON object rejects a null key.
  • An invalid value surfaces as an Error in the callback when find sends the request. See How find reports results and errors on the Taxonomy class page.

Additional Resource Refer to Content Delivery API Errors for the full error code list.

Behavior

  • Client-side only. equalAndBelow records the condition {"<taxonomy>": {"$eq_below": "<term>"}} and sends no request.
  • For the term blue, entries tagged blue, navy_blue or sky_blue all match.
  • equalAndBelow sends no depth, so the API applies its default of 10 levels, as the Equal and Below Operator reference states.
  • A second filter on the same field path replaces the condition.

Example

Basic usage: match a term and every term below it

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Stack;
import com.contentstack.sdk.Taxonomy;
import com.contentstack.sdk.TaxonomyCallback;
import org.json.JSONArray;
import org.json.JSONObject;

public class FindEqualAndBelow {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        Taxonomy taxonomy = stack.taxonomy().equalAndBelow("taxonomies.color", "blue");

        try {
            taxonomy.find(new TaxonomyCallback() {
                @Override
                public void onResponse(JSONObject response, Error error) {
                    if (error != null) {
                        // The API rejected the request
                        System.out.println("Request failed: " + error.getErrorCode() + " " + error.getErrorMessage());
                        return;
                    }
                    JSONArray entries = response.optJSONArray("entries");
                    for (int i = 0; entries != null && i < entries.length(); i++) {
                        System.out.println(entries.getJSONObject(i).optString("title"));
                    }
                }
            });
        } catch (RuntimeException e) {
            // Thrown when the request does not complete, or the body is not JSON
            System.out.println("Request did not complete: " + e.getMessage());
        }
    }
}

equalAndBelowWithLevel

equalAndBelowWithLevel is meant to match entries tagged with a term or with its descendants, down to a given depth.

NameTypeDescription
taxonomy (required)String

Taxonomy field path, such as taxonomies.color.

Default: Not applicable
termsUid (required)String

UID of the target term.

Default: Not applicable
level (required)int

Number of levels below the term to include.

Default: Not applicable

Returns: Taxonomy. The same taxonomy query, for chaining.

Validation

  • There is no client-side validation. equalAndBelowWithLevel accepts any int, including 0 and negative values.
  • A null field path throws NullPointerException from the org.json package, because a JSON object rejects a null key.
  • An invalid value surfaces as an Error in the callback when find sends the request. See How find reports results and errors on the Taxonomy class page.

Additional Resource Refer to Content Delivery API Errors for the full error code list.

Behavior

  • Known issue: equalAndBelowWithLevel writes the level into the term string, as {"$eq_below": "blue, level: 2"}, instead of sending a separate levels key. The API receives blue, level: 2 as the term UID. Use equalAndBelow for the default depth of 10 levels, or a Query with a levels condition, as the second example shows.
  • Client-side only. equalAndBelowWithLevel records the condition and sends no request.
  • The Equal and Below Operator reference documents the shape {"$eq_below": "<term>", "levels": <number>}.
  • A second filter on the same field path replaces the condition.

Example

Basic usage: pass a term and a depth

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Stack;
import com.contentstack.sdk.Taxonomy;
import com.contentstack.sdk.TaxonomyCallback;
import org.json.JSONArray;
import org.json.JSONObject;

public class FindEqualAndBelowWithLevel {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        // See the Known issue above: the SDK sends "blue, level: 2" as the term UID.
        Taxonomy taxonomy = stack.taxonomy().equalAndBelowWithLevel("taxonomies.color", "blue", 2);

        try {
            taxonomy.find(new TaxonomyCallback() {
                @Override
                public void onResponse(JSONObject response, Error error) {
                    if (error != null) {
                        // The API rejected the request
                        System.out.println("Request failed: " + error.getErrorCode() + " " + error.getErrorMessage());
                        return;
                    }
                    JSONArray entries = response.optJSONArray("entries");
                    for (int i = 0; entries != null && i < entries.length(); i++) {
                        System.out.println(entries.getJSONObject(i).optString("title"));
                    }
                }
            });
        } catch (RuntimeException e) {
            // Thrown when the request does not complete, or the body is not JSON
            System.out.println("Request did not complete: " + e.getMessage());
        }
    }
}

Workaround: send the levels key through a Query on one content type

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Entry;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Query;
import com.contentstack.sdk.QueryResult;
import com.contentstack.sdk.QueryResultsCallBack;
import com.contentstack.sdk.ResponseType;
import com.contentstack.sdk.Stack;
import org.json.JSONObject;

public class MatchTermToDepthWithQuery {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");

        // Build the documented shape: {"$eq_below": "blue", "levels": 2}
        JSONObject condition = new JSONObject().put("$eq_below", "blue").put("levels", 2);
        Query query = stack.contentType("<CONTENT_TYPE_UID>").query().where("taxonomies.color", condition);

        query.find(new QueryResultsCallBack() {
            @Override
            public void onCompletion(ResponseType responseType, QueryResult queryresult, Error error) {
                if (error != null) { System.out.println(error.getErrorMessage()); return; }
                for (Entry entry : queryresult.getResultObjects()) {
                    System.out.println(entry.getTitle());
                }
            }
        });
    }
}

exists

exists matches entries by whether they carry a value for a taxonomy field.

NameTypeDescription
taxonomy (required)String

Taxonomy field path, such as taxonomies.color.

Default: Not applicable
value (required)Boolean

true to match entries that carry the taxonomy.

Default: Not applicable

Returns: Taxonomy. The same taxonomy query, for chaining.

Validation

  • There is no client-side validation. A null value sends an empty condition, {"<taxonomy>": {}}.
  • A null field path throws NullPointerException from the org.json package, because a JSON object rejects a null key.
  • An invalid value surfaces as an Error in the callback when find sends the request. See How find reports results and errors on the Taxonomy class page.

Additional Resource Refer to Content Delivery API Errors for the full error code list.

Behavior

  • Client-side only. exists records the condition {"<taxonomy>": {"$exists": <value>}} and sends no request.
  • The Exists Operator reference documents the value true. exists sends false as given.
  • A second filter on the same field path replaces the condition.

Example

Basic usage: match entries that carry the color taxonomy

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Stack;
import com.contentstack.sdk.Taxonomy;
import com.contentstack.sdk.TaxonomyCallback;
import org.json.JSONArray;
import org.json.JSONObject;

public class FindEntriesWithTaxonomy {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        Taxonomy taxonomy = stack.taxonomy().exists("taxonomies.color", true);

        try {
            taxonomy.find(new TaxonomyCallback() {
                @Override
                public void onResponse(JSONObject response, Error error) {
                    if (error != null) {
                        // The API rejected the request
                        System.out.println("Request failed: " + error.getErrorCode() + " " + error.getErrorMessage());
                        return;
                    }
                    JSONArray entries = response.optJSONArray("entries");
                    for (int i = 0; entries != null && i < entries.length(); i++) {
                        System.out.println(entries.getJSONObject(i).optString("title"));
                    }
                }
            });
        } catch (RuntimeException e) {
            // Thrown when the request does not complete, or the body is not JSON
            System.out.println("Request did not complete: " + e.getMessage());
        }
    }
}

find

find retrieves the published entries that match the conditions chained on this taxonomy query.

NameTypeDescription
callback (required)TaxonomyCallback

Receives the response or the error. See Callbacks.

Default: Not applicable

Returns: void. The result arrives in the callback.

Validation

  • There is no client-side validation of the query. find sends whatever the filters recorded, including an empty query.
  • Throws NullPointerException if callback is null. find sends the request first, then fails when it calls the callback.
  • Throws RuntimeException when the request does not complete (timeout, DNS error, dropped connection), after the retries of the stack. The exception wraps the IOException, and the callback does not run.
  • Throws JSONException from the org.json package when the response body is not JSON. The callback does not run.
  • An API rejection does not throw.
    • The callback receives null and an Error with the error_message, error_code and errors values of the response body.
    • A missing message or detail becomes an empty string, and a missing code becomes 0.
    • Check error first in the callback, even inside a try block.

Additional Resource Refer to Content Delivery API Errors for the full error code list.

Behavior

  • find sends one request to Get all entries with defined taxonomies (GET /v3/taxonomies/entries). The recorded conditions travel as JSON in the query parameter, which the SDK URL-encodes.
  • find sends no other query parameter. The environment of the stack travels in the environment header only.
  • On success, response is the whole parsed response body, with the matching entries in its entries array. find does not convert entries to Entry objects.
  • find runs the request on the calling thread and calls the callback before it returns.
  • find leaves the conditions on the instance, so a second find call sends the same query again.
  • find does not call the onRequest and onResponse hooks of a ContentstackPlugin.

Limitations

  • Does not send locale, include_taxonomy_terms, limit or skip. Use a Query on one content type when you need those parameters. See the Query class page.
  • Does not page through the results. One call returns one response.

Example

Basic usage: return the entries tagged with a term

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Stack;
import com.contentstack.sdk.Taxonomy;
import com.contentstack.sdk.TaxonomyCallback;
import org.json.JSONArray;
import org.json.JSONObject;

import java.util.Arrays;

public class FindTaggedEntries {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        Taxonomy taxonomy = stack.taxonomy().in("taxonomies.<TAXONOMY_UID>", Arrays.asList("<TERM_UID>"));

        try {
            taxonomy.find(new TaxonomyCallback() {
                @Override
                public void onResponse(JSONObject response, Error error) {
                    if (error != null) {
                        // The API rejected the request
                        System.out.println("Request failed: " + error.getErrorCode() + " " + error.getErrorMessage());
                        return;
                    }
                    JSONArray entries = response.optJSONArray("entries");
                    for (int i = 0; entries != null && i < entries.length(); i++) {
                        System.out.println(entries.getJSONObject(i).optString("title"));
                    }
                }
            });
        } catch (RuntimeException e) {
            // Thrown when the request does not complete, or the body is not JSON
            System.out.println("Request did not complete: " + e.getMessage());
        }
    }
}

Error handling: print the code, message and detail of an API rejection

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Stack;
import com.contentstack.sdk.Taxonomy;
import com.contentstack.sdk.TaxonomyCallback;
import org.json.JSONObject;

public class FindErrorDetail {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        Taxonomy taxonomy = stack.taxonomy().equalAndBelow("taxonomies.<TAXONOMY_UID>", "<TERM_UID>");

        taxonomy.find(new TaxonomyCallback() {
            @Override
            public void onResponse(JSONObject response, Error error) {
                if (error != null) {
                    // getErrorDetail returns the errors object as a JSON string, or an empty string
                    System.out.println(error.getErrorCode() + " " + error.getErrorMessage() + " " + error.getErrorDetail());
                    return;
                }
                System.out.println(response.toString(2));
            }
        });
    }
}

Alternative form: pass the callback as a lambda

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Stack;
import com.contentstack.sdk.Taxonomy;

public class FindWithLambda {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        Taxonomy taxonomy = stack.taxonomy().exists("taxonomies.color", true);

        // TaxonomyCallback is an interface, so a lambda works here.
        taxonomy.find((response, error) -> {
            if (error != null) { System.out.println(error.getErrorMessage()); return; }
            System.out.println(response.optJSONArray("entries"));
        });
    }
}

in

in matches entries tagged with at least one of the given terms of a taxonomy.

NameTypeDescription
taxonomy (required)String

Taxonomy field path, such as taxonomies.color.

Default: Not applicable
listOfItems (required)List<String>

Term UIDs, any of which satisfies the condition.

Default: Not applicable

Returns: Taxonomy. The same taxonomy query, for chaining.

Validation

  • There is no client-side validation. in records an empty list as an empty $in array, and a null list the same way.
  • A null field path throws NullPointerException from the org.json package, because a JSON object rejects a null key.
  • An invalid value surfaces as an Error in the callback when find sends the request. See How find reports results and errors on the Taxonomy class page.

Additional Resource Refer to Content Delivery API Errors for the full error code list.

Behavior

  • Client-side only. in records the condition {"<taxonomy>": {"$in": [<terms>]}} and sends no request.
  • find sends the condition in the shape the IN Operator reference describes.
  • A second in call on the same field path replaces the first. List every term in one call instead.
  • A condition on another field path, from any filter, becomes a separate top-level key of the same query.

Example

Basic usage: match entries tagged with either of two terms

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Stack;
import com.contentstack.sdk.Taxonomy;
import com.contentstack.sdk.TaxonomyCallback;
import org.json.JSONArray;
import org.json.JSONObject;

import java.util.Arrays;

public class FindEntriesInTerms {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        Taxonomy taxonomy = stack.taxonomy().in("taxonomies.color", Arrays.asList("red", "yellow"));

        try {
            taxonomy.find(new TaxonomyCallback() {
                @Override
                public void onResponse(JSONObject response, Error error) {
                    if (error != null) {
                        // The API rejected the request
                        System.out.println("Request failed: " + error.getErrorCode() + " " + error.getErrorMessage());
                        return;
                    }
                    JSONArray entries = response.optJSONArray("entries");
                    for (int i = 0; entries != null && i < entries.length(); i++) {
                        System.out.println(entries.getJSONObject(i).optString("title"));
                    }
                }
            });
        } catch (RuntimeException e) {
            // Thrown when the request does not complete, or the body is not JSON
            System.out.println("Request did not complete: " + e.getMessage());
        }
    }
}

Edge case: a second call on the same field replaces the first

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Stack;
import com.contentstack.sdk.Taxonomy;
import com.contentstack.sdk.TaxonomyCallback;
import org.json.JSONArray;
import org.json.JSONObject;

import java.util.Arrays;

public class ReplaceInCondition {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        // Only the second condition survives, so this matches yellow alone.
        Taxonomy taxonomy = stack.taxonomy()
                .in("taxonomies.color", Arrays.asList("red"))
                .in("taxonomies.color", Arrays.asList("yellow"));

        taxonomy.find(new TaxonomyCallback() {
            @Override
            public void onResponse(JSONObject response, Error error) {
                if (error != null) { System.out.println(error.getErrorMessage()); return; }
                JSONArray entries = response.optJSONArray("entries");
                System.out.println((entries == null ? 0 : entries.length()) + " entries");
            }
        });
    }
}

or

or matches entries that satisfy at least one of the given taxonomy conditions.

NameTypeDescription
listOfItems (required)List<JSONObject>

Conditions, any of which an entry must satisfy.

Default: Not applicable

Returns: Taxonomy. The same taxonomy query, for chaining.

Validation

  • There is no client-side validation. or records an empty list, or a null list, as an empty $or array.
  • or does not check the conditions inside the list. A malformed condition reaches the API as given.
  • An invalid value surfaces as an Error in the callback when find sends the request. See How find reports results and errors on the Taxonomy class page.

Additional Resource Refer to Content Delivery API Errors for the full error code list.

Behavior

  • Client-side only. or records the condition {"$or": [<conditions>]} and sends no request.
  • Each JSONObject in the list is one condition, such as {"taxonomies.color": "red"}. find sends the list in the shape the OR Operator (Taxonomy) reference describes.
  • or owns the fixed $or key, so a second or call replaces the whole list. Put every condition in one call.

Example

Basic usage: match entries tagged with either of two terms in two taxonomies

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Stack;
import com.contentstack.sdk.Taxonomy;
import com.contentstack.sdk.TaxonomyCallback;
import org.json.JSONArray;
import org.json.JSONObject;

import java.util.Arrays;

public class FindEntriesOrTerms {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        JSONObject color = new JSONObject().put("taxonomies.color", "black");
        JSONObject size = new JSONObject().put("taxonomies.size", "small");
        Taxonomy taxonomy = stack.taxonomy().or(Arrays.asList(color, size));

        try {
            taxonomy.find(new TaxonomyCallback() {
                @Override
                public void onResponse(JSONObject response, Error error) {
                    if (error != null) {
                        // The API rejected the request
                        System.out.println("Request failed: " + error.getErrorCode() + " " + error.getErrorMessage());
                        return;
                    }
                    JSONArray entries = response.optJSONArray("entries");
                    for (int i = 0; entries != null && i < entries.length(); i++) {
                        System.out.println(entries.getJSONObject(i).optString("title"));
                    }
                }
            });
        } catch (RuntimeException e) {
            // Thrown when the request does not complete, or the body is not JSON
            System.out.println("Request did not complete: " + e.getMessage());
        }
    }
}

Edge case: a second call replaces the whole list

import com.contentstack.sdk.Contentstack;
import com.contentstack.sdk.Error;
import com.contentstack.sdk.Stack;
import com.contentstack.sdk.Taxonomy;
import com.contentstack.sdk.TaxonomyCallback;
import org.json.JSONArray;
import org.json.JSONObject;

import java.util.Arrays;

public class ReplaceOrCondition {
    public static void main(String[] args) throws IllegalAccessException {
        Stack stack = Contentstack.stack("<API_KEY>", "<DELIVERY_TOKEN>", "<ENVIRONMENT>");
        JSONObject black = new JSONObject().put("taxonomies.color", "black");
        JSONObject small = new JSONObject().put("taxonomies.size", "small");

        // Only the second list survives, so this matches small alone.
        Taxonomy taxonomy = stack.taxonomy()
                .or(Arrays.asList(black))
                .or(Arrays.asList(small));

        taxonomy.find(new TaxonomyCallback() {
            @Override
            public void onResponse(JSONObject response, Error error) {
                if (error != null) { System.out.println(error.getErrorMessage()); return; }
                JSONArray entries = response.optJSONArray("entries");
                System.out.println((entries == null ? 0 : entries.length()) + " entries");
            }
        });
    }
}