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 2006/04/29 20:52:21 UTC

svn commit: r398217 - in /incubator/cayenne/trunk/cayenne-jpa/src: main/java/org/apache/cayenne/jpa/ main/java/org/apache/cayenne/jpa/bridge/ main/java/org/apache/cayenne/jpa/conf/ main/java/org/apache/cayenne/jpa/cspi/ main/java/org/apache/cayenne/jpa...

Author: aadamchik
Date: Sat Apr 29 11:52:18 2006
New Revision: 398217

URL: http://svn.apache.org/viewcvs?rev=398217&view=rev
Log:
switching JPA provider to JPA mapping from Cayenne mapping. 
This doesn't fully work yet, although the code passes all unit tests 

Added:
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapDefaultsProcessor.java
      - copied, changed from r398019, incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapDefaultsLoader.java
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapMergeProcessor.java
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/JpaLoaderContext.java
      - copied, changed from r398019, incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapLoaderContext.java
Removed:
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapDefaultsLoader.java
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapLoaderContext.java
Modified:
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/JpaProviderException.java
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/bridge/DataMapConverter.java
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/AnnotationProcessorStack.java
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapAnnotationLoader.java
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapLoader.java
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaEntityManager.java
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaEntityManagerFactory.java
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaPersistenceProvider.java
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/map/JpaAbstractEntity.java
    incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/map/JpaEntityMap.java
    incubator/cayenne/trunk/cayenne-jpa/src/test/java/org/apache/cayenne/jpa/bridge/DataMapConverterTest.java
    incubator/cayenne/trunk/cayenne-jpa/src/test/java/org/apache/cayenne/jpa/conf/EntityMapAnnotationLoaderTest.java

Modified: incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/JpaProviderException.java
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/JpaProviderException.java?rev=398217&r1=398216&r2=398217&view=diff
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/JpaProviderException.java (original)
+++ incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/JpaProviderException.java Sat Apr 29 11:52:18 2006
@@ -15,14 +15,14 @@
  */
 package org.apache.cayenne.jpa;
 
-import org.objectstyle.cayenne.CayenneRuntimeException;
+import javax.persistence.PersistenceException;
 
 /**
  * A runtime exception thrown on various problems in the provider code.
  * 
  * @author Andrus Adamchik
  */
