You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cayenne.apache.org by aa...@apache.org on 2010/10/21 20:12:39 UTC
svn commit: r1026090 - in /cayenne/main/branches/STABLE-3.0:
docs/doc/src/main/resources/
framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/
framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/util/
framewor...
Author: aadamchik
Date: Thu Oct 21 18:12:38 2010
New Revision: 1026090
URL: http://svn.apache.org/viewvc?rev=1026090&view=rev
Log:
CAY-1489 NPE using DataContext.objectFromDataRow for a nested context
Patch by Andrei Veprev
Added:
cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/ObjectsFromDataRowsQuery.java
Modified:
cayenne/main/branches/STABLE-3.0/docs/doc/src/main/resources/RELEASE-NOTES.txt
cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/DataContext.java
cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/DataContextQueryAction.java
cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/util/ObjectContextQueryAction.java
cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/test/java/org/apache/cayenne/access/NestedDataContextReadTest.java
Modified: cayenne/main/branches/STABLE-3.0/docs/doc/src/main/resources/RELEASE-NOTES.txt
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/docs/doc/src/main/resources/RELEASE-NOTES.txt?rev=1026090&r1=1026089&r2=1026090&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/docs/doc/src/main/resources/RELEASE-NOTES.txt (original)
+++ cayenne/main/branches/STABLE-3.0/docs/doc/src/main/resources/RELEASE-NOTES.txt Thu Oct 21 18:12:38 2010
@@ -17,6 +17,7 @@ Bug Fixes Since 3.0.1:
CAY-1484 Flattened attribute queries are incorrectly generated
CAY-1485 Memory information for about dialog
CAY-1488 OutOfMemory when selecting "Remove Foreign Keys Mapped as Object Attributes"
+CAY-1489 NPE using DataContext.objectFromDataRow for a nested context
CAY-1490 Maven cgen: all and datamap modes can not be activated
CAY-1496 Problem in derby: comparison operators are not supported on Clob object values.
Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/DataContext.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/DataContext.java?rev=1026090&r1=1026089&r2=1026090&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/DataContext.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/DataContext.java Thu Oct 21 18:12:38 2010
@@ -594,10 +594,25 @@ public class DataContext extends BaseCon
public List objectsFromDataRows(
ClassDescriptor descriptor,
List<? extends DataRow> dataRows) {
+ // TODO: If data row cache is not available it means that current data context is
+ // child. We need to redirect this method call to parent data context as an
+ // internal query. It is not obvious and has some overhead. Redesign for nested
+ // contexts should be done.
+ if (getObjectStore().getDataRowCache() == null) {
+ return objectsFromDataRowsFromParentContext(descriptor, dataRows);
+ }
return new ObjectResolver(this, descriptor, true)
.synchronizedObjectsFromDataRows(dataRows);
}
+ private List objectsFromDataRowsFromParentContext(
+ ClassDescriptor descriptor,
+ List<? extends DataRow> dataRows) {
+ return getChannel().onQuery(
+ this,
+ new ObjectsFromDataRowsQuery(descriptor, dataRows)).firstList();
+ }
+
/**
* Converts a list of DataRows to a List of DataObject registered with this
* DataContext.
Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/DataContextQueryAction.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/DataContextQueryAction.java?rev=1026090&r1=1026089&r2=1026090&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/DataContextQueryAction.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/DataContextQueryAction.java Thu Oct 21 18:12:38 2010
@@ -43,9 +43,28 @@ import org.apache.cayenne.util.ObjectCon
*/
class DataContextQueryAction extends ObjectContextQueryAction {
+ protected DataContext actingDataContext;
+
public DataContextQueryAction(DataContext actingContext, ObjectContext targetContext,
Query query) {
super(actingContext, targetContext, query);
+ actingDataContext = actingContext;
+ }
+
+ @Override
+ protected boolean interceptInternalQuery() {
+ return interceptObjectFromDataRowsQuery();
+ }
+
+ private boolean interceptObjectFromDataRowsQuery() {
+ if (query instanceof ObjectsFromDataRowsQuery) {
+ ObjectsFromDataRowsQuery objectsFromDataRowsQuery = (ObjectsFromDataRowsQuery) query;
+ response = new ListResponse(actingDataContext.objectsFromDataRows(
+ objectsFromDataRowsQuery.getDescriptor(),
+ objectsFromDataRowsQuery.getDataRows()));
+ return DONE;
+ }
+ return !DONE;
}
/**
Added: cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/ObjectsFromDataRowsQuery.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/ObjectsFromDataRowsQuery.java?rev=1026090&view=auto
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/ObjectsFromDataRowsQuery.java (added)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/access/ObjectsFromDataRowsQuery.java Thu Oct 21 18:12:38 2010
@@ -0,0 +1,158 @@
+/*****************************************************************
+ * 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.cayenne.access;
+
+import java.util.List;
+import java.util.Map;
+
+import org.apache.cayenne.DataRow;
+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.query.PrefetchTreeNode;
+import org.apache.cayenne.query.Query;
+import org.apache.cayenne.query.QueryCacheStrategy;
+import org.apache.cayenne.query.QueryMetadata;
+import org.apache.cayenne.query.QueryRouter;
+import org.apache.cayenne.query.SQLAction;
+import org.apache.cayenne.query.SQLActionVisitor;
+import org.apache.cayenne.reflect.ClassDescriptor;
+
+class ObjectsFromDataRowsQuery implements Query, QueryMetadata {
+
+ private ClassDescriptor descriptor;
+
+ private List<? extends DataRow> dataRows;
+
+ public ObjectsFromDataRowsQuery(ClassDescriptor descriptor,
+ List<? extends DataRow> dataRows) {
+ super();
+ this.descriptor = descriptor;
+ this.dataRows = dataRows;
+ }
+
+ public ClassDescriptor getDescriptor() {
+ return descriptor;
+ }
+
+ public List<? extends DataRow> getDataRows() {
+ return dataRows;
+ }
+
+ public QueryMetadata getMetaData(EntityResolver resolver) {
+ return this;
+ }
+
+ public void route(QueryRouter router, EntityResolver resolver, Query substitutedQuery) {
+ }
+
+ public SQLAction createSQLAction(SQLActionVisitor visitor) {
+ return null;
+ }
+
+ public String getName() {
+ return null;
+ }
+
+ public boolean isResolvingInherited() {
+ return false;
+ }
+
+ public int getFetchStartIndex() {
+ return 0;
+ }
+
+ public DataMap getDataMap() {
+ return null;
+ }
+
+ public ClassDescriptor getClassDescriptor() {
+ return null;
+ }
+
+ public ObjEntity getObjEntity() {
+ return null;
+ }
+
+ public DbEntity getDbEntity() {
+ return null;
+ }
+
+ public Procedure getProcedure() {
+ return null;
+ }
+
+ public QueryCacheStrategy getCacheStrategy() {
+ return null;
+ }
+
+ public String getCacheKey() {
+ return null;
+ }
+
+ public String[] getCacheGroups() {
+ return null;
+ }
+
+ public boolean isFetchingDataRows() {
+ return false;
+ }
+
+ public boolean isRefreshingObjects() {
+ return false;
+ }
+
+ public int getPageSize() {
+ return 0;
+ }
+
+ public int getFetchOffset() {
+ return 0;
+ }
+
+ public int getFetchLimit() {
+ return 0;
+ }
+
+ public Query getOrginatingQuery() {
+ return null;
+ }
+
+ public PrefetchTreeNode getPrefetchTree() {
+ return null;
+ }
+
+ public Map<String, String> getPathSplitAliases() {
+ return null;
+ }
+
+ public List<Object> getResultSetMapping() {
+ return null;
+ }
+
+ public int getStatementFetchSize() {
+ return 0;
+ }
+
+ public String getCachePolicy() {
+ return null;
+ }
+}
Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/util/ObjectContextQueryAction.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/util/ObjectContextQueryAction.java?rev=1026090&r1=1026089&r2=1026090&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/util/ObjectContextQueryAction.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/main/java/org/apache/cayenne/util/ObjectContextQueryAction.java Thu Oct 21 18:12:38 2010
@@ -88,13 +88,7 @@ public abstract class ObjectContextQuery
if (interceptRelationshipQuery() != DONE) {
if (interceptRefreshQuery() != DONE) {
if (interceptLocalCache() != DONE) {
- // when changing the flow below, make sure to update
- // 'getCacheObjectFactory' method that mimics the interceptors
- // below 'interceptLocalCache'. See comment in an inner class
- // factory in this method...
- if (interceptPaginatedQuery() != DONE) {
- runQuery();
- }
+ executePostCache();
}
}
}
@@ -104,6 +98,14 @@ public abstract class ObjectContextQuery
return response;
}
+ private void executePostCache() {
+ if (interceptInternalQuery() != DONE) {
+ if (interceptPaginatedQuery() != DONE) {
+ runQuery();
+ }
+ }
+ }
+
/**
* Transfers fetched objects into the target context if it is different from "acting"
* context. Note that when this method is invoked, result objects are already
@@ -150,6 +152,10 @@ public abstract class ObjectContextQuery
}
+ protected boolean interceptInternalQuery() {
+ return !DONE;
+ }
+
protected boolean interceptOIDQuery() {
if (query instanceof ObjectIdQuery) {
ObjectIdQuery oidQuery = (ObjectIdQuery) query;
@@ -315,12 +321,7 @@ public abstract class ObjectContextQuery
return new QueryCacheEntryFactory() {
public Object createObject() {
- // must follow the same logic as 'execute' below locla cache interceptor
- // method... reuse that code somehow???
- if (interceptPaginatedQuery() != DONE) {
- runQuery();
- }
-
+ executePostCache();
return response.firstList();
}
};
Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/test/java/org/apache/cayenne/access/NestedDataContextReadTest.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/test/java/org/apache/cayenne/access/NestedDataContextReadTest.java?rev=1026090&r1=1026089&r2=1026090&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/test/java/org/apache/cayenne/access/NestedDataContextReadTest.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-jdk1.5-unpublished/src/test/java/org/apache/cayenne/access/NestedDataContextReadTest.java Thu Oct 21 18:12:38 2010
@@ -19,6 +19,7 @@
package org.apache.cayenne.access;
+import java.util.Date;
import java.util.Iterator;
import java.util.List;
@@ -26,6 +27,7 @@ import org.apache.art.Artist;
import org.apache.art.Painting;
import org.apache.cayenne.DataObject;
import org.apache.cayenne.DataObjectUtils;
+import org.apache.cayenne.DataRow;
import org.apache.cayenne.ObjectContext;
import org.apache.cayenne.ObjectId;
import org.apache.cayenne.PersistenceState;
@@ -475,4 +477,24 @@ public class NestedDataContextReadTest e
unblockQueries();
}
}
+
+ public void testObjectFromDataRow() throws Exception {
+ deleteTestData();
+
+ DataContext context = createDataContext();
+ DataContext childContext = (DataContext) context.createChildContext();
+
+ DataRow row = new DataRow(8);
+ row.put("ARTIST_ID", 5l);
+ row.put("ARTIST_NAME", "A");
+ row.put("DATE_OF_BIRTH", new Date());
+
+ Artist artist = childContext.objectFromDataRow(Artist.class, row, true);
+ assertNotNull(artist);
+ assertEquals(PersistenceState.COMMITTED, artist.getPersistenceState());
+ assertSame(childContext, artist.getObjectContext());
+ Object parentArtist = context.getObjectStore().getNode(artist.getObjectId());
+ assertNotNull(parentArtist);
+ assertNotSame(artist, parentArtist);
+ }
}