You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@openjpa.apache.org by al...@apache.org on 2008/10/02 22:41:18 UTC

svn commit: r701236 - in /openjpa/trunk: openjpa-kernel/src/main/java/org/apache/openjpa/kernel/ openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/ openjpa-persistence-jdbc/src/test/resources/META-INF/

Author: allee8285
Date: Thu Oct  2 13:41:18 2008
New Revision: 701236

URL: http://svn.apache.org/viewvc?rev=701236&view=rev
Log:
OPENJPA-732 - Fixed BrokerImpl's fields of type Set to consistently use the correct implementation type of HashSet rather than ArrayList or LinkList.

Added:
    openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/Message.java
    openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/MessageListenerImpl.java
    openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/TestMessageListeners.java
Modified:
    openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/BrokerImpl.java
    openjpa/trunk/openjpa-persistence-jdbc/src/test/resources/META-INF/listener-orm.xml
    openjpa/trunk/openjpa-persistence-jdbc/src/test/resources/META-INF/persistence.xml

Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/BrokerImpl.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/BrokerImpl.java?rev=701236&r1=701235&r2=701236&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/BrokerImpl.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/BrokerImpl.java Thu Oct  2 13:41:18 2008
@@ -1522,7 +1522,7 @@
                 _savepoints = new LinkedMap();
             } else {
                 if (_savepointCache == null)
-                    save.save(Collections.EMPTY_LIST);
+                    save.save(Collections.EMPTY_SET);
                 else {
                     save.save(_savepointCache);
                     _savepointCache.clear();
@@ -2190,7 +2190,7 @@
         if (hasTransactionalObjects())
             transStates = _transCache;
         else
-            transStates = Collections.EMPTY_LIST;
+            transStates = Collections.EMPTY_SET;
 
         // fire after rollback/commit event
         Collection mobjs = null;
@@ -2265,7 +2265,7 @@
 
         // now clear trans cache; keep cleared version rather than
         // null to avoid having to re-create the set later; more efficient
-        if (transStates != Collections.EMPTY_LIST) {
+        if (transStates != Collections.EMPTY_SET) {
             _transCache = (TransactionalCache) transStates;
             _transCache.clear();
         }
@@ -3310,7 +3310,7 @@
             Object obj;
             StateManagerImpl sm;
             ClassMetaData meta;
-            Collection sms = new ArrayList(objs.size());
+            Collection sms = new HashSet(objs.size());
             List exceps = null;
             for (Iterator itr = objs.iterator(); itr.hasNext();) {
                 obj = itr.next();
@@ -3637,7 +3637,7 @@
         try {
             assertActiveTransaction();
 
-            Collection sms = new ArrayList(objs.size());
+            Collection sms = new HashSet(objs.size());
             Object obj;
             StateManagerImpl sm;
             for (Iterator itr = objs.iterator(); itr.hasNext();) {
@@ -3784,7 +3784,7 @@
      */
     protected Collection getTransactionalStates() {
         if (!hasTransactionalObjects())
-            return Collections.EMPTY_LIST;
+            return Collections.EMPTY_SET;
         return _transCache.copy();
     }
 
@@ -3803,7 +3803,7 @@
      */
     protected Collection getDirtyStates() {
         if (!hasTransactionalObjects())
-            return Collections.EMPTY_LIST;
+            return Collections.EMPTY_SET;
 
         return _transCache.copyDirty();
     }
@@ -3814,8 +3814,8 @@
      */
     protected Collection getPendingTransactionalStates() {
         if (_pending == null)
-            return Collections.EMPTY_LIST;
-        return new ArrayList(_pending);
+            return Collections.EMPTY_SET;
+        return new HashSet(_pending);
     }
 
     /**
@@ -4036,19 +4036,19 @@
 
     public Collection getPersistedTypes() {
         if (_persistedClss == null || _persistedClss.isEmpty())
-            return Collections.EMPTY_LIST;
+            return Collections.EMPTY_SET;
         return Collections.unmodifiableCollection(_persistedClss);
     }
 
     public Collection getUpdatedTypes() {
         if (_updatedClss == null || _updatedClss.isEmpty())
-            return Collections.EMPTY_LIST;
+            return Collections.EMPTY_SET;
         return Collections.unmodifiableCollection(_updatedClss);
     }
 
     public Collection getDeletedTypes() {
         if (_deletedClss == null || _deletedClss.isEmpty())
-            return Collections.EMPTY_LIST;
+            return Collections.EMPTY_SET;
         return Collections.unmodifiableCollection(_deletedClss);
     }
 
@@ -4503,12 +4503,12 @@
          */
         public Collection copy() {
             if (isEmpty())
-                return Collections.EMPTY_LIST;
+                return Collections.EMPTY_SET;
 
             // size may not be entirely accurate due to refs expiring, so
             // manually copy each object; doesn't matter this way if size too
             // big by some
-            List copy = new ArrayList(size());
+            Set copy = new HashSet(size());
             if (_dirty != null)
                 for (Iterator itr = _dirty.iterator(); itr.hasNext();)
                     copy.add(itr.next());
@@ -4523,8 +4523,8 @@
          */
         public Collection copyDirty() {
             if (_dirty == null || _dirty.isEmpty())
-                return Collections.EMPTY_LIST;
-            return new ArrayList(_dirty);
+                return Collections.EMPTY_SET;
+            return new HashSet(_dirty);
         }
 
         /**

Added: openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/Message.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/Message.java?rev=701236&view=auto
==============================================================================
--- openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/Message.java (added)
+++ openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/Message.java Thu Oct  2 13:41:18 2008
@@ -0,0 +1,112 @@
+/*
+ * 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.persistence.callbacks;
+
+import java.util.Date;
+
+import javax.persistence.Basic;
+import javax.persistence.Entity;
+import javax.persistence.EntityListeners;
+import javax.persistence.Id;
+import javax.persistence.Version;
+
+/**
+ * A very simple persistent entity that holds a "message", has a "created" field
+ * that is initialized to the time at which the object was created, and an id
+ * field that is initialized to the current time.
+ */
+@Entity
+@EntityListeners(value = MessageListenerImpl.class)
+public class Message {
+    @Id
+    private long id = System.currentTimeMillis();
+
+    @Basic
+    private String message;
+
+    @Basic
+    private Date created = null;
+
+    @Basic
+    private Date updated = null;
+
+    @Version
+    Integer version;
+
+    public Message() {
+    }
+
+    public Message(String msg) {
+        message = msg;
+    }
+
+    public void setId(long val) {
+        id = val;
+    }
+
+    public long getId() {
+        return id;
+    }
+
+    public void setMessage(String msg) {
+        message = msg;
+    }
+
+    public String getMessage() {
+        return message;
+    }
+
+    public void setCreated(Date date) {
+        created = date;
+    }
+
+    public Date getCreated() {
+        return created;
+    }
+
+    public Integer getVersion() {
+        return version;
+    }
+
+    public void setVersion(Integer version) {
+        this.version = version;
+    }
+
+    public Date getUpdated() {
+        return updated;
+    }
+
+    public void setUpdated(Date updated) {
+        this.updated = updated;
+    }
+
+    @Override
+    public boolean equals(Object o) {
+        if (o instanceof Message) {
+            Message other = (Message) o;
+            return other.getId() == this.getId();
+        }
+        return false;
+    }
+
+    @Override
+    public int hashCode() {
+        return super.hashCode();
+    }
+}
\ No newline at end of file

Added: openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/MessageListenerImpl.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/MessageListenerImpl.java?rev=701236&view=auto
==============================================================================
--- openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/MessageListenerImpl.java (added)
+++ openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/MessageListenerImpl.java Thu Oct  2 13:41:18 2008
@@ -0,0 +1,102 @@
+/*
+ * 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.persistence.callbacks;
+
+import java.util.Date;
+
+import javax.persistence.PrePersist;
+import javax.persistence.PostPersist;
+import javax.persistence.PostLoad;
+import javax.persistence.PreUpdate;
+import javax.persistence.PostUpdate;
+import javax.persistence.PreRemove;
+import javax.persistence.PostRemove;
+
+public class MessageListenerImpl {
+
+    public static int prePersistCount;
+    public static int postPersistCount;
+    public static int preUpdateCount;
+    public static int postUpdateCount;
+    public static int preRemoveCount;
+    public static int postRemoveCount;
+    public static int postLoadCount;
+
+    @PrePersist
+    public void prePersist(Object o) {
+        prePersistCount++;
+
+        if (o instanceof Message) {
+            ((Message) o).setCreated(new Date());
+            ((Message) o).setUpdated(new Date());
+        }
+    }
+
+    @PostPersist
+    public void postPersist(Object o) {
+        postPersistCount++;
+    }
+
+    @PostLoad
+    public void postLoad(Object o) {
+        postLoadCount++;
+    }
+
+    @PreUpdate
+    public void preUpdate(Object o) {
+        preUpdateCount++;
+
+        if (o instanceof Message) {
+            ((Message) o).setUpdated(new Date());
+        }
+    }
+
+    @PostUpdate
+    public void postUpdate(Object o) {
+        postUpdateCount++;
+    }
+
+    @PreRemove
+    public void preRemove(Object o) {
+        preRemoveCount++;
+    }
+
+    @PostRemove
+    public void postRemove(Object o) {
+        postRemoveCount++;
+    }
+
+    public static void resetCounters() {
+        prePersistCount = 0;
+        postPersistCount = 0;
+        preUpdateCount = 0;
+        postUpdateCount = 0;
+        preRemoveCount = 0;
+        postRemoveCount = 0;
+        postLoadCount = 0;
+    }
+
+    public static String getStates() {
+        return "prePersistCount = " + prePersistCount + ", postPersistCount = "
+            + postPersistCount + ", preUpdateCount = " + preUpdateCount
+            + ", postUpdateCount = " + postUpdateCount + ", preRemoveCount = "
+            + preRemoveCount + ", postRemoveCount = " + postRemoveCount
+            + ", postLoadCount = " + postLoadCount;
+    }
+}

Added: openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/TestMessageListeners.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/TestMessageListeners.java?rev=701236&view=auto
==============================================================================
--- openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/TestMessageListeners.java (added)
+++ openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/callbacks/TestMessageListeners.java Thu Oct  2 13:41:18 2008
@@ -0,0 +1,180 @@
+/*
+ * 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.persistence.callbacks;
+
+import javax.persistence.Query;
+
+import org.apache.openjpa.persistence.test.SingleEMFTestCase;
+import org.apache.openjpa.persistence.OpenJPAEntityManager;
+
+public class TestMessageListeners extends SingleEMFTestCase {
+
+    public void setUp() {
+        setUp(CLEAR_TABLES);
+    }
+
+    @Override
+    protected String getPersistenceUnitName() {
+        return "listener-pu";
+    }
+
+    public void testUpdateInPrePersist() {
+        // Create a new EntityManager from the EntityManagerFactory. The
+        // EntityManager is the main object in the persistence API, and is
+        // used to create, delete, and query objects, as well as access
+        // the current transaction
+        OpenJPAEntityManager em = emf.createEntityManager();
+        try {
+            // Begin a new local transaction so that we can persist a new entity
+            em.getTransaction().begin();
+
+            MessageListenerImpl.resetCounters();
+
+            // Create and persist a new Message entity
+            Message message = new Message("Hello Persistence!");
+            assertNull("Test message's created field to be null.", message
+                .getCreated());
+            assertNull("Test message's updated field to be null.", message
+                .getUpdated());
+
+            em.persist(message);
+
+            // Pre-persist invoked, created and updated fields set
+            assertStatus(1, 0, 0, 0, 0, 0, 0);
+            assertNotNull("Test message's created field being set.", message
+                .getCreated());
+            assertNotNull("Test message's updated field being set.", message
+                .getUpdated());
+
+            em.flush();
+            // Post-persist invoked
+            assertStatus(1, 1, 0, 0, 0, 0, 0);
+
+            em.clear();
+
+            // Perform a simple query to get the Message
+            Query q = em.createQuery("select m from Message m where m.id="
+                + message.getId());
+            Message m = (Message) q.getSingleResult();
+
+            assertEquals("Test first expected message.", "Hello Persistence!",
+                m.getMessage());
+            assertNotNull("Test message's created field being set.", m
+                .getCreated());
+            assertNotNull("Test message's updated field being set.", m
+                .getUpdated());
+
+            // query trigger a load because em is cleared.
+            assertStatus(1, 1, 0, 0, 0, 0, 1);
+
+            em.getTransaction().commit();
+
+            // since data is flushed, commit data with no event fired.
+            assertStatus(1, 1, 0, 0, 0, 0, 1);
+        } finally {
+            if (em != null && em.getTransaction().isActive())
+                em.getTransaction().rollback();
+            if (em != null && em.isOpen())
+                em.close();
+        }
+    }
+
+    public void testUpdateInPreUpdate() {
+        // Create a new EntityManager from the EntityManagerFactory. The
+        // EntityManager is the main object in the persistence API, and is
+        // used to create, delete, and query objects, as well as access
+        // the current transaction
+        OpenJPAEntityManager em = emf.createEntityManager();
+        try {
+            // Begin a new local transaction so that we can persist a new entity
+            em.getTransaction().begin();
+
+            MessageListenerImpl.resetCounters();
+
+            // Create and persist a new Message entity
+            Message message = new Message("Hello Persistence!");
+            assertNull("Test message's created field to be null.", message
+                .getCreated());
+            assertNull("Test message's updated field to be null.", message
+                .getUpdated());
+
+            em.persist(message);
+
+            // Pre-persist invoked, created and updated fields set
+            assertStatus(1, 0, 0, 0, 0, 0, 0);
+            assertNotNull("Test message's created field being set.", message
+                .getCreated());
+            assertNotNull("Test message's updated field being set.", message
+                .getUpdated());
+
+            // Perform a simple query to get the Message
+            Query q = em.createQuery("select m from Message m where m.id="
+                + message.getId());
+            Message m = (Message) q.getSingleResult();
+            assertEquals("Test first expected message.", "Hello Persistence!",
+                m.getMessage());
+            assertNotNull("Test message's created field being set.", m
+                .getCreated());
+            assertNotNull("Test message's updated field being set.", m
+                .getUpdated());
+
+            // Query cause flush to occur, hence fire the postPersist event
+            assertStatus(1, 1, 0, 0, 0, 0, 0);
+
+            // Create and persist another new Message entity
+            message = new Message("Hello Persistence 2!");
+            assertNull("Test message's created field to be null.", message
+                .getCreated());
+            assertNull("Test message's updated field to be null.", message
+                .getUpdated());
+
+            em.persist(message);
+
+            // Pre-persist invoked, created and updated fields set
+            assertStatus(2, 1, 0, 0, 0, 0, 0);
+            assertNotNull("Test message's created field being set.", message
+                .getCreated());
+            assertNotNull("Test message's updated field being set.", message
+                .getUpdated());
+
+            em.getTransaction().commit();
+
+            // Complete the 2nd @postPersist and the @preUpdate caused by
+            // setters calls in @postPersist
+            assertStatus(2, 2, 1, 1, 0, 0, 0);
+
+        } finally {
+            if (em != null && em.getTransaction().isActive())
+                em.getTransaction().rollback();
+            if (em != null && em.isOpen())
+                em.close();
+        }
+    }
+
+    private void assertStatus(int prePersist, int postPersist, int preUpdate,
+        int postUpdate, int preRemove, int postRemove, int postLoad) {
+        assertEquals(prePersist, MessageListenerImpl.prePersistCount);
+        assertEquals(postPersist, MessageListenerImpl.postPersistCount);
+        assertEquals(preUpdate, MessageListenerImpl.preUpdateCount);
+        assertEquals(postUpdate, MessageListenerImpl.postUpdateCount);
+        assertEquals(preRemove, MessageListenerImpl.preRemoveCount);
+        assertEquals(postRemove, MessageListenerImpl.postRemoveCount);
+        assertEquals(postLoad, MessageListenerImpl.postLoadCount);
+    }
+}

Modified: openjpa/trunk/openjpa-persistence-jdbc/src/test/resources/META-INF/listener-orm.xml
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-persistence-jdbc/src/test/resources/META-INF/listener-orm.xml?rev=701236&r1=701235&r2=701236&view=diff
==============================================================================
--- openjpa/trunk/openjpa-persistence-jdbc/src/test/resources/META-INF/listener-orm.xml (original)
+++ openjpa/trunk/openjpa-persistence-jdbc/src/test/resources/META-INF/listener-orm.xml Thu Oct  2 13:41:18 2008
@@ -34,4 +34,7 @@
     <entity class="EntityListenerEntity">
         <exclude-default-listeners/>
     </entity>
+    <entity class="Message">
+        <exclude-default-listeners/>
+    </entity>
 </entity-mappings>
\ No newline at end of file

Modified: openjpa/trunk/openjpa-persistence-jdbc/src/test/resources/META-INF/persistence.xml
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-persistence-jdbc/src/test/resources/META-INF/persistence.xml?rev=701236&r1=701235&r2=701236&view=diff
==============================================================================
--- openjpa/trunk/openjpa-persistence-jdbc/src/test/resources/META-INF/persistence.xml (original)
+++ openjpa/trunk/openjpa-persistence-jdbc/src/test/resources/META-INF/persistence.xml Thu Oct  2 13:41:18 2008
@@ -84,6 +84,7 @@
         <mapping-file>META-INF/listener-orm.xml</mapping-file>
         <class>org.apache.openjpa.persistence.callbacks.EntityListenerEntity</class>
         <class>org.apache.openjpa.persistence.callbacks.GlobalListenerEntity</class>
+        <class>org.apache.openjpa.persistence.callbacks.Message</class>
         <properties>
             <property name="openjpa.jdbc.SynchronizeMappings"
                   value="buildSchema(ForeignKeys=true)"/>