You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@openjpa.apache.org by cu...@apache.org on 2011/08/15 18:36:07 UTC
svn commit: r1157903 - in /openjpa/trunk:
openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/
openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/jdbc/kernel/
Author: curtisr7
Date: Mon Aug 15 16:36:07 2011
New Revision: 1157903
URL: http://svn.apache.org/viewvc?rev=1157903&view=rev
Log:
OPENJPA-2039: Select FKs for fields that are in the DFG, but not in active fetchplan.
Added:
openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/jdbc/kernel/OptSelectEntity.java (with props)
openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/jdbc/kernel/TestJDBCStoreOptSelect.java (with props)
Modified:
openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/JDBCStoreManager.java
Modified: openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/JDBCStoreManager.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/JDBCStoreManager.java?rev=1157903&r1=1157902&r2=1157903&view=diff
==============================================================================
--- openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/JDBCStoreManager.java (original)
+++ openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/JDBCStoreManager.java Mon Aug 15 16:36:07 2011
@@ -97,8 +97,7 @@ import org.apache.openjpa.util.UserExcep
* @author Abe White
* @nojavadoc
*/
-public class JDBCStoreManager
- implements StoreManager, JDBCStore {
+public class JDBCStoreManager implements StoreManager, JDBCStore {
private static final Localizer _loc = Localizer.forPackage
(JDBCStoreManager.class);
@@ -112,7 +111,8 @@ public class JDBCStoreManager
private RefCountConnection _conn = null;
private boolean _active = false;
private Log _log = null;
-
+ boolean _ignoreDfgForFkSelect = false;
+
// track the pending statements so we can cancel them
private Set<Statement> _stmnts = Collections.synchronizedSet(new HashSet<Statement>());
@@ -1404,17 +1404,16 @@ public class JDBCStoreManager
}
/**
- * When selecting fieldes, a special case is made for mappings that use
- * 2-part selects that aren't explicitly *not* in the dfg so that they
- * can get their primary table data. This method tests for that special
- * case as an optimization.
- */
- private boolean optSelect(FieldMapping fm, Select sel,
- OpenJPAStateManager sm, JDBCFetchConfiguration fetch) {
- return !fm.isInDefaultFetchGroup()
- && !fm.isDefaultFetchGroupExplicit()
- && (sm == null || sm.getPCState() == PCState.TRANSIENT
- || !sm.getLoaded().get(fm.getIndex()))
+ * When selecting fields, a special case is made for mappings that use 2-part selects that aren't explicitly *not*
+ * in the dfg so that they can get their primary table data. This method tests for that special case as an
+ * optimization.
+ */
+ private boolean optSelect(FieldMapping fm, Select sel, OpenJPAStateManager sm, JDBCFetchConfiguration fetch) {
+ boolean dfg =
+ _ignoreDfgForFkSelect ||
+ !fm.isInDefaultFetchGroup() && !fm.isDefaultFetchGroupExplicit();
+
+ return dfg && (sm == null || sm.getPCState() == PCState.TRANSIENT || !sm.getLoaded().get(fm.getIndex()))
&& fm.supportsSelect(sel, Select.TYPE_TWO_PART, sm, this, fetch) > 0;
}
@@ -1552,10 +1551,12 @@ public class JDBCStoreManager
? getConfiguration().getFinderCacheInstance() : null;
}
+ public void setIgnoreDfgForFkSelect(boolean b) {
+ _ignoreDfgForFkSelect = b;
+ }
/**
- * Connection returned to client code. Makes sure its wrapped connection
- * ref count is decremented on finalize.
+ * Connection returned to client code. Makes sure its wrapped connection ref count is decremented on finalize.
*/
public abstract static class ClientConnection extends
DelegatingConnection {
Added: openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/jdbc/kernel/OptSelectEntity.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/jdbc/kernel/OptSelectEntity.java?rev=1157903&view=auto
==============================================================================
--- openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/jdbc/kernel/OptSelectEntity.java (added)
+++ openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/jdbc/kernel/OptSelectEntity.java Mon Aug 15 16:36:07 2011
@@ -0,0 +1,86 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.openjpa.jdbc.kernel;
+
+import javax.persistence.Entity;
+import javax.persistence.FetchType;
+import javax.persistence.GeneratedValue;
+import javax.persistence.GenerationType;
+import javax.persistence.Id;
+import javax.persistence.OneToOne;
+import javax.persistence.Version;
+
+@Entity
+public class OptSelectEntity {
+ @Id
+ @GeneratedValue(strategy = GenerationType.AUTO)
+ int id;
+
+ @Version
+ int version;
+
+ @OneToOne
+ OptSelectEntity eagerOneToOne;
+
+ @OneToOne(mappedBy = "eagerOneToOne")
+ OptSelectEntity eagerOneToOneOwner;
+
+ @OneToOne(fetch = FetchType.LAZY)
+ OptSelectEntity lazyOneToOne;
+
+ @OneToOne(mappedBy = "lazyOneToOne", fetch = FetchType.LAZY)
+ OptSelectEntity lazyOneToOneOwner;
+
+ public int getId() {
+ return id;
+ }
+
+ public OptSelectEntity getEagerOneToOne() {
+ return eagerOneToOne;
+ }
+
+ public void setEagerOneToOne(OptSelectEntity eagerOneToOne) {
+ this.eagerOneToOne = eagerOneToOne;
+ }
+
+ public OptSelectEntity getEagerOneToOneOwner() {
+ return eagerOneToOneOwner;
+ }
+
+ public void setEagerOneToOneOwner(OptSelectEntity eagerOneToOneOwner) {
+ this.eagerOneToOneOwner = eagerOneToOneOwner;
+ }
+
+ public OptSelectEntity getLazyOneToOne() {
+ return lazyOneToOne;
+ }
+
+ public void setLazyOneToOne(OptSelectEntity lazyOneToOne) {
+ this.lazyOneToOne = lazyOneToOne;
+ }
+
+ public OptSelectEntity getLazyOneToOneOwner() {
+ return lazyOneToOneOwner;
+ }
+
+ public void setLazyOneToOneOwner(OptSelectEntity lazyOneToOneOwner) {
+ this.lazyOneToOneOwner = lazyOneToOneOwner;
+ }
+
+}
Propchange: openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/jdbc/kernel/OptSelectEntity.java
------------------------------------------------------------------------------
svn:eol-style = native
Added: openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/jdbc/kernel/TestJDBCStoreOptSelect.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/jdbc/kernel/TestJDBCStoreOptSelect.java?rev=1157903&view=auto
==============================================================================
--- openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/jdbc/kernel/TestJDBCStoreOptSelect.java (added)
+++ openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/jdbc/kernel/TestJDBCStoreOptSelect.java Mon Aug 15 16:36:07 2011
@@ -0,0 +1,127 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.openjpa.jdbc.kernel;
+
+import org.apache.openjpa.enhance.PersistenceCapable;
+import org.apache.openjpa.kernel.StateManagerImpl;
+import org.apache.openjpa.kernel.StoreManager;
+import org.apache.openjpa.meta.ClassMetaData;
+import org.apache.openjpa.meta.FieldMetaData;
+import org.apache.openjpa.meta.MetaDataRepository;
+import org.apache.openjpa.persistence.EntityManagerImpl;
+import org.apache.openjpa.persistence.FetchPlan;
+import org.apache.openjpa.persistence.OpenJPAEntityManagerSPI;
+import org.apache.openjpa.persistence.test.SQLListenerTestCase;
+
+public class TestJDBCStoreOptSelect extends SQLListenerTestCase {
+ Object[] props = new Object[] { CLEAR_TABLES, OptSelectEntity.class };
+ OptSelectEntity e1, e2;
+
+ @Override
+ public void setUp() throws Exception {
+ super.setUp(props);
+ createData();
+ }
+
+ public void test() {
+ OpenJPAEntityManagerSPI em = emf.createEntityManager();
+ StoreManager store = ((EntityManagerImpl) em).getBroker().getStoreManager().getDelegate();
+
+ FetchPlan fp = getFetchPlan(em);
+ try {
+ sql.clear();
+
+ if (store instanceof JDBCStoreManager == false) {
+ fail("StoreManager is not an instanceof JDBCStoreManager");
+ }
+ // Set this JDBCStoreManager property so that we will select FKs for fields that are in the DFG, but not
+ // included in the current select.
+ ((JDBCStoreManager) store).setIgnoreDfgForFkSelect(true);
+
+ // Remove all relationships
+ fp.removeField(OptSelectEntity.class, "eagerOneToOne");
+ fp.removeField(OptSelectEntity.class, "eagerOneToOneOwner");
+ fp.removeField(OptSelectEntity.class, "lazyOneToOne");
+ fp.removeField(OptSelectEntity.class, "lazyOneToOneOwner");
+
+ OptSelectEntity ee1 = em.find(OptSelectEntity.class, e1.getId());
+
+ // Make sure our sql has no joins
+ assertEquals(1, sql.size());
+ String s = sql.get(0);
+ assertFalse(s.contains("JOIN") && s.contains("join"));
+
+ // Check to see how many fks(intermediate fields) we selected.
+ StateManagerImpl smi = ((StateManagerImpl) ((PersistenceCapable) ee1).pcGetStateManager());
+ ClassMetaData cmd =
+ em.getConfiguration().getMetaDataRepositoryInstance().getMetaData(OptSelectEntity.class, null, true);
+ int fks = 0;
+ for (FieldMetaData fmd : cmd.getFields()) {
+ if (smi.getIntermediate(fmd.getIndex()) != null) {
+ fks++;
+ }
+ }
+ assertEquals(2, fks);
+ } finally {
+ if (em.getTransaction().isActive()) {
+ em.getTransaction().rollback();
+ }
+ if (em.isOpen()) {
+ em.close();
+ }
+ }
+ }
+
+ private FetchPlan getFetchPlan(OpenJPAEntityManagerSPI em) {
+ MetaDataRepository mdr = em.getConfiguration().getMetaDataRepositoryInstance();
+ FetchPlan fp = em.pushFetchPlan();
+ fp.removeFetchGroups(fp.getFetchGroups());
+ for (Class<?> cls : new Class<?>[] { OptSelectEntity.class }) {
+ ClassMetaData cmd = mdr.getMetaData(cls, null, true);
+ for (FieldMetaData fmd : cmd.getFields()) {
+ fp.addField(cls, fmd.getName());
+ }
+ }
+ return fp;
+ }
+
+ void createData() {
+ OpenJPAEntityManagerSPI em = emf.createEntityManager();
+ try {
+ em.getTransaction().begin();
+ e1 = new OptSelectEntity();
+ e2 = new OptSelectEntity();
+
+ e1.setEagerOneToOne(e2);
+ e2.setEagerOneToOneOwner(e2);
+
+ e1.setLazyOneToOne(e2);
+ e2.setLazyOneToOneOwner(e1);
+
+ em.persistAll(e1, e2);
+
+ em.getTransaction().commit();
+ } finally {
+ if (em.getTransaction().isActive())
+ em.getTransaction().rollback();
+ if (em.isOpen())
+ em.close();
+ }
+ }
+}
Propchange: openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/jdbc/kernel/TestJDBCStoreOptSelect.java
------------------------------------------------------------------------------
svn:eol-style = native