-public class JpaProviderException extends CayenneRuntimeException {
+public class JpaProviderException extends PersistenceException {
 
     public JpaProviderException() {
         super();

Modified: incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/bridge/DataMapConverter.java
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/bridge/DataMapConverter.java?rev=398217&r1=398216&r2=398217&view=diff
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/bridge/DataMapConverter.java (original)
+++ incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/bridge/DataMapConverter.java Sat Apr 29 11:52:18 2006
@@ -19,6 +19,7 @@
 import java.lang.reflect.Field;
 
 import org.apache.cayenne.jpa.JpaProviderException;
+import org.apache.cayenne.jpa.conf.JpaLoaderContext;
 import org.apache.cayenne.jpa.map.AccessType;
 import org.apache.cayenne.jpa.map.JpaAttribute;
 import org.apache.cayenne.jpa.map.JpaColumn;
@@ -40,7 +41,6 @@
 import org.objectstyle.cayenne.project.ProjectPath;
 import org.objectstyle.cayenne.util.Util;
 import org.objectstyle.cayenne.validation.SimpleValidationFailure;
-import org.objectstyle.cayenne.validation.ValidationResult;
 
 /**
  * A converter between {@link org.apache.cayenne.jpa.map.JpaEntityMap} and Cayenne
@@ -50,17 +50,13 @@
  */
 public class DataMapConverter {
 
-    protected ValidationResult conflicts;
+    protected JpaLoaderContext context;
 
     protected ProjectPath targetPath;
     protected HierarchicalTreeVisitor visitor;
 
-    public DataMapConverter(ValidationResult conflicts) {
-        this.conflicts = conflicts;
-    }
-
-    public ValidationResult getConflicts() {
-        return conflicts;
+    public DataMapConverter(JpaLoaderContext context) {
+        this.context = context;
     }
 
     public synchronized DataMap toDataMap(String name, JpaEntityMap jpaMap) {
@@ -81,7 +77,7 @@
     }
 
     protected void recordConflict(ProjectPath path, String message) {
-        conflicts.addFailure(new SimpleValidationFailure(path.getObject(), message));
+        context.recordConflict(new SimpleValidationFailure(path.getObject(), message));
     }
 
     /**

Modified: incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/AnnotationProcessorStack.java
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/AnnotationProcessorStack.java?rev=398217&r1=398216&r2=398217&view=diff
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/AnnotationProcessorStack.java (original)
+++ incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/AnnotationProcessorStack.java Sat Apr 29 11:52:18 2006
@@ -28,7 +28,7 @@
     /**
      * Returns parent context.
      */
-    EntityMapLoaderContext getContext();
+    JpaLoaderContext getContext();
 
     void push(Object object);
 

Modified: incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapAnnotationLoader.java
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapAnnotationLoader.java?rev=398217&r1=398216&r2=398217&view=diff
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapAnnotationLoader.java (original)
+++ incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapAnnotationLoader.java Sat Apr 29 11:52:18 2006
@@ -89,7 +89,7 @@
         // 'attribute' is implied...
     }
 
-    protected EntityMapLoaderContext context;
+    protected JpaLoaderContext context;
 
     protected Comparator<Annotation> typeAnnotationsSorter;
     protected Comparator<Annotation> memberAnnotationsSorter;
@@ -98,7 +98,7 @@
     protected AnnotationProcessorFactory memberProcessorFactory;
     protected AnnotationProcessorFactory callbackProcessorFactory;
 
-    public EntityMapAnnotationLoader(EntityMapLoaderContext context) {
+    public EntityMapAnnotationLoader(JpaLoaderContext context) {
         this.context = context;
         this.typeAnnotationsSorter = new AnnotationSorter(
                 TYPE_ANNOTATION_ORDERING_WEIGHTS);

Copied: incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapDefaultsProcessor.java (from r398019, incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapDefaultsLoader.java)
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapDefaultsProcessor.java?p2=incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapDefaultsProcessor.java&p1=incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapDefaultsLoader.java&r1=398019&r2=398217&rev=398217&view=diff
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapDefaultsLoader.java (original)
+++ incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapDefaultsProcessor.java Sat Apr 29 11:52:18 2006
@@ -36,16 +36,16 @@
  * 
  * @author Andrus Adamchik
  */
-public class EntityMapDefaultsLoader {
+public class EntityMapDefaultsProcessor {
 
     protected HierarchicalTreeVisitor visitor;
-    protected EntityMapLoaderContext context;
+    protected JpaLoaderContext context;
 
-    public EntityMapDefaultsLoader(EntityMapLoaderContext context) {
+    public EntityMapDefaultsProcessor(JpaLoaderContext context) {
         this.context = context;
     }
 
-    public void loadDefaults(JpaEntityMap entityMap) throws JpaProviderException {
+    public void applyDefaults(JpaEntityMap entityMap) throws JpaProviderException {
 
         if (visitor == null) {
             visitor = createVisitor();
@@ -109,6 +109,7 @@
             if (entity.getTable() == null) {
                 JpaTable table = new JpaTable(AnnotationPrototypes.getTable());
                 table.setName(entity.getName());
+                entity.setTable(table);
             }
 
             return true;
@@ -183,17 +184,18 @@
         @Override
         public boolean onStartNode(ProjectPath path) {
             JpaColumn column = (JpaColumn) path.getObject();
-            
-            if(column.getName() == null) {
-                JpaAttribute attribute = (JpaAttribute) path.firstInstanceOf(JpaAttribute.class);
+
+            if (column.getName() == null) {
+                JpaAttribute attribute = (JpaAttribute) path
+                        .firstInstanceOf(JpaAttribute.class);
                 column.setName(attribute.getName());
             }
 
-            if(column.getTable() == null) {
+            if (column.getTable() == null) {
                 JpaEntity entity = (JpaEntity) path.firstInstanceOf(JpaEntity.class);
                 column.setTable(entity.getTable().getName());
             }
-             
+
             return true;
         }
     }

Modified: incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapLoader.java
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapLoader.java?rev=398217&r1=398216&r2=398217&view=diff
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapLoader.java (original)
+++ incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapLoader.java Sat Apr 29 11:52:18 2006
@@ -62,7 +62,7 @@
     static final String DESCRIPTOR_LOCATION = "META-INF/orm.xml";
 
     protected JpaEntityMap entityMap;
-    protected EntityMapLoaderContext context;
+    protected JpaLoaderContext context;
     protected Map<String, JpaClassDescriptor> descriptors;
 
     /**
@@ -70,7 +70,7 @@
      * from all locations supported by the JPA specification.
      */
     public EntityMapLoader(PersistenceUnitInfo persistenceUnit) {
-        this.context = new EntityMapLoaderContext();
+        this.context = new JpaLoaderContext();
         this.entityMap = loadEntityMap(persistenceUnit);
     }
 
@@ -88,18 +88,10 @@
     protected JpaEntityMap loadEntityMap(PersistenceUnitInfo persistenceUnit)
             throws JpaProviderException {
 
-        // algorithm is the following:
-        // 1. load all ORM descriptors and merge them together
-        // 2. load annotations for all mentioned classes
-        // 3. merge combined ORM descriptor with the annotated descriptor, overriding
-        // annotation values.
-        // 4. set defaults
-
         try {
-            JpaEntityMap xmlMap = loadFromXML(persistenceUnit);
             JpaEntityMap baseMap = loadFromAnnotations(persistenceUnit);
-            baseMap.mergeOverride(xmlMap);
-            new EntityMapDefaultsLoader(context).loadDefaults(baseMap);
+            updateFromXML(baseMap, persistenceUnit);
+            updateFromDefaults(baseMap);
 
             return baseMap;
         }
@@ -112,8 +104,16 @@
     }
 
     /**
-     * Loads a combined mapping descriptor from all supported locations of the mapping
-     * files.
+     * Updates missing values with spec-compilant defaults.
+     */
+    protected void updateFromDefaults(JpaEntityMap baseMap) {
+        new EntityMapDefaultsProcessor(context).applyDefaults(baseMap);
+    }
+
+    /**
+     * Updates mapping with data loaded from XML. JPA specification gives some leeway in
+     * processing conflicting mapping files. Cayenne provider strategy is "last mapping
+     * file overrides all".
      * <h3>Specification Documentation, Chapter 6.2.1.6</h3>
      * <p>
      * An <em>orm.xml</em> file may be specified in the META-INF directory in the root
@@ -123,12 +123,13 @@
      * present anywhere on the classpath. An orm.xml file or other mapping file is loaded
      * as a resource by the persistence provider.
      */
-    protected JpaEntityMap loadFromXML(PersistenceUnitInfo persistenceUnit)
+    protected void updateFromXML(JpaEntityMap baseMap, PersistenceUnitInfo persistenceUnit)
             throws IOException {
 
+        EntityMapMergeProcessor merger = new EntityMapMergeProcessor(baseMap, context);
+
         Set loadedLocations = new HashSet();
         EntityMapXMLLoader loader = new EntityMapXMLLoader();
-        JpaEntityMap map = null;
 
         // 1. load from the standard file called orm.xml
         loadedLocations.add(DESCRIPTOR_LOCATION);
@@ -137,7 +138,8 @@
                 .getResources(DESCRIPTOR_LOCATION);
 
         while (standardDescriptors.hasMoreElements()) {
-            map = loadFromXML(loader, standardDescriptors.nextElement(), map);
+            JpaEntityMap map = loader.getEntityMap(standardDescriptors.nextElement());
+            merger.mergeOverride(map);
         }
 
         // 2. load from orm.xml within the jars
@@ -154,35 +156,45 @@
                         .getClassLoader()
                         .getResources(descriptor);
                 while (mappedDescriptors.hasMoreElements()) {
-                    map = loadFromXML(loader, mappedDescriptors.nextElement(), map);
+                    JpaEntityMap map = loader.getEntityMap(mappedDescriptors
+                            .nextElement());
+                    merger.mergeOverride(map);
                 }
             }
         }
-
-        return map != null ? map : new JpaEntityMap();
     }
 
+    /**
+     * Creates a new JpaEntityMap based on metadata annotations of persistent classes.
+     */
     protected JpaEntityMap loadFromAnnotations(PersistenceUnitInfo persistenceUnit) {
 
-        // TODO: implement me!
-        return new JpaEntityMap();
-    }
+        JpaEntityMap map = new JpaEntityMap();
 
-    /**
-     * Loads a single descriptor from provided URL, merging it with an existing descriptor
-     * if it exists. Retruns a combination descriptor.
-     */
-    private JpaEntityMap loadFromXML(
-            EntityMapXMLLoader loader,
-            URL url,
-            JpaEntityMap baseMap) {
+        if (!persistenceUnit.getManagedClassNames().isEmpty()) {
+
+            ClassLoader loader = persistenceUnit.getClassLoader();
+            EntityMapAnnotationLoader annotationLoader = new EntityMapAnnotationLoader(
+                    context);
+
+            for (String className : persistenceUnit.getManagedClassNames()) {
+
+                Class managedClass;
+                try {
+                    managedClass = Class.forName(className, true, loader);
+                }
+                catch (ClassNotFoundException e) {
+                    throw new JpaProviderException("Class not found: " + className, e);
+                }
 
-        JpaEntityMap map = loader.getEntityMap(url);
-        if (baseMap == null) {
-            return map;
+                annotationLoader.loadClassMapping(map, managedClass);
+            }
         }
 
-        baseMap.mergeNoOverride(map, context);
-        return baseMap;
+        return map;
+    }
+
+    public JpaLoaderContext getContext() {
+        return context;
     }
 }

Added: incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapMergeProcessor.java
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapMergeProcessor.java?rev=398217&view=auto
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapMergeProcessor.java (added)
+++ incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapMergeProcessor.java Sat Apr 29 11:52:18 2006
@@ -0,0 +1,42 @@
+/*
+ *  Copyright 2006 The Apache Software Foundation
+ *
+ *  Licensed 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.jpa.conf;
+
+import org.apache.cayenne.jpa.map.JpaEntityMap;
+
+/**
+ * Implements an algorithm for merging two JpaEntityMaps.
+ * 
+ * @author Andrus Adamchik
+ */
+public class EntityMapMergeProcessor {
+
+    protected JpaEntityMap baseMap;
+    protected JpaLoaderContext context;
+
+    public EntityMapMergeProcessor(JpaEntityMap baseMap, JpaLoaderContext context) {
+        this.baseMap = baseMap;
+        this.context = context;
+    }
+
+    public void mergeOverride(JpaEntityMap map) {
+
+    }
+
+    public void mergeNoOverride(JpaEntityMap map) {
+
+    }
+}

Copied: incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/JpaLoaderContext.java (from r398019, incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapLoaderContext.java)
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/JpaLoaderContext.java?p2=incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/JpaLoaderContext.java&p1=incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapLoaderContext.java&r1=398019&r2=398217&rev=398217&view=diff
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/EntityMapLoaderContext.java (original)
+++ incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/conf/JpaLoaderContext.java Sat Apr 29 11:52:18 2006
@@ -29,12 +29,12 @@
  * 
  * @author Andrus Adamchik
  */
-public class EntityMapLoaderContext {
+public class JpaLoaderContext {
 
     protected Map<String, JpaClassDescriptor> descriptors;
     protected ValidationResult conflicts;
 
-    public EntityMapLoaderContext() {
+    public JpaLoaderContext() {
         this.conflicts = new ValidationResult();
     }
 
@@ -85,8 +85,8 @@
 
         LinkedList stack = new LinkedList();
 
-        public EntityMapLoaderContext getContext() {
-            return EntityMapLoaderContext.this;
+        public JpaLoaderContext getContext() {
+            return JpaLoaderContext.this;
         }
 
         public int depth() {
@@ -119,7 +119,7 @@
                 buffer.append(", details: ").append(message);
             }
 
-            EntityMapLoaderContext.this.recordConflict(new SimpleValidationFailure(
+            JpaLoaderContext.this.recordConflict(new SimpleValidationFailure(
                     peek(),
                     buffer.toString()));
         }

Modified: incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaEntityManager.java
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaEntityManager.java?rev=398217&r1=398216&r2=398217&view=diff
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaEntityManager.java (original)
+++ incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaEntityManager.java Sat Apr 29 11:52:18 2006
@@ -29,43 +29,42 @@
 
 public class CjpaEntityManager extends JpaEntityManager {
 
-    private DataContext ctxt;
+    private DataContext context;
 
-    public CjpaEntityManager(EntityManagerFactory factory,
+    public CjpaEntityManager(DataContext context, EntityManagerFactory factory,
             PersistenceContextType contextType) {
         super(factory, contextType);
-
-        ctxt = DataContext.createDataContext();
+        this.context = context;
     }
 
     @Override
     protected void persistInternal(Object entity) {
         checkEntityType(entity);
-        ctxt.registerNewObject((DataObject) entity);
+        context.registerNewObject((DataObject) entity);
     }
 
     @Override
     protected <T> T mergeInternal(T entity) {
         checkEntityType(entity);
         Persistent dao = (Persistent) entity;
-        return (T) ctxt.localObject(dao.getObjectId(), dao);
+        return (T) context.localObject(dao.getObjectId(), dao);
     }
 
     @Override
     protected void removeInternal(Object entity) {
         checkEntityType(entity);
-        ctxt.deleteObject((Persistent) entity);
+        context.deleteObject((Persistent) entity);
     }
 
     @Override
     protected <T> T findInternal(Class<T> entityClass, Object primaryKey) {
-        return (T) DataObjectUtils.objectForPK(ctxt, entityClass, primaryKey);
+        return (T) DataObjectUtils.objectForPK(context, entityClass, primaryKey);
     }
 
     @Override
     protected void flushInternal() {
         try {
-            ctxt.commitChanges();
+            context.commitChanges();
         }
         catch (CayenneRuntimeException e) {
             throw new PersistenceException(e);
@@ -83,22 +82,22 @@
         checkEntityType(entity);
 
         Persistent p = (Persistent) entity;
-        return p.getObjectContext() == ctxt;
+        return p.getObjectContext() == context;
     }
-    
+
     @Override
     public Query createNamedQuery(String name) {
         checkClosed();
 
-        return new CjpaQuery(ctxt, name);
+        return new CjpaQuery(context, name);
     }
-    
+
     @Override
     public Query createNativeQuery(String sqlString, Class resultClass) {
         checkClosed();
         checkEntityType(resultClass);
-        
-        return new CjpaNativeQuery(ctxt, sqlString, resultClass);
+
+        return new CjpaNativeQuery(context, sqlString, resultClass);
     }
 
     protected void checkEntityType(Object entity) throws IllegalArgumentException {

Modified: incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaEntityManagerFactory.java
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaEntityManagerFactory.java?rev=398217&r1=398216&r2=398217&view=diff
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaEntityManagerFactory.java (original)
+++ incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaEntityManagerFactory.java Sat Apr 29 11:52:18 2006
@@ -20,25 +20,28 @@
 import javax.persistence.spi.PersistenceUnitInfo;
 
 import org.apache.cayenne.jpa.JpaEntityManagerFactory;
+import org.objectstyle.cayenne.access.DataDomain;
 
 /**
  * A default EntityManagerFactory used by Cayenne JPA provider.
  * <h3>Cayenne Compatibility Note</h3>
  * <p>
- * CjpaEntityManagerFactory wraps a special Cayenne Configuration object that can load
- * both JPA and regular Cayenne mappings.
+ * CjpaEntityManagerFactory wraps a DataDomain that maps to a persistence unit.
  * </p>
  * 
  * @author Andrus Adamchik
  */
 public class CjpaEntityManagerFactory extends JpaEntityManagerFactory {
 
-    public CjpaEntityManagerFactory(PersistenceUnitInfo unitInfo) {
+    protected DataDomain domain;
+
+    public CjpaEntityManagerFactory(DataDomain domain, PersistenceUnitInfo unitInfo) {
         super(unitInfo);
+        this.domain = domain;
     }
 
     @Override
     protected EntityManager createEntityManagerInternal(PersistenceContextType type) {
-        return new CjpaEntityManager(this, type);
+        return new CjpaEntityManager(domain.createDataContext(), this, type);
     }
 }

Modified: incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaPersistenceProvider.java
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaPersistenceProvider.java?rev=398217&r1=398216&r2=398217&view=diff
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaPersistenceProvider.java (original)
+++ incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/cspi/CjpaPersistenceProvider.java Sat Apr 29 11:52:18 2006
@@ -15,19 +15,31 @@
  */
 package org.apache.cayenne.jpa.cspi;
 
+import java.io.InputStream;
+
 import javax.persistence.EntityManagerFactory;
 import javax.persistence.spi.PersistenceUnitInfo;
 import javax.persistence.spi.PersistenceUnitTransactionType;
 
+import org.apache.cayenne.jpa.bridge.DataMapConverter;
+import org.apache.cayenne.jpa.conf.EntityMapLoader;
+import org.apache.cayenne.jpa.map.JpaEntityMap;
 import org.apache.cayenne.jpa.spi.JpaPersistenceProvider;
+import org.objectstyle.cayenne.access.DataDomain;
+import org.objectstyle.cayenne.conf.Configuration;
+import org.objectstyle.cayenne.map.DataMap;
+import org.objectstyle.cayenne.util.ResourceLocator;
 
 /**
- * A PersistenceProvider implementation based on Cayenne stack.
+ * A PersistenceProvider implementation based on Cayenne stack. Wraps a Cayenne
+ * Configuration instance.
  * 
  * @author Andrus Adamchik
  */
 public class CjpaPersistenceProvider extends JpaPersistenceProvider {
 
+    protected Configuration configuration;
+
     /**
      * Creates a new PersistenceProvider with properties configured to run in a standalone
      * mode with Cayenne stack.
@@ -45,6 +57,11 @@
         defaultProperties.put(
                 TRANSACTION_TYPE_PROPERTY,
                 PersistenceUnitTransactionType.RESOURCE_LOCAL.name());
+
+        this.configuration = new LazyConfiguration();
+
+        // set a singleton that may be used by Cayenne
+        Configuration.initializeSharedConfiguration(configuration);
     }
 
     /**
@@ -53,6 +70,65 @@
      */
     @Override
     public EntityManagerFactory createContainerManagerFactory(PersistenceUnitInfo info) {
-        return new CjpaEntityManagerFactory(info);
+        String name = info.getPersistenceUnitName();
+        DataDomain domain = configuration.getDomain(name);
+
+        if (domain == null) {
+            domain = new DataDomain(name);
+            configuration.addDomain(domain);
+
+            // TODO: andrus, 4/29/2006 - report conflicts...
+
+            EntityMapLoader loader = new EntityMapLoader(info);
+            JpaEntityMap jpaMap = loader.getEntityMap();
+            
+            DataMapConverter converter = new DataMapConverter(loader.getContext());
+            DataMap cayenneMap = converter.toDataMap(name, jpaMap);
+
+            domain.addMap(cayenneMap);
+        }
+
+        return new CjpaEntityManagerFactory(domain, info);
+    }
+
+    public Configuration getConfiguration() {
+        return configuration;
     }
+
+    class LazyConfiguration extends Configuration {
+
+        @Override
+        public boolean canInitialize() {
+            return true;
+        }
+
+        @Override
+        public void initialize() throws Exception {
+        }
+
+        @Override
+        public void didInitialize() {
+        }
+
+        @Override
+        protected ResourceLocator getResourceLocator() {
+            throw new UnsupportedOperationException();
+        }
+
+        @Override
+        protected InputStream getDomainConfiguration() {
+            throw new UnsupportedOperationException();
+        }
+
+        @Override
+        protected InputStream getMapConfiguration(String name) {
+            throw new UnsupportedOperationException();
+        }
+
+        @Override
+        protected InputStream getViewConfiguration(String location) {
+            throw new UnsupportedOperationException();
+        }
+    }
+
 }

Modified: incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/map/JpaAbstractEntity.java
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/map/JpaAbstractEntity.java?rev=398217&r1=398216&r2=398217&view=diff
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/map/JpaAbstractEntity.java (original)
+++ incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/map/JpaAbstractEntity.java Sat Apr 29 11:52:18 2006
@@ -48,15 +48,17 @@
             throw new IllegalArgumentException("Null attribute name");
         }
 
-        for (JpaAttribute attribute : attributes) {
-            if (attributeName.equals(attribute.getName())) {
-                return attribute;
+        if (attributes != null) {
+            for (JpaAttribute attribute : attributes) {
+                if (attributeName.equals(attribute.getName())) {
+                    return attribute;
+                }
             }
         }
 
         return null;
     }
-    
+
     @TreeNodeChild
     public JpaEmbeddedId getEmbeddedId() {
         return embeddedId;
@@ -155,7 +157,7 @@
         this.preUpdate = preUpdate;
     }
 
-    @TreeNodeChild(type=JpaId.class)
+    @TreeNodeChild(type = JpaId.class)
     public Collection<JpaId> getIds() {
         if (ids == null) {
             ids = new ArrayList<JpaId>();
@@ -164,7 +166,7 @@
         return ids;
     }
 
-    @TreeNodeChild(type=JpaAttribute.class)
+    @TreeNodeChild(type = JpaAttribute.class)
     public Collection<JpaAttribute> getAttributes() {
         if (attributes == null) {
             attributes = new ArrayList<JpaAttribute>();

Modified: incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/map/JpaEntityMap.java
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/map/JpaEntityMap.java?rev=398217&r1=398216&r2=398217&view=diff
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/map/JpaEntityMap.java (original)
+++ incubator/cayenne/trunk/cayenne-jpa/src/main/java/org/apache/cayenne/jpa/map/JpaEntityMap.java Sat Apr 29 11:52:18 2006
@@ -21,7 +21,6 @@
 import javax.persistence.CascadeType;
 import javax.persistence.FlushModeType;
 
-import org.apache.cayenne.jpa.conf.EntityMapLoaderContext;
 import org.apache.cayenne.util.TreeNodeChild;
 
 /**
@@ -50,26 +49,17 @@
     protected JpaEntityListeners defaultEntityListeners;
     protected Collection<CascadeType> cascades;
 
-    /**
-     * Merges all entities from another map, overriding existing values.
-     * 
-     * @return An object containing unresolvable conflicts or null if no conflicts
-     *         occured.
-     */
-    public void mergeOverride(JpaEntityMap map) {
-        // TODO: implement
-        throw new UnsupportedOperationException("TODO");
-    }
-
-    /**
-     * Merges all entities from another map.
-     * 
-     * @return An object containing unresolvable conflicts or null if no conflicts
-     *         occured.
-     */
-    public void mergeNoOverride(JpaEntityMap map, EntityMapLoaderContext context) {
-        // TODO: implement
-        throw new UnsupportedOperationException("TODO");
+    public boolean isEmpty() {
+        return (entities == null || entities.isEmpty())
+                && (embeddables == null || embeddables.isEmpty())
+                && (mappedSuperclasses == null || mappedSuperclasses.isEmpty())
+                && (namedQueries == null || namedQueries.isEmpty())
+                && (namedNativeQueries == null || namedNativeQueries.isEmpty())
+                && (sqlResultSetMappings == null || sqlResultSetMappings.isEmpty())
+                && (sequenceGenerators == null || sequenceGenerators.isEmpty())
+                && (tableGenerators == null || tableGenerators.isEmpty())
+                && (cascades == null || cascades.isEmpty())
+                && defaultEntityListeners == null;
     }
 
     /**

Modified: incubator/cayenne/trunk/cayenne-jpa/src/test/java/org/apache/cayenne/jpa/bridge/DataMapConverterTest.java
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/test/java/org/apache/cayenne/jpa/bridge/DataMapConverterTest.java?rev=398217&r1=398216&r2=398217&view=diff
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/test/java/org/apache/cayenne/jpa/bridge/DataMapConverterTest.java (original)
+++ incubator/cayenne/trunk/cayenne-jpa/src/test/java/org/apache/cayenne/jpa/bridge/DataMapConverterTest.java Sat Apr 29 11:52:18 2006
@@ -18,14 +18,13 @@
 import junit.framework.TestCase;
 
 import org.apache.cayenne.jpa.conf.EntityMapAnnotationLoader;
-import org.apache.cayenne.jpa.conf.EntityMapDefaultsLoader;
-import org.apache.cayenne.jpa.conf.EntityMapLoaderContext;
+import org.apache.cayenne.jpa.conf.EntityMapDefaultsProcessor;
+import org.apache.cayenne.jpa.conf.JpaLoaderContext;
 import org.apache.cayenne.jpa.entity.cayenne.MockCayenneEntity1;
 import org.apache.cayenne.jpa.entity.cayenne.MockCayenneEntity2;
 import org.apache.cayenne.jpa.entity.cayenne.MockCayenneEntityMap1;
 import org.apache.cayenne.jpa.map.JpaEntityMap;
 import org.objectstyle.cayenne.map.DataMap;
-import org.objectstyle.cayenne.validation.ValidationResult;
 
 public class DataMapConverterTest extends TestCase {
 
@@ -37,9 +36,8 @@
         // TODO: unsupported by DataMap
         // jpaMap.setCatalog("c1");
 
-        DataMap cayenneMap = new DataMapConverter(new ValidationResult()).toDataMap(
-                "n1",
-                jpaMap);
+        DataMap cayenneMap = new DataMapConverter(new JpaLoaderContext())
+                .toDataMap("n1", jpaMap);
         assertEquals("n1", cayenneMap.getName());
         assertEquals("p1", cayenneMap.getDefaultPackage());
         assertEquals("s1", cayenneMap.getDefaultSchema());
@@ -50,7 +48,7 @@
      */
     public void testLoadClassMapping() throws Exception {
         JpaEntityMap map = new JpaEntityMap();
-        EntityMapLoaderContext context = new EntityMapLoaderContext();
+        JpaLoaderContext context = new JpaLoaderContext();
         EntityMapAnnotationLoader loader = new EntityMapAnnotationLoader(context);
 
         loader.loadClassMapping(map, MockCayenneEntity1.class);
@@ -59,15 +57,15 @@
         loader.loadClassMapping(map, MockCayenneEntityMap1.class);
 
         // apply defaults before conversion
-        new EntityMapDefaultsLoader(context).loadDefaults(map);
+        new EntityMapDefaultsProcessor(context).applyDefaults(map);
 
         assertFalse("Found conflicts: " + context.getConflicts(), context
                 .getConflicts()
                 .hasFailures());
 
-        ValidationResult dataMapConflicts = new ValidationResult();
-        DataMap dataMap = new DataMapConverter(dataMapConflicts).toDataMap("n1", map);
-        assertFalse("Found DataMap conflicts: " + dataMapConflicts, dataMapConflicts
+        DataMap dataMap = new DataMapConverter(context).toDataMap("n1", map);
+        assertFalse("Found DataMap conflicts: " + context.getConflicts(), context
+                .getConflicts()
                 .hasFailures());
 
         new DataMapMappingAssertion().testDataMap(dataMap);

Modified: incubator/cayenne/trunk/cayenne-jpa/src/test/java/org/apache/cayenne/jpa/conf/EntityMapAnnotationLoaderTest.java
URL: http://svn.apache.org/viewcvs/incubator/cayenne/trunk/cayenne-jpa/src/test/java/org/apache/cayenne/jpa/conf/EntityMapAnnotationLoaderTest.java?rev=398217&r1=398216&r2=398217&view=diff
==============================================================================
--- incubator/cayenne/trunk/cayenne-jpa/src/test/java/org/apache/cayenne/jpa/conf/EntityMapAnnotationLoaderTest.java (original)
+++ incubator/cayenne/trunk/cayenne-jpa/src/test/java/org/apache/cayenne/jpa/conf/EntityMapAnnotationLoaderTest.java Sat Apr 29 11:52:18 2006
@@ -46,7 +46,7 @@
     public void testSortAnnotations() throws Exception {
 
         EntityMapAnnotationLoader loader = new EntityMapAnnotationLoader(
-                new EntityMapLoaderContext());
+                new JpaLoaderContext());
 
         Annotation[] a1 = new Annotation[3];
         a1[0] = MockAnnotatedBean1.class.getAnnotation(NamedQuery.class);
@@ -66,7 +66,7 @@
      */
     public void testAttributeOverride() {
         JpaEntityMap map = new JpaEntityMap();
-        EntityMapLoaderContext context = new EntityMapLoaderContext();
+        JpaLoaderContext context = new JpaLoaderContext();
         EntityMapAnnotationLoader loader = new EntityMapAnnotationLoader(context);
         loader.loadClassMapping(map, MockAnnotatedBean2.class);
 
@@ -96,7 +96,7 @@
      */
     public void testLoadClassMapping() throws Exception {
         JpaEntityMap map = new JpaEntityMap();
-        EntityMapLoaderContext context = new EntityMapLoaderContext();
+        JpaLoaderContext context = new JpaLoaderContext();
         EntityMapAnnotationLoader loader = new EntityMapAnnotationLoader(context);
 
         loader.loadClassMapping(map, MockEntity1.class);