HHH-7437 - Fix and test

This commit is contained in:
Lukasz Antoniak 2013-01-03 13:10:16 +01:00
parent 9f4f817a73
commit bcf73bd32c
3 changed files with 169 additions and 1 deletions

View File

@ -43,6 +43,7 @@ import org.hibernate.envers.entities.mapper.PropertyMapper;
import org.hibernate.envers.entities.mapper.relation.lazy.initializor.Initializor;
import org.hibernate.envers.exception.AuditException;
import org.hibernate.envers.reader.AuditReaderImplementor;
import org.hibernate.envers.tools.Tools;
import org.hibernate.envers.tools.reflection.ReflectionTools;
import org.hibernate.property.Setter;
@ -139,7 +140,10 @@ public abstract class AbstractCollectionMapper<T> implements PropertyMapper {
public void mapModifiedFlagsToMapFromEntity(SessionImplementor session, Map<String, Object> data, Object newObj, Object oldObj) {
PropertyData propertyData = commonCollectionMapperData.getCollectionReferencingPropertyData();
if (propertyData.isUsingModifiedFlag()) {
if(isFromNullToEmptyOrFromEmptyToNull((PersistentCollection) newObj, (Serializable) oldObj)){
if (isNotPersistentCollection(newObj) || isNotPersistentCollection(oldObj)) {
// Compare POJOs.
data.put(propertyData.getModifiedFlagPropertyName(), !Tools.objectsEqual(newObj, oldObj));
} else if (isFromNullToEmptyOrFromEmptyToNull((PersistentCollection) newObj, (Serializable) oldObj)) {
data.put(propertyData.getModifiedFlagPropertyName(), true);
} else {
List<PersistentCollectionChangeData> changes = mapCollectionChanges(
@ -150,6 +154,10 @@ public abstract class AbstractCollectionMapper<T> implements PropertyMapper {
}
}
private boolean isNotPersistentCollection(Object obj) {
return obj != null && !(obj instanceof PersistentCollection);
}
private boolean isFromNullToEmptyOrFromEmptyToNull(PersistentCollection newColl, Serializable oldColl) {
// Comparing new and old collection content.
Collection newCollection = getNewCollectionContent(newColl);

View File

@ -82,6 +82,20 @@ public class MultipleCollectionEntity {
refEntities2.remove(refEntity2);
}
/**
* For test purpose only.
*/
public void setRefEntities1(List<MultipleCollectionRefEntity1> refEntities1) {
this.refEntities1 = refEntities1;
}
/**
* For test purpose only.
*/
public void setRefEntities2(List<MultipleCollectionRefEntity2> refEntities2) {
this.refEntities2 = refEntities2;
}
@Override
public String toString() {
return "MultipleCollectionEntity [id=" + id + ", text=" + text

View File

@ -0,0 +1,146 @@
package org.hibernate.envers.test.integration.modifiedflags;
import java.util.ArrayList;
import java.util.List;
import javax.persistence.EntityManager;
import org.junit.Test;
import org.hibernate.envers.test.Priority;
import org.hibernate.envers.test.entities.collection.MultipleCollectionEntity;
import org.hibernate.envers.test.entities.collection.MultipleCollectionRefEntity1;
import org.hibernate.envers.test.entities.collection.MultipleCollectionRefEntity2;
import org.hibernate.testing.TestForIssue;
import static org.junit.Assert.assertEquals;
import static org.hibernate.envers.test.tools.TestTools.extractRevisionNumbers;
import static org.hibernate.envers.test.tools.TestTools.makeList;
/**
* @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com)
*/
@TestForIssue(jiraKey = "HHH-7437")
public class HasChangedDetachedMultipleCollection extends AbstractModifiedFlagsEntityTest {
private Long mce1Id = null;
private Long mce2Id = null;
private Long mcre1Id = null;
private Long mcre2Id = null;
@Override
protected Class<?>[] getAnnotatedClasses() {
return new Class<?>[] {
MultipleCollectionEntity.class, MultipleCollectionRefEntity1.class, MultipleCollectionRefEntity2.class
};
}
@Test
@Priority(10)
public void initData() {
EntityManager em = getEntityManager();
// Revision 1 - addition.
em.getTransaction().begin();
MultipleCollectionEntity mce1 = new MultipleCollectionEntity();
mce1.setText( "MultipleCollectionEntity-1-1" );
em.persist( mce1 ); // Persisting entity with empty collections.
em.getTransaction().commit();
mce1Id = mce1.getId();
// Revision 2 - update.
em.getTransaction().begin();
mce1 = em.find( MultipleCollectionEntity.class, mce1.getId() );
MultipleCollectionRefEntity1 mcre1 = new MultipleCollectionRefEntity1();
mcre1.setText( "MultipleCollectionRefEntity1-1-1" );
mcre1.setMultipleCollectionEntity( mce1 );
mce1.addRefEntity1( mcre1 );
em.persist( mcre1 );
mce1 = em.merge( mce1 );
em.getTransaction().commit();
mcre1Id = mcre1.getId();
// No changes.
em.getTransaction().begin();
mce1 = em.find( MultipleCollectionEntity.class, mce1.getId() );
mce1 = em.merge( mce1 );
em.getTransaction().commit();
em.close();
em = getEntityManager();
// Revision 3 - updating detached collection.
em.getTransaction().begin();
mce1.removeRefEntity1( mcre1 );
mce1 = em.merge( mce1 );
em.getTransaction().commit();
em.close();
em = getEntityManager();
// Revision 4 - updating detached entity, no changes to collection attributes.
em.getTransaction().begin();
mce1.setRefEntities1( new ArrayList<MultipleCollectionRefEntity1>() );
mce1.setRefEntities2( new ArrayList<MultipleCollectionRefEntity2>() );
mce1.setText( "MultipleCollectionEntity-1-2" );
mce1 = em.merge( mce1 );
em.getTransaction().commit();
em.close();
em = getEntityManager();
// No changes to detached entity (collections were empty before).
em.getTransaction().begin();
mce1.setRefEntities1( new ArrayList<MultipleCollectionRefEntity1>() );
mce1.setRefEntities2( new ArrayList<MultipleCollectionRefEntity2>() );
mce1 = em.merge( mce1 );
em.getTransaction().commit();
// Revision 5 - addition.
em.getTransaction().begin();
MultipleCollectionEntity mce2 = new MultipleCollectionEntity();
mce2.setText( "MultipleCollectionEntity-2-1" );
MultipleCollectionRefEntity2 mcre2 = new MultipleCollectionRefEntity2();
mcre2.setText( "MultipleCollectionRefEntity2-1-1" );
mcre2.setMultipleCollectionEntity( mce2 );
mce2.addRefEntity2( mcre2 );
em.persist( mce2 ); // Cascade persisting related entity.
em.getTransaction().commit();
mce2Id = mce2.getId();
mcre2Id = mcre2.getId();
em.close();
}
@Test
public void testHasChanged() {
List list = queryForPropertyHasChanged( MultipleCollectionEntity.class, mce1Id, "text" );
assertEquals( 2, list.size() );
assertEquals( makeList( 1, 4 ), extractRevisionNumbers( list ) );
list = queryForPropertyHasChanged( MultipleCollectionEntity.class, mce1Id, "refEntities1" );
assertEquals( 3, list.size() );
assertEquals( makeList( 1, 2, 3 ), extractRevisionNumbers( list ) );
list = queryForPropertyHasChanged( MultipleCollectionEntity.class, mce1Id, "refEntities2" );
assertEquals( 1, list.size() );
assertEquals( makeList( 1 ), extractRevisionNumbers( list ) );
list = queryForPropertyHasChanged( MultipleCollectionRefEntity1.class, mcre1Id, "text" );
assertEquals( 1, list.size() );
assertEquals( makeList( 2 ), extractRevisionNumbers( list ) );
list = queryForPropertyHasChanged( MultipleCollectionEntity.class, mce2Id, "text" );
assertEquals( 1, list.size() );
assertEquals( makeList( 5 ), extractRevisionNumbers( list ) );
list = queryForPropertyHasChanged( MultipleCollectionEntity.class, mce2Id, "refEntities2" );
assertEquals( 1, list.size() );
assertEquals( makeList( 5 ), extractRevisionNumbers( list ) );
list = queryForPropertyHasChanged( MultipleCollectionRefEntity2.class, mcre2Id, "text" );
assertEquals( 1, list.size() );
assertEquals( makeList( 5 ), extractRevisionNumbers( list ) );
}
}