[hibernate-commits] Hibernate SVN: r20143 - in core/trunk: core/src/main/java/org/hibernate/action and 4 other directories.

hibernate-commits at lists.jboss.org hibernate-commits at lists.jboss.org
Fri Aug 13 18:29:42 EDT 2010


Author: steve.ebersole at jboss.com
Date: 2010-08-13 18:29:41 -0400 (Fri, 13 Aug 2010)
New Revision: 20143

Modified:
   core/trunk/core/src/main/java/org/hibernate/SessionFactory.java
   core/trunk/core/src/main/java/org/hibernate/action/BulkOperationCleanupAction.java
   core/trunk/core/src/main/java/org/hibernate/engine/ActionQueue.java
   core/trunk/core/src/main/java/org/hibernate/engine/SessionFactoryImplementor.java
   core/trunk/core/src/main/java/org/hibernate/impl/SessionFactoryImpl.java
   core/trunk/core/src/main/java/org/hibernate/jmx/SessionFactoryStub.java
   core/trunk/testsuite/src/test/java/org/hibernate/test/querycache/QueryCacheTest.java
Log:
HHH-5426 - HQL update/delete does not invalidate the query cache


Modified: core/trunk/core/src/main/java/org/hibernate/SessionFactory.java
===================================================================
--- core/trunk/core/src/main/java/org/hibernate/SessionFactory.java	2010-08-13 22:26:52 UTC (rev 20142)
+++ core/trunk/core/src/main/java/org/hibernate/SessionFactory.java	2010-08-13 22:29:41 UTC (rev 20143)
@@ -193,7 +193,7 @@
 	 *
 	 * @since 3.0 changed key from {@link Class} to {@link String}.
 	 */
-	public Map getAllClassMetadata();
+	public Map<String,ClassMetadata> getAllClassMetadata();
 
 	/**
 	 * Get the {@link CollectionMetadata} for all mapped collections

Modified: core/trunk/core/src/main/java/org/hibernate/action/BulkOperationCleanupAction.java
===================================================================
--- core/trunk/core/src/main/java/org/hibernate/action/BulkOperationCleanupAction.java	2010-08-13 22:26:52 UTC (rev 20142)
+++ core/trunk/core/src/main/java/org/hibernate/action/BulkOperationCleanupAction.java	2010-08-13 22:29:41 UTC (rev 20143)
@@ -1,10 +1,10 @@
 /*
  * Hibernate, Relational Persistence for Idiomatic Java
  *
- * Copyright (c) 2008, Red Hat Middleware LLC or third-party contributors as
+ * Copyright (c) 2010, Red Hat Inc. or third-party contributors as
  * indicated by the @author tags or express copyright attribution
  * statements applied by the authors.  All third-party contributions are
- * distributed under license by Red Hat Middleware LLC.
+ * distributed under license by Red Hat Inc.
  *
  * This copyrighted material is made available to anyone wishing to use, modify,
  * copy, or redistribute it subject to the terms and conditions of the GNU
@@ -20,28 +20,26 @@
  * Free Software Foundation, Inc.
  * 51 Franklin Street, Fifth Floor
  * Boston, MA  02110-1301  USA
- *
  */
 package org.hibernate.action;
 
+import java.io.Serializable;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.LinkedHashSet;
+import java.util.Set;
+
 import org.hibernate.HibernateException;
-import org.hibernate.cache.access.SoftLock;
-import org.hibernate.cache.access.EntityRegionAccessStrategy;
 import org.hibernate.cache.access.CollectionRegionAccessStrategy;
-import org.hibernate.persister.entity.EntityPersister;
-import org.hibernate.persister.entity.Queryable;
-import org.hibernate.persister.collection.CollectionPersister;
+import org.hibernate.cache.access.EntityRegionAccessStrategy;
+import org.hibernate.cache.access.SoftLock;
 import org.hibernate.engine.SessionFactoryImplementor;
 import org.hibernate.engine.SessionImplementor;
+import org.hibernate.persister.collection.CollectionPersister;
+import org.hibernate.persister.entity.EntityPersister;
+import org.hibernate.persister.entity.Queryable;
 
