InterMine Query Package
The InterMine database query system is implemented in the Java package org.intermine.objectstore.query. The main class of the package is Query which represents a query that can be passed to the ORMappingTool. The Java Query maps directly onto IQL. It may be useful to refer to our QueryExamples. In fact, by far the easiest method of creating a Java InterMine Query object is to use the following constructor:
import org.intermine.objectstore.query.Query;
import org.intermine.objectstore.query.iql.IqlQuery;
Query q = new IqlQuery("--- IQL Query text ---", null).toQuery();
However, in a Java program, one will occasionally require more flexibility - the Java interface is a more direct method of inserting parameters into the Query, rather than converting them into text and expecting the parser to convert back.
Structure
The Java Query object contains:
- a From list (which is actually a Set), accessed through Query.addFrom(), which can contain FromElement objects (which includes QueryClass, QueryClassBag or Query).
- a Select list, accessed through Query.addToSelect(), which can contain any QuerySelectable object (which includes QueryClass, QueryExpression, QueryField, QueryFunction, and QueryValue among others).
- an Order By list, accessed through Query.addToOrderBy(), which can contain any QueryOrderable.
- a Group By list (which is actually a Set), accessed through Query.addToGroupBy(), which can contain QueryNode objects. However, it does not make sense to include QueryValue objects directly, or QueryFunction objects at all.
- a reference to a single Constraint object, accessed through Query.setConstraint(), but multiple constraints can be included by encapsulating them in a ConstraintSet object.
An Example
This is an example of how one would build a Java InterMine Query object to represent the IQL query:
SELECT a.field1, a.field2 FROM a WHERE a.field3 = 'Hello';
The Query is built up in stages.
import org.intermine.objectstore.query.Query;
import org.intermine.objectstore.query.QueryClass;
import org.intermine.objectstore.query.QueryField;
import org.intermine.objectstore.query.QueryValue;
import org.intermine.objectstore.query.SimpleConstraint;
Query q = new Query();
QueryClass c = new QueryClass(a.class);
QueryField f1 = new QueryField(c, "field1");
QueryField f2 = new QueryField(c, "field2");
QueryField f3 = new QueryField(c, "field3");
QueryValue v = new QueryValue("Hello");
SimpleConstraint sc = new SimpleConstraint(f3, SimpleConstraint.EQUALS, v);
q.addFrom(c);
q.addToSelect(f1);
q.addToSelect(f2);
q.setConstraint(sc);
q.setDistinct(false);
Another Example
this is a commented query used in the InterMine code that should also show how to obtain a 'join' between 2 relations (the ContainsConstraint? section) and how to impose an ORDER BY
// Documented as an example of how to use the query API
// This query selects Gene.primaryIdentifier where it has a non-null value
// for all Genes from D. melanogaster (taxon id 7227).
// Create a new query
Query q = new Query();
// Create a set to hold constraints that will be ANDed together
ConstraintSet cs = new ConstraintSet(ConstraintOp.AND);
// Include Gene on the from list
QueryClass qcGene = new QueryClass(Gene.class);
q.addFrom(qcGene);
// Select the Gene.primaryIdentifier field
QueryField qf = new QueryField(qcGene, "primaryIdentifier");
q.addToSelect(qf);
// Filter out any null Gene.primaryIdentifier values
SimpleConstraint sc2 = new SimpleConstraint(qf, ConstraintOp.IS_NOT_NULL);
cs.addConstraint(sc2);
// Add organism to the from list
QueryClass qcOrg = new QueryClass(Organism.class);
q.addFrom(qcOrg);
// Constrain Organism.taxonId to be D. melanogaster
QueryField qfOrgTaxon = new QueryField(qcOrg, "taxonId");
SimpleConstraint sc1 = new SimpleConstraint(qfOrgTaxon, ConstraintOp.EQUALS,
new QueryValue(new Integer(7227)));
cs.addConstraint(sc1);
// Now relate the Gene to the Organism we have just constrained, link by Gene.organism
// reference.
QueryObjectReference ref1 = new QueryObjectReference(qcGene, "organism");
ContainsConstraint cc1 = new ContainsConstraint(ref1, ConstraintOp.CONTAINS, qcOrg);
cs.addConstraint(cc1);
// Set the constraint of the query
q.setConstraint(cs);
// Order the results by Gene.primaryIdentifier
q.addToOrderBy(qf);
// Make the output distinct, just like SQL DISTINCT syntax
q.setDistinct(true);
// Execute the query and get an iterator over results. batch size controls
// how results are paged into memory. High numbers mean better performace
// but more memory usage.
SingletonResults res = os.executeSingleton(q);
res.setBatchSize(10000);
