HHH-8567 - Query identifier properties

This commit is contained in:
Lukasz Antoniak 2013-10-03 10:45:35 +02:00
parent c7dbdf9fd5
commit 7d455272ba
2 changed files with 92 additions and 4 deletions

View File

@ -23,12 +23,19 @@
*/
package org.hibernate.envers.query.criteria;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.envers.configuration.AuditConfiguration;
import org.hibernate.envers.entities.RelationDescription;
import org.hibernate.envers.entities.RelationType;
import org.hibernate.envers.exception.AuditException;
import org.hibernate.envers.query.property.PropertyNameGetter;
import org.hibernate.envers.reader.AuditReaderImplementor;
import org.hibernate.type.EmbeddedComponentType;
import org.hibernate.type.Type;
/**
* @author Adam Warski (adam at warski dot org)
@ -73,14 +80,46 @@ public class CriteriaTools {
* @param versionsReader Versions reader.
* @param entityName Original entity name (not audited).
* @param propertyName Property name or placeholder.
* @return Path to property. Handles identifier placeholder used by {@link AuditId}.
*
* @return Path to property. Handles identifier placeholder used by {@link org.hibernate.envers.query.criteria.AuditId}.
*/
public static String determinePropertyName(AuditConfiguration auditCfg, AuditReaderImplementor versionsReader,
String entityName, String propertyName) {
public static String determinePropertyName(
AuditConfiguration auditCfg, AuditReaderImplementor versionsReader,
String entityName, String propertyName) {
final SessionFactoryImplementor sessionFactory = versionsReader.getSessionImplementor().getFactory();
if ( AuditId.IDENTIFIER_PLACEHOLDER.equals( propertyName ) ) {
final String identifierPropertyName = versionsReader.getSessionImplementor().getFactory().getEntityPersister( entityName ).getIdentifierPropertyName();
final String identifierPropertyName = sessionFactory.getEntityPersister( entityName ).getIdentifierPropertyName();
propertyName = auditCfg.getAuditEntCfg().getOriginalIdPropName() + "." + identifierPropertyName;
}
else {
final List<String> identifierPropertyNames = identifierPropertyNames( sessionFactory, entityName );
if ( identifierPropertyNames.contains( propertyName ) ) {
propertyName = auditCfg.getAuditEntCfg().getOriginalIdPropName() + "." + propertyName;
}
}
return propertyName;
}
/**
* @param sessionFactory Session factory.
* @param entityName Entity name.
*
* @return List of property names representing entity identifier.
*/
private static List<String> identifierPropertyNames(SessionFactoryImplementor sessionFactory, String entityName) {
final String identifierPropertyName = sessionFactory.getEntityPersister( entityName ).getIdentifierPropertyName();
if ( identifierPropertyName != null ) {
// Single id.
return Arrays.asList( identifierPropertyName );
}
final Type identifierType = sessionFactory.getEntityPersister( entityName ).getIdentifierType();
if ( identifierType instanceof EmbeddedComponentType ) {
// Multiple ids.
final EmbeddedComponentType embeddedComponentType = (EmbeddedComponentType) identifierType;
return Arrays.asList( embeddedComponentType.getPropertyNames() );
}
return Collections.EMPTY_LIST;
}
}

View File

@ -38,6 +38,10 @@ import org.hibernate.envers.query.AuditEntity;
import org.hibernate.envers.test.BaseEnversJPAFunctionalTestCase;
import org.hibernate.envers.test.Priority;
import org.hibernate.envers.test.entities.StrIntTestEntity;
import org.hibernate.envers.test.entities.ids.EmbId;
import org.hibernate.envers.test.entities.ids.EmbIdTestEntity;
import org.hibernate.envers.test.entities.ids.MulId;
import org.hibernate.envers.test.entities.ids.MulIdTestEntity;
import org.hibernate.envers.test.tools.TestTools;
import org.hibernate.testing.TestForIssue;
@ -50,9 +54,13 @@ public class SimpleQuery extends BaseEnversJPAFunctionalTestCase {
private Integer id1;
private Integer id2;
private Integer id3;
private MulId mulId1;
private EmbId embId1;
public void configure(Ejb3Configuration cfg) {
cfg.addAnnotatedClass(StrIntTestEntity.class);
cfg.addAnnotatedClass(MulIdTestEntity.class);
cfg.addAnnotatedClass(EmbIdTestEntity.class);
}
@Test
@ -79,6 +87,12 @@ public class SimpleQuery extends BaseEnversJPAFunctionalTestCase {
// Revision 2
em.getTransaction().begin();
mulId1 = new MulId( 1, 2 );
em.persist( new MulIdTestEntity( mulId1.getId1(), mulId1.getId2(), "data" ) );
embId1 = new EmbId( 3, 4 );
em.persist( new EmbIdTestEntity( embId1, "something" ) );
site1 = em.find(StrIntTestEntity.class, id1);
site2 = em.find(StrIntTestEntity.class, id2);
@ -343,4 +357,39 @@ public class SimpleQuery extends BaseEnversJPAFunctionalTestCase {
Assert.assertTrue( ( number >= 0 && number <= 5 ) || ( number >= 20 && number <= 100 ) );
}
}
@Test
@TestForIssue(jiraKey = "HHH-8567")
public void testIdPropertyRestriction() {
StrIntTestEntity ver2 = (StrIntTestEntity) getAuditReader().createQuery()
.forEntitiesAtRevision( StrIntTestEntity.class, 2 )
.add( AuditEntity.property( "id" ).eq( id2 ) )
.getSingleResult();
Assert.assertEquals( new StrIntTestEntity( "a", 20, id2 ), ver2 );
}
@Test
@TestForIssue(jiraKey = "HHH-8567")
public void testMultipleIdPropertyRestriction() {
MulIdTestEntity ver2 = (MulIdTestEntity) getAuditReader().createQuery()
.forEntitiesAtRevision( MulIdTestEntity.class, 2 )
.add( AuditEntity.property( "id1" ).eq( mulId1.getId1() ) )
.add( AuditEntity.property( "id2" ).eq( mulId1.getId2() ) )
.getSingleResult();
Assert.assertEquals( new MulIdTestEntity( mulId1.getId1(), mulId1.getId2(), "data" ), ver2 );
}
@Test
@TestForIssue(jiraKey = "HHH-8567")
public void testEmbeddedIdPropertyRestriction() {
EmbIdTestEntity ver2 = (EmbIdTestEntity) getAuditReader().createQuery()
.forEntitiesAtRevision( EmbIdTestEntity.class, 2 )
.add( AuditEntity.property( "id.x" ).eq( embId1.getX() ) )
.add( AuditEntity.property( "id.y" ).eq( embId1.getY() ) )
.getSingleResult();
Assert.assertEquals( new EmbIdTestEntity( embId1, "something" ), ver2 );
}
}