Repository: cayenne Updated Branches: refs/heads/master 7a2fb98f9 -> 0ca73a17a
CAY-2406 Add prefetch-related API to SQLSelect Project: http://git-wip-us.apache.org/repos/asf/cayenne/repo Commit: http://git-wip-us.apache.org/repos/asf/cayenne/commit/a43c1e6a Tree: http://git-wip-us.apache.org/repos/asf/cayenne/tree/a43c1e6a Diff: http://git-wip-us.apache.org/repos/asf/cayenne/diff/a43c1e6a Branch: refs/heads/master Commit: a43c1e6a297ac5440d646f8f11ba54fe7c292509 Parents: b718949 Author: Maxim Petrusevich <maks1...@gmail.com> Authored: Fri Feb 9 16:06:29 2018 +0300 Committer: Maxim Petrusevich <maks1...@gmail.com> Committed: Fri Feb 9 16:06:29 2018 +0300 ---------------------------------------------------------------------- .../org/apache/cayenne/query/SQLSelect.java | 40 +++++++++++++++- .../org/apache/cayenne/query/SQLTemplate.java | 5 -- .../apache/cayenne/access/JointPrefetchIT.java | 49 ++++++++++++++++++++ 3 files changed, 87 insertions(+), 7 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/cayenne/blob/a43c1e6a/cayenne-server/src/main/java/org/apache/cayenne/query/SQLSelect.java ---------------------------------------------------------------------- diff --git a/cayenne-server/src/main/java/org/apache/cayenne/query/SQLSelect.java b/cayenne-server/src/main/java/org/apache/cayenne/query/SQLSelect.java index d9de26e..579dc5f 100644 --- a/cayenne-server/src/main/java/org/apache/cayenne/query/SQLSelect.java +++ b/cayenne-server/src/main/java/org/apache/cayenne/query/SQLSelect.java @@ -19,7 +19,6 @@ package org.apache.cayenne.query; import java.util.Arrays; -import java.util.Collection; import java.util.Collections; import java.util.HashMap; import java.util.List; @@ -101,6 +100,7 @@ public class SQLSelect<T> extends IndirectQuery implements Select<T> { protected int offset; protected int pageSize; protected int statementFetchSize; + protected PrefetchTreeNode prefetches; public SQLSelect(String sql) { this(null, sql); @@ -240,7 +240,7 @@ public class SQLSelect<T> extends IndirectQuery implements Select<T> { } @Override - protected Query createReplacementQuery(EntityResolver resolver) { + public Query createReplacementQuery(EntityResolver resolver) { Object root; @@ -263,6 +263,7 @@ public class SQLSelect<T> extends IndirectQuery implements Select<T> { template.setDefaultTemplate(getSql()); template.setCacheGroup(cacheGroup); template.setCacheStrategy(cacheStrategy); + template.addPrefetch(prefetches); if (positionalParams != null) { template.setParamsList(positionalParams); @@ -468,4 +469,39 @@ public class SQLSelect<T> extends IndirectQuery implements Select<T> { public int getStatementFetchSize() { return statementFetchSize; } + + /** + * Merges a prefetch path with specified semantics into the query prefetch tree. + * @param path Path expression + * @param semantics Defines a strategy to prefetch relationships. See {@link PrefetchTreeNode} + * @return this object + * @since 4.1 + */ + public SQLSelect<T> addPrefetch(String path, int semantics) { + if (path == null) { + return this; + } + if (prefetches == null) { + prefetches = new PrefetchTreeNode(); + } + prefetches.addPath(path).setSemantics(semantics); + return this; + } + + /** + * Merges a prefetch into the query prefetch tree. + * @param node Prefetch which will added to query prefetch tree + * @return this object + * @since 4.1 + */ + public SQLSelect<T> addPrefetch(PrefetchTreeNode node) { + if (node == null) { + return this; + } + if (prefetches == null) { + prefetches = new PrefetchTreeNode(); + } + prefetches.merge(node); + return this; + } } http://git-wip-us.apache.org/repos/asf/cayenne/blob/a43c1e6a/cayenne-server/src/main/java/org/apache/cayenne/query/SQLTemplate.java ---------------------------------------------------------------------- diff --git a/cayenne-server/src/main/java/org/apache/cayenne/query/SQLTemplate.java b/cayenne-server/src/main/java/org/apache/cayenne/query/SQLTemplate.java index eed51c1..5a84322 100644 --- a/cayenne-server/src/main/java/org/apache/cayenne/query/SQLTemplate.java +++ b/cayenne-server/src/main/java/org/apache/cayenne/query/SQLTemplate.java @@ -20,16 +20,11 @@ package org.apache.cayenne.query; import org.apache.cayenne.access.QueryEngine; -import org.apache.cayenne.configuration.ConfigurationNodeVisitor; import org.apache.cayenne.map.DataMap; import org.apache.cayenne.map.DbEntity; import org.apache.cayenne.map.EntityResolver; import org.apache.cayenne.map.ObjEntity; -import org.apache.cayenne.map.Procedure; -import org.apache.cayenne.map.QueryDescriptor; import org.apache.cayenne.map.SQLResult; -import org.apache.cayenne.util.XMLEncoder; -import org.apache.cayenne.util.XMLSerializable; import java.util.ArrayList; import java.util.Arrays; http://git-wip-us.apache.org/repos/asf/cayenne/blob/a43c1e6a/cayenne-server/src/test/java/org/apache/cayenne/access/JointPrefetchIT.java ---------------------------------------------------------------------- diff --git a/cayenne-server/src/test/java/org/apache/cayenne/access/JointPrefetchIT.java b/cayenne-server/src/test/java/org/apache/cayenne/access/JointPrefetchIT.java index 87689b5..6cada72 100644 --- a/cayenne-server/src/test/java/org/apache/cayenne/access/JointPrefetchIT.java +++ b/cayenne-server/src/test/java/org/apache/cayenne/access/JointPrefetchIT.java @@ -29,6 +29,7 @@ import org.apache.cayenne.di.Inject; import org.apache.cayenne.exp.Expression; import org.apache.cayenne.map.ObjAttribute; import org.apache.cayenne.map.ObjEntity; +import org.apache.cayenne.query.SQLSelect; import org.apache.cayenne.query.SQLTemplate; import org.apache.cayenne.query.SelectQuery; import org.apache.cayenne.query.SortOrder; @@ -401,4 +402,52 @@ public class JointPrefetchIT extends ServerCase { assertEquals(PersistenceState.COMMITTED, g2.getPersistenceState()); }); } + + @Test + public void testJointPrefetchSQLSelectToMany() throws Exception { + createJointPrefetchDataSet(); + SQLSelect sqlSelect = SQLSelect.query(Artist.class, "SELECT " + + "#result('PAINTING_ID' 'int' '' 'paintingArray.PAINTING_ID'), " + + "#result('ARTIST_NAME' 'String'), " + + "#result('DATE_OF_BIRTH' 'java.util.Date'), " + + "#result('t0.ARTIST_ID' 'int' '' 'ARTIST_ID') " + + "FROM ARTIST t0, PAINTING t1 " + + "WHERE t0.ARTIST_ID = t1.ARTIST_ID"); + sqlSelect.addPrefetch(Artist.PAINTING_ARRAY.joint()); + + @SuppressWarnings("unchecked") + final List<Artist> objects = (List<Artist>)sqlSelect.select(context); + queryInterceptor.runWithQueriesBlocked(() -> { + assertNotNull(objects); + assertEquals(2, objects.size()); + + for (Artist artist : objects) { + List<Painting> paintings = artist.getPaintingArray(); + assertTrue(paintings.size() > 0); + for (Painting painting : paintings) { + assertEquals(PersistenceState.COMMITTED, painting.getPersistenceState()); + } + } + }); + } + + @Test + public void testJointPrefetchSQLSelectNestedJoint() throws Exception { + createJointPrefetchDataSet(); + SQLSelect sqlSelect = SQLSelect.query(Artist.class, "SELECT " + + "#result('GALLERY_ID' 'int' '' 'paintingArray.toGallery.GALLERY_ID')," + + "#result('GALLERY_NAME' 'String' '' 'paintingArray.toGallery.GALLERY_NAME')," + + "#result('t0.ARTIST_ID' 'int' '' 'ARTIST_ID') " + + "FROM ARTIST t0, GALLERY t2 "); + sqlSelect.addPrefetch(Artist.PAINTING_ARRAY.dot(Painting.TO_GALLERY).joint()); + + sqlSelect.select(context); + queryInterceptor.runWithQueriesBlocked(() -> { + DataObject g1 = (DataObject) context.getGraphManager().getNode( + new ObjectId("Gallery", Gallery.GALLERY_ID_PK_COLUMN, 33001) + ); + assertNotNull(g1); + assertEquals("G1", g1.readProperty("galleryName")); + }); + } }