Class StructureQueryBuilder<B extends StructureQueryBuilder<B>>

Object
StructureQueryBuilder<B>
Direct Known Subclasses:
StructureQueryBuilder.Head, StructureQueryBuilder.Sub

@PublicApi public class StructureQueryBuilder<B extends StructureQueryBuilder<B>> extends Object

StructureQueryBuilder allows you to build a structure query with a fluent interface. You begin the building process with begin() and end it with StructureQueryBuilder.Head.end(); if the Java compiler accepts the resulting expression, it is also a syntactically valid StructuredJQL expression.

A structure query consists of constraints that select rows in a forest, connected with OR and AND; each constraint can be negated. A constraint can be either a basic or a relational constraint.

Working example (assumes that begin() is statically imported):

     Query typeEpic = JqlQueryBuilder.newBuilder().where().issueType("Epic").buildQuery();
     Query typeTask = JqlQueryBuilder.newBuilder().where().issueType("Task").buildQuery();
     Query versionQuery = JqlQueryBuilder.newBuilder().where().fixVersion("5.2.11", "6.0").buildQuery();
     Query unresolved = JqlQueryBuilder.newBuilder().where().unresolved().buildQuery();
 
     StructureQuery q1 = begin().jql(unresolved).end();
     StructureQuery q2 = begin().root().end();
     StructureQuery q3 = begin().parent.is.empty().end();
     StructureQuery q4 = begin().child.in.issueKeys("TS-129", "TS-239").end();
     StructureQuery q5 = begin().child.of.issueKeys("TS-129", "TS-239").end();
     StructureQuery q6 = begin().ancestor.or().issue.in.jql(versionQuery).end();
     StructureQuery q7 = begin().issue.or().descendant.of.jql(versionQuery).end();
     StructureQuery q8 = begin().self.or().sibling.of.sub().parent.of.issueKey("TS-129").endsub().end();
     StructureQuery q9 = begin().child.of.sub().child.of.root().endsub().end();
     StructureQuery q10 = begin().prevSibling.is.sub().empty().or.jql(unresolved).endsub().end();
     StructureQuery q11 = begin().sub().root().or.jql(typeEpic).endsub().and.descendant.in.jql(unresolved).end();
     StructureQuery q12 = begin().parent.in.jql(typeEpic).and.issue.notIn.jql(typeTask).end();
     StructureQuery q13 = begin().self.or().descendant.of.constraint("folder", "Future tasks").end(); 
 

Explanation:

  1. Query q1 matches all unresolved issues in a forest.
  2. Queries q2 and q3 both match all top-level rows.
  3. Query q4 matches parents of issue TS-129 and parents of issue TS-239.
  4. Query q5 matches sub-rows of issue TS-129 and sub-rows of issue TS-239.
  5. Queries q6, q7 both match issues with fix version 5.2.11 or 6.0 and their subtrees.
  6. Query q8 matches siblings of TS-129's parents.
  7. Query q9 matches rows on the 3rd level of the hierarchy.
  8. Query q10 matches all rows such that either all the issues under the same parent that come before them are unresolved, or there are no issues under the same parent that come before them.
  9. Query q11 matches all such top-level rows and all such Epics that have unresolved sub-issues at any level.
  10. Query q12 matches all rows (both issues and non-issues) under Epics that are not Tasks.
  11. Query q13 matches the subtree of folder named "Future tasks".