-import java.io.Serializable;
-import java.util.Map;
-import java.util.Set;
-import java.util.Iterator;
-import java.util.HashSet;
-import java.util.ArrayList;
-import java.util.Arrays;
-
 /**
  * An {@link org.hibernate.engine.ActionQueue} {@link Executable} for ensuring
  * shared cache cleanup in relation to performed bulk HQL queries.
@@ -57,8 +55,8 @@
 public class BulkOperationCleanupAction implements Executable, Serializable {
 	private final Serializable[] affectedTableSpaces;
 
-	private final Set entityCleanups = new HashSet();
-	private final Set collectionCleanups = new HashSet();
+	private final Set<EntityCleanup> entityCleanups = new HashSet<EntityCleanup>();
+	private final Set<CollectionCleanup> collectionCleanups = new HashSet<CollectionCleanup>();
 
 	/**
 	 * Constructs an action to cleanup "affected cache regions" based on the
@@ -72,17 +70,17 @@
 	 */
 	public BulkOperationCleanupAction(SessionImplementor session, Queryable[] affectedQueryables) {
 		SessionFactoryImplementor factory = session.getFactory();
-		ArrayList tmpSpaces = new ArrayList();
-		for ( int i = 0; i < affectedQueryables.length; i++ ) {
-			tmpSpaces.addAll( Arrays.asList( affectedQueryables[i].getQuerySpaces() ) );
-			if ( affectedQueryables[i].hasCache() ) {
-				entityCleanups.add( new EntityCleanup( affectedQueryables[i].getCacheAccessStrategy() ) );
+		LinkedHashSet<String> spacesList = new LinkedHashSet<String>();
+		for ( Queryable persister : affectedQueryables ) {
+			spacesList.addAll( Arrays.asList( (String[]) persister.getQuerySpaces() ) );
+
+			if ( persister.hasCache() ) {
+				entityCleanups.add( new EntityCleanup( persister.getCacheAccessStrategy() ) );
 			}
-			Set roles = factory.getCollectionRolesByEntityParticipant( affectedQueryables[i].getEntityName() );
+
+			Set<String> roles = factory.getCollectionRolesByEntityParticipant( persister.getEntityName() );
 			if ( roles != null ) {
-				Iterator itr = roles.iterator();
-				while ( itr.hasNext() ) {
-					String role = ( String ) itr.next();
+				for ( String role : roles ) {
 					CollectionPersister collectionPersister = factory.getCollectionPersister( role );
 					if ( collectionPersister.hasCache() ) {
 						collectionCleanups.add( new CollectionCleanup( collectionPersister.getCacheAccessStrategy() ) );
@@ -91,14 +89,14 @@
 			}
 		}
 
-		this.affectedTableSpaces = ( Serializable[] ) tmpSpaces.toArray( new Serializable[ tmpSpaces.size() ] );
+		this.affectedTableSpaces = spacesList.toArray( new String[ spacesList.size() ] );
 	}
 
 	/**
 	 * Constructs an action to cleanup "affected cache regions" based on a
 	 * set of affected table spaces.  This differs from {@link #BulkOperationCleanupAction(SessionImplementor, Queryable[])}
 	 * in that here we have the affected <strong>table names</strong>.  From those
-	 * we deduce the entity persisters whcih are affected based on the defined
+	 * we deduce the entity persisters which are affected based on the defined
 	 * {@link EntityPersister#getQuerySpaces() table spaces}; and from there, we
 	 * determine the affected collection regions based on any collections
 	 * in which those entity persisters participate as elements/keys/etc.
@@ -106,26 +104,24 @@
 	 * @param session The session to which this request is tied.
 	 * @param tableSpaces The table spaces.
 	 */
+	@SuppressWarnings({ "unchecked" })
 	public BulkOperationCleanupAction(SessionImplementor session, Set tableSpaces) {
-		Set tmpSpaces = new HashSet(tableSpaces);
-		SessionFactoryImplementor factory = session.getFactory();
-		Iterator iterator = factory.getAllClassMetadata().entrySet().iterator();
-		while ( iterator.hasNext() ) {
-			Map.Entry entry = (Map.Entry) iterator.next();
-			String entityName = (String) entry.getKey();
-			EntityPersister persister = factory.getEntityPersister( entityName );
-			Serializable[] entitySpaces = persister.getQuerySpaces();
+		LinkedHashSet<String> spacesList = new LinkedHashSet<String>();
+		spacesList.addAll( tableSpaces );
 
+		SessionFactoryImplementor factory = session.getFactory();
+		for ( String entityName : factory.getAllClassMetadata().keySet() ) {
+			final EntityPersister persister = factory.getEntityPersister( entityName );
+			final String[] entitySpaces = (String[]) persister.getQuerySpaces();
 			if ( affectedEntity( tableSpaces, entitySpaces ) ) {
-				tmpSpaces.addAll( Arrays.asList( entitySpaces ) );
+				spacesList.addAll( Arrays.asList( entitySpaces ) );
+
 				if ( persister.hasCache() ) {
 					entityCleanups.add( new EntityCleanup( persister.getCacheAccessStrategy() ) );
 				}
-				Set roles = session.getFactory().getCollectionRolesByEntityParticipant( persister.getEntityName() );
+				Set<String> roles = session.getFactory().getCollectionRolesByEntityParticipant( persister.getEntityName() );
 				if ( roles != null ) {
-					Iterator itr = roles.iterator();
-					while ( itr.hasNext() ) {
-						String role = ( String ) itr.next();
+					for ( String role : roles ) {
 						CollectionPersister collectionPersister = factory.getCollectionPersister( role );
 						if ( collectionPersister.hasCache() ) {
 							collectionCleanups.add(
@@ -137,7 +133,7 @@
 			}
 		}
 
-		this.affectedTableSpaces = ( Serializable[] ) tmpSpaces.toArray( new Serializable[ tmpSpaces.size() ] );
+		this.affectedTableSpaces = spacesList.toArray( new String[ spacesList.size() ] );
 	}
 
 
@@ -158,8 +154,8 @@
 			return true;
 		}
 
-		for ( int i = 0; i < checkTableSpaces.length; i++ ) {
-			if ( affectedTableSpaces.contains( checkTableSpaces[i] ) ) {
+		for ( Serializable checkTableSpace : checkTableSpaces ) {
+			if ( affectedTableSpaces.contains( checkTableSpace ) ) {
 				return true;
 			}
 		}

Modified: core/trunk/core/src/main/java/org/hibernate/engine/ActionQueue.java
===================================================================
--- core/trunk/core/src/main/java/org/hibernate/engine/ActionQueue.java	2010-08-13 22:26:52 UTC (rev 20142)
+++ core/trunk/core/src/main/java/org/hibernate/engine/ActionQueue.java	2010-08-13 22:29:41 UTC (rev 20143)
@@ -1,10 +1,10 @@
 /*
  * Hibernate, Relational Persistence for Idiomatic Java
  *
- * Copyright (c) 2008, Red Hat Middleware LLC or third-party contributors as
+ * Copyright (c) 2010, Red Hat Inc. or third-party contributors as
  * indicated by the @author tags or express copyright attribution
  * statements applied by the authors.  All third-party contributions are
- * distributed under license by Red Hat Middleware LLC.
+ * distributed under license by Red Hat Inc.
  *
  * This copyrighted material is made available to anyone wishing to use, modify,
  * copy, or redistribute it subject to the terms and conditions of the GNU
@@ -20,7 +20,6 @@
  * Free Software Foundation, Inc.
  * 51 Franklin Street, Fifth Floor
  * Boston, MA  02110-1301  USA
- *
  */
 package org.hibernate.engine;
 
@@ -30,17 +29,18 @@
 import java.io.Serializable;
 import java.util.ArrayList;
 import java.util.HashMap;
-import java.util.Iterator;
+import java.util.HashSet;
 import java.util.LinkedList;
 import java.util.List;
 import java.util.Set;
-import java.util.HashSet;
 
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
 import org.hibernate.AssertionFailure;
 import org.hibernate.HibernateException;
+import org.hibernate.action.AfterTransactionCompletionProcess;
+import org.hibernate.action.BeforeTransactionCompletionProcess;
 import org.hibernate.action.BulkOperationCleanupAction;
 import org.hibernate.action.CollectionRecreateAction;
 import org.hibernate.action.CollectionRemoveAction;
@@ -50,8 +50,6 @@
 import org.hibernate.action.EntityInsertAction;
 import org.hibernate.action.EntityUpdateAction;
 import org.hibernate.action.Executable;
-import org.hibernate.action.AfterTransactionCompletionProcess;
-import org.hibernate.action.BeforeTransactionCompletionProcess;
 import org.hibernate.cache.CacheException;
 import org.hibernate.type.Type;
 
@@ -121,36 +119,43 @@
 		collectionUpdates.clear();
 	}
 
+	@SuppressWarnings({ "unchecked" })
 	public void addAction(EntityInsertAction action) {
 		insertions.add( action );
 	}
 
+	@SuppressWarnings({ "unchecked" })
 	public void addAction(EntityDeleteAction action) {
 		deletions.add( action );
 	}
 
+	@SuppressWarnings({ "unchecked" })
 	public void addAction(EntityUpdateAction action) {
 		updates.add( action );
 	}
 
+	@SuppressWarnings({ "unchecked" })
 	public void addAction(CollectionRecreateAction action) {
 		collectionCreations.add( action );
 	}
 
+	@SuppressWarnings({ "unchecked" })
 	public void addAction(CollectionRemoveAction action) {
 		collectionRemovals.add( action );
 	}
 
+	@SuppressWarnings({ "unchecked" })
 	public void addAction(CollectionUpdateAction action) {
 		collectionUpdates.add( action );
 	}
 
+	@SuppressWarnings({ "unchecked" })
 	public void addAction(EntityIdentityInsertAction insert) {
 		insertions.add( insert );
 	}
 
 	public void addAction(BulkOperationCleanupAction cleanupAction) {
-		registerProcess( cleanupAction.getAfterTransactionCompletionProcess() );
+		registerCleanupActions( cleanupAction );
 	}
 
 	public void registerProcess(AfterTransactionCompletionProcess process) {
@@ -238,14 +243,14 @@
 		return ( insertions.size() > 0 || deletions.size() > 0 );
 	}
 
-	private static boolean areTablesToUpdated(List executables, Set tablespaces) {
-		int size = executables.size();
-		for ( int j = 0; j < size; j++ ) {
-			Serializable[] spaces = ( ( Executable ) executables.get( j ) ).getPropertySpaces();
-			for ( int i = 0; i < spaces.length; i++ ) {
-				if ( tablespaces.contains( spaces[i] ) ) {
+	@SuppressWarnings({ "unchecked" })
+	private static boolean areTablesToUpdated(List actions, Set tableSpaces) {
+		for ( Executable action : (List<Executable>) actions ) {
+			final Serializable[] spaces = action.getPropertySpaces();
+			for ( Serializable space : spaces ) {
+				if ( tableSpaces.contains( space ) ) {
 					if ( log.isDebugEnabled() ) {
-						log.debug( "changes must be flushed to space: " + spaces[i] );
+						log.debug( "changes must be flushed to space: " + space );
 					}
 					return true;
 				}
@@ -268,20 +273,23 @@
 			executable.execute();
 		}
 		finally {
-			beforeTransactionProcesses.register( executable.getBeforeTransactionCompletionProcess() );
-			if ( session.getFactory().getSettings().isQueryCacheEnabled() ) {
-				final String[] spaces = (String[]) executable.getPropertySpaces();
-				afterTransactionProcesses.addSpacesToInvalidate( spaces );
-				session.getFactory().getUpdateTimestampsCache().preinvalidate( executable.getPropertySpaces() );
-			}
-			afterTransactionProcesses.register( executable.getAfterTransactionCompletionProcess() );
+			registerCleanupActions( executable );
 		}
 	}
 
+	private void registerCleanupActions(Executable executable) {
+		beforeTransactionProcesses.register( executable.getBeforeTransactionCompletionProcess() );
+		if ( session.getFactory().getSettings().isQueryCacheEnabled() ) {
+			final String[] spaces = (String[]) executable.getPropertySpaces();
+			afterTransactionProcesses.addSpacesToInvalidate( spaces );
+			session.getFactory().getUpdateTimestampsCache().preinvalidate( spaces );
+		}
+		afterTransactionProcesses.register( executable.getAfterTransactionCompletionProcess() );
+	}
+
+	@SuppressWarnings({ "unchecked" })
 	private void prepareActions(List queue) throws HibernateException {
-		int size = queue.size();
-		for ( int i = 0; i < size; i++ ) {
-			Executable executable = ( Executable ) queue.get( i );
+		for ( Executable executable : (List<Executable>) queue ) {
 			executable.beforeExecutions();
 		}
 	}
@@ -327,6 +335,7 @@
 		return insertions.size();
 	}
 
+	@SuppressWarnings({ "unchecked" })
 	public void sortCollectionActions() {
 		if ( session.getFactory().getSettings().isOrderUpdatesEnabled() ) {
 			//sort the updates by fk
@@ -336,6 +345,7 @@
 		}
 	}
 
+	@SuppressWarnings({ "unchecked" })
 	public void sortActions() {
 		if ( session.getFactory().getSettings().isOrderUpdatesEnabled() ) {
 			//sort the updates by pk
@@ -359,6 +369,7 @@
 		new InsertActionSorter().sort();
 	}
 
+	@SuppressWarnings({ "UnusedDeclaration" })
 	public ArrayList cloneDeletions() {
 		return ( ArrayList ) deletions.clone();
 	}
@@ -374,6 +385,7 @@
 		}
 	}
 
+	@SuppressWarnings({ "UnusedDeclaration" })
 	public boolean hasAfterTransactionActions() {
 		return afterTransactionProcesses.processes.size() > 0;
 	}
@@ -457,6 +469,7 @@
 	 * @throws IOException indicates a problem reading from the stream
 	 * @throws ClassNotFoundException Generally means we were unable to locate user classes.
 	 */
+	@SuppressWarnings({ "unchecked" })
 	public static ActionQueue deserialize(
 			ObjectInputStream ois,
 			SessionImplementor session) throws IOException, ClassNotFoundException {
@@ -465,42 +478,42 @@
 
 		int queueSize = ois.readInt();
 		log.trace( "starting deserialization of [" + queueSize + "] insertions entries" );
-		rtn.insertions = new ArrayList( queueSize );
+		rtn.insertions = new ArrayList<Executable>( queueSize );
 		for ( int i = 0; i < queueSize; i++ ) {
 			rtn.insertions.add( ois.readObject() );
 		}
 
 		queueSize = ois.readInt();
 		log.trace( "starting deserialization of [" + queueSize + "] deletions entries" );
-		rtn.deletions = new ArrayList( queueSize );
+		rtn.deletions = new ArrayList<Executable>( queueSize );
 		for ( int i = 0; i < queueSize; i++ ) {
 			rtn.deletions.add( ois.readObject() );
 		}
 
 		queueSize = ois.readInt();
 		log.trace( "starting deserialization of [" + queueSize + "] updates entries" );
-		rtn.updates = new ArrayList( queueSize );
+		rtn.updates = new ArrayList<Executable>( queueSize );
 		for ( int i = 0; i < queueSize; i++ ) {
 			rtn.updates.add( ois.readObject() );
 		}
 
 		queueSize = ois.readInt();
 		log.trace( "starting deserialization of [" + queueSize + "] collectionUpdates entries" );
-		rtn.collectionUpdates = new ArrayList( queueSize );
+		rtn.collectionUpdates = new ArrayList<Executable>( queueSize );
 		for ( int i = 0; i < queueSize; i++ ) {
 			rtn.collectionUpdates.add( ois.readObject() );
 		}
 
 		queueSize = ois.readInt();
 		log.trace( "starting deserialization of [" + queueSize + "] collectionRemovals entries" );
-		rtn.collectionRemovals = new ArrayList( queueSize );
+		rtn.collectionRemovals = new ArrayList<Executable>( queueSize );
 		for ( int i = 0; i < queueSize; i++ ) {
 			rtn.collectionRemovals.add( ois.readObject() );
 		}
 
 		queueSize = ois.readInt();
 		log.trace( "starting deserialization of [" + queueSize + "] collectionCreations entries" );
-		rtn.collectionCreations = new ArrayList( queueSize );
+		rtn.collectionCreations = new ArrayList<Executable>( queueSize );
 		for ( int i = 0; i < queueSize; i++ ) {
 			rtn.collectionCreations.add( ois.readObject() );
 		}
@@ -509,7 +522,7 @@
 
 	private static class BeforeTransactionCompletionProcessQueue {
 		private SessionImplementor session;
-		private List processes = new ArrayList();
+		private List<BeforeTransactionCompletionProcess> processes = new ArrayList<BeforeTransactionCompletionProcess>();
 
 		private BeforeTransactionCompletionProcessQueue(SessionImplementor session) {
 			this.session = session;
@@ -526,7 +539,7 @@
 			final int size = processes.size();
 			for ( int i = 0; i < size; i++ ) {
 				try {
-					BeforeTransactionCompletionProcess process = ( BeforeTransactionCompletionProcess ) processes.get( i );
+					BeforeTransactionCompletionProcess process = processes.get( i );
 					process.doBeforeTransactionCompletion( session );
 				}
 				catch ( HibernateException he ) {
@@ -542,8 +555,9 @@
 
 	private static class AfterTransactionCompletionProcessQueue {
 		private SessionImplementor session;
-		private Set querySpacesToInvalidate = new HashSet();
-		private List processes = new ArrayList( INIT_QUEUE_LIST_SIZE * 3 );
+		private Set<String> querySpacesToInvalidate = new HashSet<String>();
+		private List<AfterTransactionCompletionProcess> processes
+				= new ArrayList<AfterTransactionCompletionProcess>( INIT_QUEUE_LIST_SIZE * 3 );
 
 		private AfterTransactionCompletionProcessQueue(SessionImplementor session) {
 			this.session = session;
@@ -573,7 +587,7 @@
 			final int size = processes.size();
 			for ( int i = 0; i < size; i++ ) {
 				try {
-					AfterTransactionCompletionProcess process = ( AfterTransactionCompletionProcess ) processes.get( i );
+					AfterTransactionCompletionProcess process = processes.get( i );
 					process.doAfterTransactionCompletion( success, session );
 				}
 				catch ( CacheException ce ) {
@@ -588,7 +602,7 @@
 
 			if ( session.getFactory().getSettings().isQueryCacheEnabled() ) {
 				session.getFactory().getUpdateTimestampsCache().invalidate(
-						( String[] ) querySpacesToInvalidate.toArray( new String[ querySpacesToInvalidate.size()] )
+						querySpacesToInvalidate.toArray( new String[ querySpacesToInvalidate.size()] )
 				);
 			}
 			querySpacesToInvalidate.clear();
@@ -616,11 +630,10 @@
 		/**
 		 * Sort the insert actions.
 		 */
+		@SuppressWarnings({ "unchecked", "UnnecessaryBoxing" })
 		public void sort() {
-
 			// the list of entity names that indicate the batch number
-			for ( Iterator actionItr = insertions.iterator(); actionItr.hasNext(); ) {
-				EntityInsertAction action = ( EntityInsertAction ) actionItr.next();
+			for ( EntityInsertAction action : (List<EntityInsertAction>) insertions ) {
 				// remove the current element from insertions. It will be added back later.
 				String entityName = action.getEntityName();
 
@@ -641,7 +654,7 @@
 					// doing the batch number before adding the name to the list is
 					// a faster way to get an accurate number.
 
-					batchNumber = new Integer( actionBatches.size() );
+					batchNumber = Integer.valueOf( actionBatches.size() );
 					latestBatches.put( entityName, batchNumber );
 				}
 				entityBatchNumber.put( currentEntity, batchNumber );
@@ -652,8 +665,8 @@
 			// now rebuild the insertions list. There is a batch for each entry in the name list.
 			for ( int i = 0; i < actionBatches.size(); i++ ) {
 				List batch = ( List ) actionBatches.get( new Integer( i ) );
-				for ( Iterator batchItr = batch.iterator(); batchItr.hasNext(); ) {
-					EntityInsertAction action = ( EntityInsertAction ) batchItr.next();
+				for ( Object aBatch : batch ) {
+					EntityInsertAction action = (EntityInsertAction) aBatch;
 					insertions.add( action );
 				}
 			}
@@ -667,6 +680,7 @@
 		 *
 		 * @return An appropriate batch number; todo document this process better
 		 */
+		@SuppressWarnings({ "UnnecessaryBoxing", "unchecked" })
 		private Integer findBatchNumber(
 				EntityInsertAction action,
 				String entityName) {
@@ -691,7 +705,7 @@
 					Integer associationBatchNumber = ( Integer ) entityBatchNumber.get( value );
 					if ( associationBatchNumber != null && associationBatchNumber.compareTo( latestBatchNumberForType ) > 0 ) {
 						// create a new batch for this type. The batch number is the number of current batches.
-						latestBatchNumberForType = new Integer( actionBatches.size() );
+						latestBatchNumberForType = Integer.valueOf( actionBatches.size() );
 						latestBatches.put( entityName, latestBatchNumberForType );
 						// since this entity will now be processed in the latest possible batch,
 						// we can be assured that it will come after all other associations,
@@ -703,6 +717,7 @@
 			return latestBatchNumberForType;
 		}
 
+		@SuppressWarnings({ "unchecked" })
 		private void addToBatch(Integer batchNumber, EntityInsertAction action) {
 			List actions = ( List ) actionBatches.get( batchNumber );
 

Modified: core/trunk/core/src/main/java/org/hibernate/engine/SessionFactoryImplementor.java
===================================================================
--- core/trunk/core/src/main/java/org/hibernate/engine/SessionFactoryImplementor.java	2010-08-13 22:26:52 UTC (rev 20142)
+++ core/trunk/core/src/main/java/org/hibernate/engine/SessionFactoryImplementor.java	2010-08-13 22:29:41 UTC (rev 20143)
@@ -230,7 +230,7 @@
 	 * @param entityName The entity name for which to get the collection roles.
 	 * @return set of all the collection roles in which the given entityName participates.
 	 */
-	public Set getCollectionRolesByEntityParticipant(String entityName);
+	public Set<String> getCollectionRolesByEntityParticipant(String entityName);
 
 	public EntityNotFoundDelegate getEntityNotFoundDelegate();
 

Modified: core/trunk/core/src/main/java/org/hibernate/impl/SessionFactoryImpl.java
===================================================================
--- core/trunk/core/src/main/java/org/hibernate/impl/SessionFactoryImpl.java	2010-08-13 22:26:52 UTC (rev 20142)
+++ core/trunk/core/src/main/java/org/hibernate/impl/SessionFactoryImpl.java	2010-08-13 22:29:41 UTC (rev 20143)
@@ -158,10 +158,10 @@
 	private final String uuid;
 
 	private final transient Map entityPersisters;
-	private final transient Map classMetadata;
+	private final transient Map<String,ClassMetadata> classMetadata;
 	private final transient Map collectionPersisters;
 	private final transient Map collectionMetadata;
-	private final transient Map collectionRolesByEntityParticipant;
+	private final transient Map<String,Set<String>> collectionRolesByEntityParticipant;
 	private final transient Map identifierGenerators;
 	private final transient Map namedQueries;
 	private final transient Map namedSqlQueries;
@@ -263,7 +263,7 @@
 
 		entityPersisters = new HashMap();
 		Map entityAccessStrategies = new HashMap();
-		Map classMeta = new HashMap();
+		Map<String,ClassMetadata> classMeta = new HashMap<String,ClassMetadata>();
 		classes = cfg.getClassMappings();
 		while ( classes.hasNext() ) {
 			final PersistentClass model = (PersistentClass) classes.next();
@@ -285,9 +285,9 @@
 			entityPersisters.put( model.getEntityName(), cp );
 			classMeta.put( model.getEntityName(), cp.getClassMetadata() );
 		}
-		classMetadata = Collections.unmodifiableMap(classMeta);
+		this.classMetadata = Collections.unmodifiableMap(classMeta);
 
-		Map tmpEntityToCollectionRoleMap = new HashMap();
+		Map<String,Set<String>> tmpEntityToCollectionRoleMap = new HashMap<String,Set<String>>();
 		collectionPersisters = new HashMap();
 		Iterator collections = cfg.getCollectionMappings();
 		while ( collections.hasNext() ) {
@@ -726,8 +726,8 @@
 		return settings.getSQLExceptionConverter();
 	}
 
-	public Set getCollectionRolesByEntityParticipant(String entityName) {
-		return ( Set ) collectionRolesByEntityParticipant.get( entityName );
+	public Set<String> getCollectionRolesByEntityParticipant(String entityName) {
+		return collectionRolesByEntityParticipant.get( entityName );
 	}
 
 	// from javax.naming.Referenceable
@@ -884,7 +884,7 @@
 		}
 	}
 
-	public Map getAllClassMetadata() throws HibernateException {
+	public Map<String,ClassMetadata> getAllClassMetadata() throws HibernateException {
 		return classMetadata;
 	}
 

Modified: core/trunk/core/src/main/java/org/hibernate/jmx/SessionFactoryStub.java
===================================================================
--- core/trunk/core/src/main/java/org/hibernate/jmx/SessionFactoryStub.java	2010-08-13 22:26:52 UTC (rev 20142)
+++ core/trunk/core/src/main/java/org/hibernate/jmx/SessionFactoryStub.java	2010-08-13 22:29:41 UTC (rev 20143)
@@ -131,7 +131,7 @@
 		return getImpl().getCollectionMetadata(roleName);
 	}
 
-	public Map getAllClassMetadata() throws HibernateException {
+	public Map<String,ClassMetadata> getAllClassMetadata() throws HibernateException {
 		return getImpl().getAllClassMetadata();
 	}
 

Modified: core/trunk/testsuite/src/test/java/org/hibernate/test/querycache/QueryCacheTest.java
===================================================================
--- core/trunk/testsuite/src/test/java/org/hibernate/test/querycache/QueryCacheTest.java	2010-08-13 22:26:52 UTC (rev 20142)
+++ core/trunk/testsuite/src/test/java/org/hibernate/test/querycache/QueryCacheTest.java	2010-08-13 22:29:41 UTC (rev 20143)
@@ -42,6 +42,51 @@
 	public static Test suite() {
 		return new FunctionalTestClassTestSuite( QueryCacheTest.class );
 	}
+
+	public void testInvalidationFromBulkHQL() {
+		// http://opensource.atlassian.com/projects/hibernate/browse/HHH-5426
+
+		getSessions().getCache().evictQueryRegions();
+		getSessions().getStatistics().clear();
+
+		Session s = openSession();
+		List list = new ArrayList();
+		s.beginTransaction();
+		for (int i = 0; i < 3; i++) {
+			Item a = new Item();
+			a.setName("a" + i);
+			a.setDescription("a" + i);
+			list.add(a);
+			s.persist(a);
+		}
+		s.getTransaction().commit();
+		s.close();
+
+		s = openSession();
+		s.beginTransaction();
+		String queryString = "select count(*) from Item";
+		// this query will hit the database and create the cache
+		Long result = (Long) s.createQuery(queryString).setCacheable(true).uniqueResult();
+		assertEquals(3, result.intValue());
+		s.getTransaction().commit();
+		s.close();
+
+		s = openSession();
+		s.beginTransaction();
+		String updateString = "delete from Item";
+		s.createQuery(updateString).executeUpdate();
+		s.getTransaction().commit();
+		s.close();
+
+		s = openSession();
+		s.beginTransaction();
+		// and this one SHOULD not be served by the cache
+		Number result2 = (Number) s.createQuery(queryString).setCacheable(true).uniqueResult();
+		assertEquals(0, result2.intValue());
+		s.getTransaction().commit();
+		s.close();
+	}
+
 	//https://jira.jboss.org/jira/browse/JBPAPP-4224
 	public void testHitCacheInSameSession() {
 		getSessions().evictQueries();



More information about the hibernate-commits mailing list