From 13c9fd4f9d177fb7d022c72d674f1a23b909c443 Mon Sep 17 00:00:00 2001 From: Lukasz Antoniak Date: Sun, 12 Jun 2011 13:55:00 +0200 Subject: [PATCH 1/2] HHH-5580 - Persisting entity name by default --- .../main/docbook/devguide/en-US/Envers.xml | 56 +++++------ .../org/hibernate/envers/AuditReader.java | 41 +++++---- ...rackingModifiedEntitiesRevisionEntity.java | 55 +++++++++++ ...ltTrackingModifiedTypesRevisionEntity.java | 55 ----------- ...ityTypes.java => ModifiedEntityNames.java} | 4 +- .../configuration/AuditConfiguration.java | 10 +- .../configuration/GlobalConfiguration.java | 2 +- .../RevisionInfoConfiguration.java | 92 ++++++++++--------- .../envers/reader/AuditReaderImpl.java | 38 +++++--- ...ModifiedEntitiesRevisionInfoGenerator.java | 47 ++++++++++ ...ingModifiedTypesRevisionInfoGenerator.java | 47 ---------- .../ModifiedEntityNamesReader.java | 27 ++++++ .../ModifiedEntityTypesReader.java | 41 --------- .../synchronization/EntityChangeNotifier.java | 12 +-- .../org/hibernate/envers/tools/Tools.java | 9 ++ .../AnnotatedTrackingRevisionEntity.java | 24 ++--- .../ExtendedRevisionEntity.java | 15 ++- .../ExtendedRevisionListener.java | 2 +- .../AnnotatedTrackingEntitiesTest.java | 4 +- .../CustomTrackingEntitiesTest.java | 12 +-- .../DefaultTrackingEntitiesTest.java | 18 +++- .../EntityNamesTest.java | 10 +- .../ExtendedRevisionEntityTest.java | 10 +- 23 files changed, 319 insertions(+), 312 deletions(-) create mode 100644 hibernate-envers/src/main/java/org/hibernate/envers/DefaultTrackingModifiedEntitiesRevisionEntity.java delete mode 100644 hibernate-envers/src/main/java/org/hibernate/envers/DefaultTrackingModifiedTypesRevisionEntity.java rename hibernate-envers/src/main/java/org/hibernate/envers/{ModifiedEntityTypes.java => ModifiedEntityNames.java} (75%) create mode 100644 hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/DefaultTrackingModifiedEntitiesRevisionInfoGenerator.java delete mode 100644 hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/DefaultTrackingModifiedTypesRevisionInfoGenerator.java create mode 100644 hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/ModifiedEntityNamesReader.java delete mode 100644 hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/ModifiedEntityTypesReader.java diff --git a/documentation/src/main/docbook/devguide/en-US/Envers.xml b/documentation/src/main/docbook/devguide/en-US/Envers.xml index c6fbe4aa71..0488ee2892 100644 --- a/documentation/src/main/docbook/devguide/en-US/Envers.xml +++ b/documentation/src/main/docbook/devguide/en-US/Envers.xml @@ -252,12 +252,10 @@ Should entity types, that have been modified during each revision, be tracked. The default - implementation creates REVCHANGES table that stores fully qualified names - of Java classes modified in a specified revision. Single record encapsulates the revision - identifier (foreign key to REVINFO table) and a string value. This - feature shall be used when entity name can be clearly identified by Java class type. Otherwise - extend org.hibernate.envers.EntityTrackingRevisionListener - interface. For more information refer to + implementation creates REVCHANGES table that stores entity names + of modified persistent objects. Single record encapsulates the revision identifier + (foreign key to REVINFO table) and a string value. For more + information refer to and . @@ -476,40 +474,38 @@ public class ExampleListener implements RevisionListener {
- Tracking entity classes modified in revision + Tracking entity names modified during revisions By default entity types that have been changed in each revision are not being tracked. This implies the necessity to query all tables storing audited data in order to retrieve changes made during specified revision. Envers provides a simple mechanism that creates REVCHANGES - table which stores fully qualified names of Java classes modified in each revision. - Single record encapsulates the revision identifier (foreign key to REVINFO table) - and a string value. Note that this mechanism shall be used when entity name can be clearly identified - by Java class type. Otherwise extend org.hibernate.envers.EntityTrackingRevisionListener - interface (described further). + table which stores entity names of modified persistent objects. Single record encapsulates the revision + identifier (foreign key to REVINFO table) and a string value. - Tracking of modified entity types can be enabled in three different ways: + Tracking of modified entity names can be enabled in three different ways: Set org.hibernate.envers.track_entities_changed_in_revision parameter to true. In this case - org.hibernate.envers.DefaultTrackingModifiedTypesRevisionEntity will + org.hibernate.envers.DefaultTrackingModifiedEntitiesRevisionEntity will be implicitly used as the revision log entity. Create a custom revision entity that extends - org.hibernate.envers.DefaultTrackingModifiedTypesRevisionEntity class. + org.hibernate.envers.DefaultTrackingModifiedEntitiesRevisionEntity class. Mark an appropriate field of a custom revision entity with - @org.hibernate.envers.ModifiedEntityTypes annotation. The property is + @org.hibernate.envers.ModifiedEntityNames annotation. The property is required to be of ]]> type. modifiedEntityTypes; + @Column(name = "ENTITYNAME") + @ModifiedEntityNames + private Set modifiedEntityNames; ... }]]> - Users, that have chosen one of the approaches listed above, can retrieve all entities modified in + Users, that have chosen one of the approaches listed above, can retrieve all entities modified in a specified revision by utilizing API described in . @@ -545,11 +541,14 @@ public class AnnotatedTrackingRevisionEntity { CustomEntityTrackingRevisionListener.java modifiedEntityTypes = new HashSet(); + private Set modifiedEntityTypes = + new HashSet(); public void addModifiedEntityType(String entityClassName) { modifiedEntityTypes.add(new ModifiedEntityTypeEntity(this, entityClassName)); @@ -797,9 +797,9 @@ query.add(AuditEntity.relatedId("address").eq(relatedEntityId));]]> Querying for entities modified in a given revision - The basic query allows retrieving entity types changed in a specified revision: + The basic query allows retrieving entity names and corresponding Java classes changed in a specified revision: - modifiedEntityTypes = getAuditReader() + > modifiedEntityTypes = getAuditReader() .findEntityTypesChangedInRevision(revisionNumber);]]> Other queries (accessible from org.hibernate.envers.AuditReader): @@ -826,7 +826,7 @@ query.add(AuditEntity.relatedId("address").eq(relatedEntityId));]]> Note that methods described above can be legally used only when default mechanism of - tracking changed entity types is enabled (see ). + tracking changed entity names is enabled (see ).
diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/AuditReader.java b/hibernate-envers/src/main/java/org/hibernate/envers/AuditReader.java index 5929882e5a..204feb1060 100644 --- a/hibernate-envers/src/main/java/org/hibernate/envers/AuditReader.java +++ b/hibernate-envers/src/main/java/org/hibernate/envers/AuditReader.java @@ -28,6 +28,7 @@ import org.hibernate.envers.exception.AuditException; import org.hibernate.envers.exception.NotAuditedException; import org.hibernate.envers.exception.RevisionDoesNotExistException; import org.hibernate.envers.query.AuditQueryCreator; +import org.hibernate.envers.tools.Pair; import java.util.Date; import java.util.List; @@ -222,9 +223,9 @@ public interface AuditReader { *
  • org.hibernate.envers.track_entities_changed_in_revision * parameter is set to true.
  • *
  • Custom revision entity (annotated with {@link RevisionEntity}) - * extends {@link DefaultTrackingModifiedTypesRevisionEntity} base class.
  • + * extends {@link DefaultTrackingModifiedEntitiesRevisionEntity} base class. *
  • Custom revision entity (annotated with {@link RevisionEntity}) encapsulates a field - * marked with {@link ModifiedEntityTypes} interface.
  • + * marked with {@link ModifiedEntityNames} interface. * */ List findEntitiesChangedInRevision(Number revision) @@ -237,15 +238,15 @@ public interface AuditReader { * @param revisionType Type of modification. * @return Snapshots of all audited entities changed in a given revision and filtered by modification type. * @throws IllegalStateException If the associated entity manager is closed. - * @throws IllegalArgumentException If a revision number is null, less or equal to 0. + * @throws IllegalArgumentException If a revision number is {@code null}, less or equal to 0. * @throws AuditException If none of the following conditions is satisfied: * */ List findEntitiesChangedInRevision(Number revision, RevisionType revisionType) @@ -261,36 +262,36 @@ public interface AuditReader { * @param revision Revision number. * @return Map containing lists of entity snapshots grouped by modification operation (e.g. addition, update, removal). * @throws IllegalStateException If the associated entity manager is closed. - * @throws IllegalArgumentException If a revision number is null, less or equal to 0. + * @throws IllegalArgumentException If a revision number is {@code null}, less or equal to 0. * @throws AuditException If none of the following conditions is satisfied: *
      - *
    • org.hibernate.envers.track_entities_changed_in_revision - * parameter is set to true.
    • + *
    • {@code org.hibernate.envers.track_entities_changed_in_revision} + * parameter is set to {@code true}.
    • *
    • Custom revision entity (annotated with {@link RevisionEntity}) - * extends {@link DefaultTrackingModifiedTypesRevisionEntity} base class.
    • + * extends {@link DefaultTrackingModifiedEntitiesRevisionEntity} base class. *
    • Custom revision entity (annotated with {@link RevisionEntity}) encapsulates a field - * marked with {@link ModifiedEntityTypes} interface.
    • + * marked with {@link ModifiedEntityNames} interface. *
    */ Map> findEntitiesChangedInRevisionGroupByRevisionType(Number revision) throws IllegalStateException, IllegalArgumentException, AuditException; /** - * Returns set of entity classes modified in a given revision. + * Returns set of entity names and corresponding Java classes modified in a given revision. * @param revision Revision number. - * @return Set of classes modified in a given revision. + * @return Set of entity names and corresponding Java classes modified in a given revision. * @throws IllegalStateException If the associated entity manager is closed. - * @throws IllegalArgumentException If a revision number is null, less or equal to 0. + * @throws IllegalArgumentException If a revision number is {@code null}, less or equal to 0. * @throws AuditException If none of the following conditions is satisfied: *
      - *
    • org.hibernate.envers.track_entities_changed_in_revision - * parameter is set to true.
    • + *
    • {@code org.hibernate.envers.track_entities_changed_in_revision} + * parameter is set to {@code true}.
    • *
    • Custom revision entity (annotated with {@link RevisionEntity}) - * extends {@link DefaultTrackingModifiedTypesRevisionEntity} base class.
    • + * extends {@link DefaultTrackingModifiedEntitiesRevisionEntity} base class. *
    • Custom revision entity (annotated with {@link RevisionEntity}) encapsulates a field - * marked with {@link ModifiedEntityTypes} interface.
    • + * marked with {@link ModifiedEntityNames} interface. *
    */ - Set findEntityTypesChangedInRevision(Number revision) + Set> findEntityTypesChangedInRevision(Number revision) throws IllegalStateException, IllegalArgumentException, AuditException; } diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/DefaultTrackingModifiedEntitiesRevisionEntity.java b/hibernate-envers/src/main/java/org/hibernate/envers/DefaultTrackingModifiedEntitiesRevisionEntity.java new file mode 100644 index 0000000000..e70f3d778e --- /dev/null +++ b/hibernate-envers/src/main/java/org/hibernate/envers/DefaultTrackingModifiedEntitiesRevisionEntity.java @@ -0,0 +1,55 @@ +package org.hibernate.envers; + +import org.hibernate.annotations.Fetch; +import org.hibernate.annotations.FetchMode; + +import javax.persistence.*; +import java.util.HashSet; +import java.util.Set; + +/** + * Extension of standard {@link DefaultRevisionEntity} that allows tracking entity names changed in each revision. + * This revision entity is implicitly used when {@code org.hibernate.envers.track_entities_changed_in_revision} + * parameter is set to {@code true}. + * @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com) + */ +@MappedSuperclass +public class DefaultTrackingModifiedEntitiesRevisionEntity extends DefaultRevisionEntity { + @ElementCollection(fetch = FetchType.EAGER) + @JoinTable(name = "REVCHANGES", joinColumns = @JoinColumn(name = "REV")) + @Column(name = "ENTITYNAME") + @Fetch(FetchMode.JOIN) + @ModifiedEntityNames + private Set modifiedEntityNames = new HashSet(); + + public Set getModifiedEntityNames() { + return modifiedEntityNames; + } + + public void setModifiedEntityNames(Set modifiedEntityNames) { + this.modifiedEntityNames = modifiedEntityNames; + } + + public boolean equals(Object o) { + if (this == o) return true; + if (!(o instanceof DefaultTrackingModifiedEntitiesRevisionEntity)) return false; + if (!super.equals(o)) return false; + + DefaultTrackingModifiedEntitiesRevisionEntity that = (DefaultTrackingModifiedEntitiesRevisionEntity) o; + + if (modifiedEntityNames != null ? !modifiedEntityNames.equals(that.modifiedEntityNames) + : that.modifiedEntityNames != null) return false; + + return true; + } + + public int hashCode() { + int result = super.hashCode(); + result = 31 * result + (modifiedEntityNames != null ? modifiedEntityNames.hashCode() : 0); + return result; + } + + public String toString() { + return "DefaultTrackingModifiedEntitiesRevisionEntity(" + super.toString() + ", modifiedEntityNames = " + modifiedEntityNames + ")"; + } +} diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/DefaultTrackingModifiedTypesRevisionEntity.java b/hibernate-envers/src/main/java/org/hibernate/envers/DefaultTrackingModifiedTypesRevisionEntity.java deleted file mode 100644 index 83b2706f14..0000000000 --- a/hibernate-envers/src/main/java/org/hibernate/envers/DefaultTrackingModifiedTypesRevisionEntity.java +++ /dev/null @@ -1,55 +0,0 @@ -package org.hibernate.envers; - -import org.hibernate.annotations.Fetch; -import org.hibernate.annotations.FetchMode; - -import javax.persistence.*; -import java.util.HashSet; -import java.util.Set; - -/** - * Extension of {@link DefaultRevisionEntity} that allows tracking entity types changed in each revision. This revision - * entity is implicitly used when org.hibernate.envers.track_entities_changed_in_revision parameter - * is set to true. - * @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com) - */ -@MappedSuperclass -public class DefaultTrackingModifiedTypesRevisionEntity extends DefaultRevisionEntity { - @ElementCollection(fetch = FetchType.EAGER) - @JoinTable(name = "REVCHANGES", joinColumns = @JoinColumn(name = "REV")) - @Column(name = "ENTITYTYPE") - @Fetch(FetchMode.JOIN) - @ModifiedEntityTypes - private Set modifiedEntityTypes = new HashSet(); - - public Set getModifiedEntityTypes() { - return modifiedEntityTypes; - } - - public void setModifiedEntityTypes(Set modifiedEntityTypes) { - this.modifiedEntityTypes = modifiedEntityTypes; - } - - public boolean equals(Object o) { - if (this == o) return true; - if (!(o instanceof DefaultTrackingModifiedTypesRevisionEntity)) return false; - if (!super.equals(o)) return false; - - DefaultTrackingModifiedTypesRevisionEntity that = (DefaultTrackingModifiedTypesRevisionEntity) o; - - if (modifiedEntityTypes != null ? !modifiedEntityTypes.equals(that.modifiedEntityTypes) - : that.modifiedEntityTypes != null) return false; - - return true; - } - - public int hashCode() { - int result = super.hashCode(); - result = 31 * result + (modifiedEntityTypes != null ? modifiedEntityTypes.hashCode() : 0); - return result; - } - - public String toString() { - return "DefaultTrackingModifiedTypesRevisionEntity(" + super.toString() + ", modifiedEntityTypes = " + modifiedEntityTypes + ")"; - } -} diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/ModifiedEntityTypes.java b/hibernate-envers/src/main/java/org/hibernate/envers/ModifiedEntityNames.java similarity index 75% rename from hibernate-envers/src/main/java/org/hibernate/envers/ModifiedEntityTypes.java rename to hibernate-envers/src/main/java/org/hibernate/envers/ModifiedEntityNames.java index 0ecac71945..1bd81775dd 100644 --- a/hibernate-envers/src/main/java/org/hibernate/envers/ModifiedEntityTypes.java +++ b/hibernate-envers/src/main/java/org/hibernate/envers/ModifiedEntityNames.java @@ -6,11 +6,11 @@ import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; /** - * Marks a property which holds entity class names that have been modified during each revision. + * Marks a property which holds entity names that have been modified during each revision. * This annotation expects field of {@literal Set} type. * @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com) */ @Retention(RetentionPolicy.RUNTIME) @Target({ElementType.METHOD, ElementType.FIELD}) -public @interface ModifiedEntityTypes { +public @interface ModifiedEntityNames { } diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/configuration/AuditConfiguration.java b/hibernate-envers/src/main/java/org/hibernate/envers/configuration/AuditConfiguration.java index 00b1d20b8c..ad8abf4e7e 100644 --- a/hibernate-envers/src/main/java/org/hibernate/envers/configuration/AuditConfiguration.java +++ b/hibernate-envers/src/main/java/org/hibernate/envers/configuration/AuditConfiguration.java @@ -30,7 +30,7 @@ import org.hibernate.annotations.common.reflection.ReflectionManager; import org.hibernate.cfg.Configuration; import org.hibernate.envers.entities.EntitiesConfigurations; import org.hibernate.envers.entities.PropertyData; -import org.hibernate.envers.revisioninfo.ModifiedEntityTypesReader; +import org.hibernate.envers.revisioninfo.ModifiedEntityNamesReader; import org.hibernate.envers.revisioninfo.RevisionInfoNumberReader; import org.hibernate.envers.revisioninfo.RevisionInfoQueryCreator; import org.hibernate.envers.strategy.AuditStrategy; @@ -51,7 +51,7 @@ public class AuditConfiguration { private final EntitiesConfigurations entCfg; private final RevisionInfoQueryCreator revisionInfoQueryCreator; private final RevisionInfoNumberReader revisionInfoNumberReader; - private final ModifiedEntityTypesReader modifiedEntityTypesReader; + private final ModifiedEntityNamesReader modifiedEntityNamesReader; public AuditEntitiesConfiguration getAuditEntCfg() { return auditEntCfg; @@ -77,8 +77,8 @@ public class AuditConfiguration { return revisionInfoNumberReader; } - public ModifiedEntityTypesReader getModifiedEntityTypesReader() { - return modifiedEntityTypesReader; + public ModifiedEntityNamesReader getModifiedEntityNamesReader() { + return modifiedEntityNamesReader; } public AuditStrategy getAuditStrategy() { @@ -96,7 +96,7 @@ public class AuditConfiguration { auditProcessManager = new AuditProcessManager(revInfoCfgResult.getRevisionInfoGenerator()); revisionInfoQueryCreator = revInfoCfgResult.getRevisionInfoQueryCreator(); revisionInfoNumberReader = revInfoCfgResult.getRevisionInfoNumberReader(); - modifiedEntityTypesReader = revInfoCfgResult.getModifiedEntityTypesReader(); + modifiedEntityNamesReader = revInfoCfgResult.getModifiedEntityNamesReader(); auditStrategy = initializeAuditStrategy(revInfoCfgResult.getRevisionInfoClass(), revInfoCfgResult.getRevisionInfoTimestampData()); entCfg = new EntitiesConfigurator().configure(cfg, reflectionManager, globalCfg, auditEntCfg, auditStrategy, diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/configuration/GlobalConfiguration.java b/hibernate-envers/src/main/java/org/hibernate/envers/configuration/GlobalConfiguration.java index ca594c1a00..6a54186b56 100644 --- a/hibernate-envers/src/main/java/org/hibernate/envers/configuration/GlobalConfiguration.java +++ b/hibernate-envers/src/main/java/org/hibernate/envers/configuration/GlobalConfiguration.java @@ -46,7 +46,7 @@ public class GlobalConfiguration { // The default name of the catalog of the audit tables. private final String defaultCatalogName; - // Should Envers track (persist) entity types that have been changed during each revision. + // Should Envers track (persist) entity names that have been changed during each revision. private boolean trackEntitiesChangedInRevisionEnabled; /* diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/configuration/RevisionInfoConfiguration.java b/hibernate-envers/src/main/java/org/hibernate/envers/configuration/RevisionInfoConfiguration.java index 046c1dfe3e..a25b8f71f6 100644 --- a/hibernate-envers/src/main/java/org/hibernate/envers/configuration/RevisionInfoConfiguration.java +++ b/hibernate-envers/src/main/java/org/hibernate/envers/configuration/RevisionInfoConfiguration.java @@ -36,8 +36,8 @@ import org.hibernate.annotations.common.reflection.XProperty; import org.hibernate.cfg.Configuration; import org.hibernate.envers.Audited; import org.hibernate.envers.DefaultRevisionEntity; -import org.hibernate.envers.DefaultTrackingModifiedTypesRevisionEntity; -import org.hibernate.envers.ModifiedEntityTypes; +import org.hibernate.envers.DefaultTrackingModifiedEntitiesRevisionEntity; +import org.hibernate.envers.ModifiedEntityNames; import org.hibernate.envers.RevisionEntity; import org.hibernate.envers.RevisionListener; import org.hibernate.envers.RevisionNumber; @@ -46,8 +46,8 @@ import org.hibernate.envers.configuration.metadata.AuditTableData; import org.hibernate.envers.configuration.metadata.MetadataTools; import org.hibernate.envers.entities.PropertyData; import org.hibernate.envers.revisioninfo.DefaultRevisionInfoGenerator; -import org.hibernate.envers.revisioninfo.DefaultTrackingModifiedTypesRevisionInfoGenerator; -import org.hibernate.envers.revisioninfo.ModifiedEntityTypesReader; +import org.hibernate.envers.revisioninfo.DefaultTrackingModifiedEntitiesRevisionInfoGenerator; +import org.hibernate.envers.revisioninfo.ModifiedEntityNamesReader; import org.hibernate.envers.revisioninfo.RevisionInfoGenerator; import org.hibernate.envers.revisioninfo.RevisionInfoNumberReader; import org.hibernate.envers.revisioninfo.RevisionInfoQueryCreator; @@ -64,7 +64,7 @@ public class RevisionInfoConfiguration { private String revisionInfoEntityName; private PropertyData revisionInfoIdData; private PropertyData revisionInfoTimestampData; - private PropertyData modifiedEntityTypesData; + private PropertyData modifiedEntityNamesData; private Type revisionInfoTimestampType; private GlobalConfiguration globalCfg; @@ -76,7 +76,7 @@ public class RevisionInfoConfiguration { revisionInfoEntityName = "org.hibernate.envers.DefaultRevisionEntity"; revisionInfoIdData = new PropertyData("id", "id", "field", null); revisionInfoTimestampData = new PropertyData("timestamp", "timestamp", "field", null); - modifiedEntityTypesData = new PropertyData("modifiedEntityTypes", "modifiedEntityTypes", "field", null); + modifiedEntityNamesData = new PropertyData("modifiedEntityNames", "modifiedEntityNames", "field", null); revisionInfoTimestampType = new LongType(); revisionPropType = "integer"; @@ -99,7 +99,9 @@ public class RevisionInfoConfiguration { MetadataTools.addColumn(timestampProperty, "REVTSTMP", null, 0, 0, null, null, null, false); if (globalCfg.isTrackEntitiesChangedInRevisionEnabled()) { - generateEntityTypesTrackingTableMapping(class_mapping, "modifiedEntityTypes", "REVCHANGES", "REV", "ENTITYTYPE", "string"); + generateEntityNamesTrackingTableMapping(class_mapping, "modifiedEntityNames", + globalCfg.getDefaultSchemaName(), globalCfg.getDefaultCatalogName(), + "REVCHANGES", "REV", "ENTITYNAME", "string"); } return document; @@ -108,20 +110,24 @@ public class RevisionInfoConfiguration { /** * Generates mapping that represents a set of primitive types.
    * - * <set name="propertyName" table="joinTableName" cascade="persist, delete" lazy="false" fetch="join">
    + * <set name="propertyName" table="joinTableName" schema="joinTableSchema" catalog="joinTableCatalog" + *      cascade="persist, delete" lazy="false" fetch="join">
    *    <key column="joinTablePrimaryKeyColumnName" />
    *    <element type="joinTableValueColumnType">
    *       <column name="joinTableValueColumnName" />
    *    </element>
    * </set> *
    - */ - private void generateEntityTypesTrackingTableMapping(Element class_mapping, String propertyName, - String joinTableName, String joinTablePrimaryKeyColumnName, - String joinTableValueColumnName, String joinTableValueColumnType) { + */ + private void generateEntityNamesTrackingTableMapping(Element class_mapping, String propertyName, + String joinTableSchema, String joinTableCatalog, String joinTableName, + String joinTablePrimaryKeyColumnName, String joinTableValueColumnName, + String joinTableValueColumnType) { Element set = class_mapping.addElement("set"); set.addAttribute("name", propertyName); set.addAttribute("table", joinTableName); + set.addAttribute("schema", joinTableSchema); + set.addAttribute("catalog", joinTableCatalog); set.addAttribute("cascade", "persist, delete"); set.addAttribute("fetch", "join"); set.addAttribute("lazy", "false"); @@ -149,11 +155,11 @@ public class RevisionInfoConfiguration { private void searchForRevisionInfoCfgInProperties(XClass clazz, ReflectionManager reflectionManager, MutableBoolean revisionNumberFound, MutableBoolean revisionTimestampFound, - MutableBoolean modifiedEntityTypesFound, String accessType) { + MutableBoolean modifiedEntityNamesFound, String accessType) { for (XProperty property : clazz.getDeclaredProperties(accessType)) { RevisionNumber revisionNumber = property.getAnnotation(RevisionNumber.class); RevisionTimestamp revisionTimestamp = property.getAnnotation(RevisionTimestamp.class); - ModifiedEntityTypes modifiedEntityTypes = property.getAnnotation(ModifiedEntityTypes.class); + ModifiedEntityNames modifiedEntityNames = property.getAnnotation(ModifiedEntityNames.class); if (revisionNumber != null) { if (revisionNumberFound.isSet()) { @@ -204,17 +210,17 @@ public class RevisionInfoConfiguration { } } - if (modifiedEntityTypes != null) { - if (modifiedEntityTypesFound.isSet()) { - throw new MappingException("Only one property may be annotated with @ModifiedEntityTypes!"); + if (modifiedEntityNames != null) { + if (modifiedEntityNamesFound.isSet()) { + throw new MappingException("Only one property may be annotated with @ModifiedEntityNames!"); } - XClass modifiedEntityTypesClass = property.getType(); - if (reflectionManager.equals(modifiedEntityTypesClass, Set.class) && + XClass modifiedEntityNamesClass = property.getType(); + if (reflectionManager.equals(modifiedEntityNamesClass, Set.class) && reflectionManager.equals(property.getElementClass(), String.class)) { - modifiedEntityTypesData = new PropertyData(property.getName(), property.getName(), accessType, null); - modifiedEntityTypesFound.set(); + modifiedEntityNamesData = new PropertyData(property.getName(), property.getName(), accessType, null); + modifiedEntityNamesFound.set(); } else { - throw new MappingException("The field annotated with @ModifiedEntityTypes must be of Set type."); + throw new MappingException("The field annotated with @ModifiedEntityNames must be of Set type."); } } } @@ -222,16 +228,16 @@ public class RevisionInfoConfiguration { private void searchForRevisionInfoCfg(XClass clazz, ReflectionManager reflectionManager, MutableBoolean revisionNumberFound, MutableBoolean revisionTimestampFound, - MutableBoolean modifiedEntityTypesFound) { + MutableBoolean modifiedEntityNamesFound) { XClass superclazz = clazz.getSuperclass(); if (!"java.lang.Object".equals(superclazz.getName())) { - searchForRevisionInfoCfg(superclazz, reflectionManager, revisionNumberFound, revisionTimestampFound, modifiedEntityTypesFound); + searchForRevisionInfoCfg(superclazz, reflectionManager, revisionNumberFound, revisionTimestampFound, modifiedEntityNamesFound); } searchForRevisionInfoCfgInProperties(clazz, reflectionManager, revisionNumberFound, revisionTimestampFound, - modifiedEntityTypesFound, "field"); + modifiedEntityNamesFound, "field"); searchForRevisionInfoCfgInProperties(clazz, reflectionManager, revisionNumberFound, revisionTimestampFound, - modifiedEntityTypesFound, "property"); + modifiedEntityNamesFound, "property"); } public RevisionInfoConfigurationResult configure(Configuration cfg, ReflectionManager reflectionManager) { @@ -265,9 +271,9 @@ public class RevisionInfoConfiguration { MutableBoolean revisionNumberFound = new MutableBoolean(); MutableBoolean revisionTimestampFound = new MutableBoolean(); - MutableBoolean modifiedEntityTypesFound = new MutableBoolean(); + MutableBoolean modifiedEntityNamesFound = new MutableBoolean(); - searchForRevisionInfoCfg(clazz, reflectionManager, revisionNumberFound, revisionTimestampFound, modifiedEntityTypesFound); + searchForRevisionInfoCfg(clazz, reflectionManager, revisionNumberFound, revisionTimestampFound, modifiedEntityNamesFound); if (!revisionNumberFound.isSet()) { throw new MappingException("An entity annotated with @RevisionEntity must have a field annotated " + @@ -284,13 +290,13 @@ public class RevisionInfoConfiguration { revisionInfoClass = pc.getMappedClass(); revisionInfoTimestampType = pc.getProperty(revisionInfoTimestampData.getName()).getType(); if (globalCfg.isTrackEntitiesChangedInRevisionEnabled() || - DefaultTrackingModifiedTypesRevisionEntity.class.isAssignableFrom(revisionInfoClass) || - modifiedEntityTypesFound.isSet()) { + DefaultTrackingModifiedEntitiesRevisionEntity.class.isAssignableFrom(revisionInfoClass) || + modifiedEntityNamesFound.isSet()) { // If tracking modified entities parameter is enabled, custom revision info entity is a subtype - // of DefaultTrackingModifiedTypesRevisionEntity class, or @ModifiedEntityTypes annotation is used. - revisionInfoGenerator = new DefaultTrackingModifiedTypesRevisionInfoGenerator(revisionInfoEntityName, + // of DefaultTrackingModifiedEntitiesRevisionEntity class, or @ModifiedEntityNames annotation is used. + revisionInfoGenerator = new DefaultTrackingModifiedEntitiesRevisionInfoGenerator(revisionInfoEntityName, revisionInfoClass, revisionEntity.value(), revisionInfoTimestampData, isTimestampAsDate(), - modifiedEntityTypesData); + modifiedEntityNamesData); globalCfg.setTrackEntitiesChangedInRevisionEnabled(true); } else { revisionInfoGenerator = new DefaultRevisionInfoGenerator(revisionInfoEntityName, revisionInfoClass, @@ -304,10 +310,10 @@ public class RevisionInfoConfiguration { if (revisionInfoGenerator == null) { if (globalCfg.isTrackEntitiesChangedInRevisionEnabled()) { - revisionInfoClass = DefaultTrackingModifiedTypesRevisionEntity.class; - revisionInfoEntityName = DefaultTrackingModifiedTypesRevisionEntity.class.getName(); - revisionInfoGenerator = new DefaultTrackingModifiedTypesRevisionInfoGenerator(revisionInfoEntityName, revisionInfoClass, - RevisionListener.class, revisionInfoTimestampData, isTimestampAsDate(), modifiedEntityTypesData); + revisionInfoClass = DefaultTrackingModifiedEntitiesRevisionEntity.class; + revisionInfoEntityName = DefaultTrackingModifiedEntitiesRevisionEntity.class.getName(); + revisionInfoGenerator = new DefaultTrackingModifiedEntitiesRevisionInfoGenerator(revisionInfoEntityName, revisionInfoClass, + RevisionListener.class, revisionInfoTimestampData, isTimestampAsDate(), modifiedEntityNamesData); } else { revisionInfoClass = DefaultRevisionEntity.class; revisionInfoGenerator = new DefaultRevisionInfoGenerator(revisionInfoEntityName, revisionInfoClass, @@ -322,7 +328,7 @@ public class RevisionInfoConfiguration { revisionInfoTimestampData.getName(), isTimestampAsDate()), generateRevisionInfoRelationMapping(), new RevisionInfoNumberReader(revisionInfoClass, revisionInfoIdData), - globalCfg.isTrackEntitiesChangedInRevisionEnabled() ? new ModifiedEntityTypesReader(revisionInfoClass, modifiedEntityTypesData) + globalCfg.isTrackEntitiesChangedInRevisionEnabled() ? new ModifiedEntityNamesReader(revisionInfoClass, modifiedEntityNamesData) : null, revisionInfoEntityName, revisionInfoClass, revisionInfoTimestampData); } @@ -339,7 +345,7 @@ class RevisionInfoConfigurationResult { private final RevisionInfoQueryCreator revisionInfoQueryCreator; private final Element revisionInfoRelationMapping; private final RevisionInfoNumberReader revisionInfoNumberReader; - private final ModifiedEntityTypesReader modifiedEntityTypesReader; + private final ModifiedEntityNamesReader modifiedEntityNamesReader; private final String revisionInfoEntityName; private final Class revisionInfoClass; private final PropertyData revisionInfoTimestampData; @@ -347,14 +353,14 @@ class RevisionInfoConfigurationResult { RevisionInfoConfigurationResult(RevisionInfoGenerator revisionInfoGenerator, Document revisionInfoXmlMapping, RevisionInfoQueryCreator revisionInfoQueryCreator, Element revisionInfoRelationMapping, RevisionInfoNumberReader revisionInfoNumberReader, - ModifiedEntityTypesReader modifiedEntityTypesReader, String revisionInfoEntityName, + ModifiedEntityNamesReader modifiedEntityNamesReader, String revisionInfoEntityName, Class revisionInfoClass, PropertyData revisionInfoTimestampData) { this.revisionInfoGenerator = revisionInfoGenerator; this.revisionInfoXmlMapping = revisionInfoXmlMapping; this.revisionInfoQueryCreator = revisionInfoQueryCreator; this.revisionInfoRelationMapping = revisionInfoRelationMapping; this.revisionInfoNumberReader = revisionInfoNumberReader; - this.modifiedEntityTypesReader = modifiedEntityTypesReader; + this.modifiedEntityNamesReader = modifiedEntityNamesReader; this.revisionInfoEntityName = revisionInfoEntityName; this.revisionInfoClass = revisionInfoClass; this.revisionInfoTimestampData = revisionInfoTimestampData; @@ -392,7 +398,7 @@ class RevisionInfoConfigurationResult { return revisionInfoTimestampData; } - public ModifiedEntityTypesReader getModifiedEntityTypesReader() { - return modifiedEntityTypesReader; + public ModifiedEntityNamesReader getModifiedEntityNamesReader() { + return modifiedEntityNamesReader; } } diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/reader/AuditReaderImpl.java b/hibernate-envers/src/main/java/org/hibernate/envers/reader/AuditReaderImpl.java index 0a43375fc6..60de24205c 100644 --- a/hibernate-envers/src/main/java/org/hibernate/envers/reader/AuditReaderImpl.java +++ b/hibernate-envers/src/main/java/org/hibernate/envers/reader/AuditReaderImpl.java @@ -48,6 +48,8 @@ import org.hibernate.envers.query.AuditEntity; import org.hibernate.envers.query.AuditQueryCreator; import org.hibernate.envers.query.criteria.RevisionTypeAuditExpression; import org.hibernate.envers.synchronization.AuditProcess; +import org.hibernate.envers.tools.Pair; +import org.hibernate.envers.tools.Tools; import org.hibernate.event.spi.EventSource; import org.hibernate.proxy.HibernateProxy; @@ -248,10 +250,10 @@ public class AuditReaderImpl implements AuditReaderImplementor { @SuppressWarnings({"unchecked"}) public List findEntitiesChangedInRevision(Number revision) throws IllegalStateException, IllegalArgumentException, AuditException { - Set clazz = findEntityTypesChangedInRevision(revision); + Set> entityTypes = findEntityTypesChangedInRevision(revision); List result = new ArrayList(); - for (Class c : clazz) { - result.addAll(createQuery().forEntitiesModifiedAtRevision(c, revision).getResultList()); + for (Pair type : entityTypes) { + result.addAll(createQuery().forEntitiesModifiedAtRevision(type.getSecond(), type.getFirst(), revision).getResultList()); } return result; } @@ -259,10 +261,10 @@ public class AuditReaderImpl implements AuditReaderImplementor { @SuppressWarnings({"unchecked"}) public List findEntitiesChangedInRevision(Number revision, RevisionType revisionType) throws IllegalStateException, IllegalArgumentException, AuditException { - Set clazz = findEntityTypesChangedInRevision(revision); + Set> entityTypes = findEntityTypesChangedInRevision(revision); List result = new ArrayList(); - for (Class c : clazz) { - result.addAll(createQuery().forEntitiesModifiedAtRevision(c, revision) + for (Pair type : entityTypes) { + result.addAll(createQuery().forEntitiesModifiedAtRevision(type.getSecond(), type.getFirst(), revision) .add(new RevisionTypeAuditExpression(revisionType, "=")).getResultList()); } return result; @@ -271,12 +273,12 @@ public class AuditReaderImpl implements AuditReaderImplementor { @SuppressWarnings({"unchecked"}) public Map> findEntitiesChangedInRevisionGroupByRevisionType(Number revision) throws IllegalStateException, IllegalArgumentException, AuditException { - Set clazz = findEntityTypesChangedInRevision(revision); + Set> entityTypes = findEntityTypesChangedInRevision(revision); Map> result = new HashMap>(); for (RevisionType revisionType : RevisionType.values()) { - result.put(revisionType, new ArrayList()); - for (Class c : clazz) { - List list = createQuery().forEntitiesModifiedAtRevision(c, revision) + result.put(revisionType, new ArrayList()); + for (Pair type : entityTypes) { + List list = createQuery().forEntitiesModifiedAtRevision(type.getSecond(), type.getFirst(), revision) .add(new RevisionTypeAuditExpression(revisionType, "=")).getResultList(); result.get(revisionType).addAll(list); } @@ -285,14 +287,14 @@ public class AuditReaderImpl implements AuditReaderImplementor { } @SuppressWarnings({"unchecked"}) - public Set findEntityTypesChangedInRevision(Number revision) throws IllegalStateException, - IllegalArgumentException, AuditException { + public Set> findEntityTypesChangedInRevision(Number revision) throws IllegalStateException, + IllegalArgumentException, AuditException { checkNotNull(revision, "Entity revision"); checkPositive(revision, "Entity revision"); checkSession(); if (!verCfg.getGlobalCfg().isTrackEntitiesChangedInRevisionEnabled()) { throw new AuditException("This query is designed for Envers default mechanism of tracking entities modified in a given revision." - + " Extend DefaultTrackingModifiedTypesRevisionEntity, utilize @ModifiedEntityTypes annotation or set " + + " Extend DefaultTrackingModifiedEntitiesRevisionEntity, utilize @ModifiedEntityNames annotation or set " + "'org.hibernate.envers.track_entities_changed_in_revision' parameter to true."); } Set revisions = new HashSet(1); @@ -300,8 +302,14 @@ public class AuditReaderImpl implements AuditReaderImplementor { Criteria query = verCfg.getRevisionInfoQueryCreator().getRevisionsQuery(session, revisions); Object revisionInfo = query.uniqueResult(); if (revisionInfo != null) { - // If revision exists - return verCfg.getModifiedEntityTypesReader().getModifiedEntityTypes(revisionInfo); + // If revision exists. + Set entityNames = verCfg.getModifiedEntityNamesReader().getModifiedEntityNames(revisionInfo); + // Generate result that contains entity names and corresponding Java classes. + Set> result = new HashSet>(); + for (String entityName : entityNames) { + result.add(Pair.make(entityName, Tools.getEntityClass(sessionImplementor, session, entityName))); + } + return result; } return Collections.EMPTY_SET; } diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/DefaultTrackingModifiedEntitiesRevisionInfoGenerator.java b/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/DefaultTrackingModifiedEntitiesRevisionInfoGenerator.java new file mode 100644 index 0000000000..a449a265f8 --- /dev/null +++ b/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/DefaultTrackingModifiedEntitiesRevisionInfoGenerator.java @@ -0,0 +1,47 @@ +package org.hibernate.envers.revisioninfo; + +import org.hibernate.envers.DefaultTrackingModifiedEntitiesRevisionEntity; +import org.hibernate.envers.ModifiedEntityNames; +import org.hibernate.envers.RevisionListener; +import org.hibernate.envers.RevisionType; +import org.hibernate.envers.entities.PropertyData; +import org.hibernate.envers.tools.reflection.ReflectionTools; +import org.hibernate.property.Getter; +import org.hibernate.property.Setter; + +import java.io.Serializable; +import java.util.HashSet; +import java.util.Set; + +/** + * Automatically adds entity names, that have been changed during current revision, to revision entity. + * @see ModifiedEntityNames + * @see DefaultTrackingModifiedEntitiesRevisionEntity + * @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com) + */ +public class DefaultTrackingModifiedEntitiesRevisionInfoGenerator extends DefaultRevisionInfoGenerator { + private final Setter modifiedEntityNamesSetter; + private final Getter modifiedEntityNamesGetter; + + public DefaultTrackingModifiedEntitiesRevisionInfoGenerator(String revisionInfoEntityName, Class revisionInfoClass, + Class listenerClass, + PropertyData revisionInfoTimestampData, boolean timestampAsDate, + PropertyData modifiedEntityNamesData) { + super(revisionInfoEntityName, revisionInfoClass, listenerClass, revisionInfoTimestampData, timestampAsDate); + modifiedEntityNamesSetter = ReflectionTools.getSetter(revisionInfoClass, modifiedEntityNamesData); + modifiedEntityNamesGetter = ReflectionTools.getGetter(revisionInfoClass, modifiedEntityNamesData); + } + + @Override + @SuppressWarnings({"unchecked"}) + public void entityChanged(Class entityClass, String entityName, Serializable entityId, RevisionType revisionType, + Object revisionEntity) { + super.entityChanged(entityClass, entityName, entityId, revisionType, revisionEntity); + Set modifiedEntityNames = (Set) modifiedEntityNamesGetter.get(revisionEntity); + if (modifiedEntityNames == null) { + modifiedEntityNames = new HashSet(); + modifiedEntityNamesSetter.set(revisionEntity, modifiedEntityNames, null); + } + modifiedEntityNames.add(entityName); + } +} diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/DefaultTrackingModifiedTypesRevisionInfoGenerator.java b/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/DefaultTrackingModifiedTypesRevisionInfoGenerator.java deleted file mode 100644 index 178e4c2180..0000000000 --- a/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/DefaultTrackingModifiedTypesRevisionInfoGenerator.java +++ /dev/null @@ -1,47 +0,0 @@ -package org.hibernate.envers.revisioninfo; - -import org.hibernate.envers.DefaultTrackingModifiedTypesRevisionEntity; -import org.hibernate.envers.ModifiedEntityTypes; -import org.hibernate.envers.RevisionListener; -import org.hibernate.envers.RevisionType; -import org.hibernate.envers.entities.PropertyData; -import org.hibernate.envers.tools.reflection.ReflectionTools; -import org.hibernate.property.Getter; -import org.hibernate.property.Setter; - -import java.io.Serializable; -import java.util.HashSet; -import java.util.Set; - -/** - * Automatically adds entity class names, that have been changed during current revision, to revision entity. - * @see ModifiedEntityTypes - * @see DefaultTrackingModifiedTypesRevisionEntity - * @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com) - */ -public class DefaultTrackingModifiedTypesRevisionInfoGenerator extends DefaultRevisionInfoGenerator { - private final Setter modifiedEntityTypesSetter; - private final Getter modifiedEntityTypesGetter; - - public DefaultTrackingModifiedTypesRevisionInfoGenerator(String revisionInfoEntityName, Class revisionInfoClass, - Class listenerClass, - PropertyData revisionInfoTimestampData, boolean timestampAsDate, - PropertyData modifiedEntityTypesData) { - super(revisionInfoEntityName, revisionInfoClass, listenerClass, revisionInfoTimestampData, timestampAsDate); - modifiedEntityTypesSetter = ReflectionTools.getSetter(revisionInfoClass, modifiedEntityTypesData); - modifiedEntityTypesGetter = ReflectionTools.getGetter(revisionInfoClass, modifiedEntityTypesData); - } - - @Override - @SuppressWarnings({"unchecked"}) - public void entityChanged(Class entityClass, String entityName, Serializable entityId, RevisionType revisionType, - Object revisionEntity) { - super.entityChanged(entityClass, entityName, entityId, revisionType, revisionEntity); - Set modifiedEntityTypes = (Set) modifiedEntityTypesGetter.get(revisionEntity); - if (modifiedEntityTypes == null) { - modifiedEntityTypes = new HashSet(); - modifiedEntityTypesSetter.set(revisionEntity, modifiedEntityTypes, null); - } - modifiedEntityTypes.add(entityClass.getName()); - } -} diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/ModifiedEntityNamesReader.java b/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/ModifiedEntityNamesReader.java new file mode 100644 index 0000000000..7d7bb8b5a1 --- /dev/null +++ b/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/ModifiedEntityNamesReader.java @@ -0,0 +1,27 @@ +package org.hibernate.envers.revisioninfo; + +import org.hibernate.envers.entities.PropertyData; +import org.hibernate.envers.tools.reflection.ReflectionTools; +import org.hibernate.property.Getter; + +import java.util.Collections; +import java.util.HashSet; +import java.util.Set; + +/** + * Returns modified entity names from a persisted revision info entity. + * @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com) + */ +public class ModifiedEntityNamesReader { + private final Getter modifiedEntityNamesGetter; + + public ModifiedEntityNamesReader(Class revisionInfoClass, PropertyData modifiedEntityNamesData) { + modifiedEntityNamesGetter = ReflectionTools.getGetter(revisionInfoClass, modifiedEntityNamesData); + } + + @SuppressWarnings({"unchecked"}) + public Set getModifiedEntityNames(Object revisionEntity) { + Set modifiedEntityNames = (Set) modifiedEntityNamesGetter.get(revisionEntity); + return modifiedEntityNames != null ? modifiedEntityNames : Collections.EMPTY_SET; + } +} diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/ModifiedEntityTypesReader.java b/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/ModifiedEntityTypesReader.java deleted file mode 100644 index 137f9f2199..0000000000 --- a/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/ModifiedEntityTypesReader.java +++ /dev/null @@ -1,41 +0,0 @@ -package org.hibernate.envers.revisioninfo; - -import org.hibernate.envers.entities.PropertyData; -import org.hibernate.envers.tools.reflection.ReflectionTools; -import org.hibernate.property.Getter; - -import java.util.Collections; -import java.util.HashSet; -import java.util.Set; - -/** - * Returns modified entity types from a persisted revision info entity. - * @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com) - */ -public class ModifiedEntityTypesReader { - private final Getter modifiedEntityTypesGetter; - - public ModifiedEntityTypesReader(Class revisionInfoClass, PropertyData modifiedEntityTypesData) { - modifiedEntityTypesGetter = ReflectionTools.getGetter(revisionInfoClass, modifiedEntityTypesData); - } - - @SuppressWarnings({"unchecked"}) - public Set getModifiedEntityTypes(Object revisionEntity) { - // The default mechanism of tracking entity types that have been changed during each revision stores - // fully qualified Java class names. - Set modifiedEntityClassNames = (Set) modifiedEntityTypesGetter.get(revisionEntity); - if (modifiedEntityClassNames != null) { - Set result = new HashSet(modifiedEntityClassNames.size()); - for (String entityClassName : modifiedEntityClassNames) { - try { - result.add(Thread.currentThread().getContextClassLoader().loadClass(entityClassName)); - } catch (ClassNotFoundException e) { - // This shall never happen - throw new RuntimeException(e); - } - } - return result; - } - return Collections.EMPTY_SET; - } -} diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/synchronization/EntityChangeNotifier.java b/hibernate-envers/src/main/java/org/hibernate/envers/synchronization/EntityChangeNotifier.java index c98098ac18..21d09f6fb7 100644 --- a/hibernate-envers/src/main/java/org/hibernate/envers/synchronization/EntityChangeNotifier.java +++ b/hibernate-envers/src/main/java/org/hibernate/envers/synchronization/EntityChangeNotifier.java @@ -6,7 +6,7 @@ import org.hibernate.envers.RevisionType; import org.hibernate.envers.revisioninfo.RevisionInfoGenerator; import org.hibernate.envers.synchronization.work.AuditWorkUnit; import org.hibernate.envers.synchronization.work.PersistentCollectionChangeWorkUnit; -import org.hibernate.persister.entity.EntityPersister; +import org.hibernate.envers.tools.Tools; import java.io.Serializable; @@ -36,16 +36,8 @@ public class EntityChangeNotifier { // Notify about a change in collection owner entity. entityId = ((PersistentCollectionChangeWorkUnit.PersistentCollectionChangeWorkUnitId) entityId).getOwnerId(); } - Class entityClass = getEntityClass(session, vwu.getEntityName()); + Class entityClass = Tools.getEntityClass(sessionImplementor, session, vwu.getEntityName()); revisionInfoGenerator.entityChanged(entityClass, vwu.getEntityName(), entityId, vwu.getRevisionType(), currentRevisionData); } - - /** - * @return Java class mapped to specified entity name. - */ - private Class getEntityClass(Session session, String entityName) { - EntityPersister entityPersister = sessionImplementor.getFactory().getEntityPersister(entityName); - return entityPersister.getClassMetadata().getMappedClass(session.getEntityMode()); - } } diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/tools/Tools.java b/hibernate-envers/src/main/java/org/hibernate/envers/tools/Tools.java index a8d7660fe7..8f65da255c 100644 --- a/hibernate-envers/src/main/java/org/hibernate/envers/tools/Tools.java +++ b/hibernate-envers/src/main/java/org/hibernate/envers/tools/Tools.java @@ -35,6 +35,7 @@ import javassist.util.proxy.ProxyFactory; import org.hibernate.Session; import org.hibernate.engine.spi.SessionFactoryImplementor; import org.hibernate.engine.spi.SessionImplementor; +import org.hibernate.persister.entity.EntityPersister; import org.hibernate.proxy.HibernateProxy; /** @@ -178,4 +179,12 @@ public class Tools { return value; } } + + /** + * @return Java class mapped to specified entity name. + */ + public static Class getEntityClass(SessionImplementor sessionImplementor, Session session, String entityName) { + EntityPersister entityPersister = sessionImplementor.getFactory().getEntityPersister(entityName); + return entityPersister.getClassMetadata().getMappedClass(session.getEntityMode()); + } } diff --git a/hibernate-envers/src/test/java/org/hibernate/envers/test/entities/reventity/trackmodifiedentities/AnnotatedTrackingRevisionEntity.java b/hibernate-envers/src/test/java/org/hibernate/envers/test/entities/reventity/trackmodifiedentities/AnnotatedTrackingRevisionEntity.java index 28086dd310..ba0416f435 100644 --- a/hibernate-envers/src/test/java/org/hibernate/envers/test/entities/reventity/trackmodifiedentities/AnnotatedTrackingRevisionEntity.java +++ b/hibernate-envers/src/test/java/org/hibernate/envers/test/entities/reventity/trackmodifiedentities/AnnotatedTrackingRevisionEntity.java @@ -1,6 +1,6 @@ package org.hibernate.envers.test.entities.reventity.trackmodifiedentities; -import org.hibernate.envers.ModifiedEntityTypes; +import org.hibernate.envers.ModifiedEntityNames; import org.hibernate.envers.RevisionEntity; import org.hibernate.envers.RevisionNumber; import org.hibernate.envers.RevisionTimestamp; @@ -9,7 +9,7 @@ import javax.persistence.*; import java.util.Set; /** - * Sample revision entity that uses {@link ModifiedEntityTypes} annotation. + * Sample revision entity that uses {@link ModifiedEntityNames} annotation. * @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com) */ @Entity @@ -25,9 +25,9 @@ public class AnnotatedTrackingRevisionEntity { @ElementCollection @JoinTable(name = "REVCHANGES", joinColumns = @JoinColumn(name = "REV")) - @Column(name = "ENTITYTYPE") - @ModifiedEntityTypes - private Set entityTypes; + @Column(name = "ENTITYNAME") + @ModifiedEntityNames + private Set entityNames; public int getCustomId() { return customId; @@ -45,12 +45,12 @@ public class AnnotatedTrackingRevisionEntity { this.customTimestamp = customTimestamp; } - public Set getEntityTypes() { - return entityTypes; + public Set getEntityNames() { + return entityNames; } - public void setEntityTypes(Set entityTypes) { - this.entityTypes = entityTypes; + public void setEntityNames(Set entityNames) { + this.entityNames = entityNames; } public boolean equals(Object o) { @@ -61,7 +61,7 @@ public class AnnotatedTrackingRevisionEntity { if (customId != that.customId) return false; if (customTimestamp != that.customTimestamp) return false; - if (entityTypes != null ? !entityTypes.equals(that.entityTypes) : that.entityTypes != null) return false; + if (entityNames != null ? !entityNames.equals(that.entityNames) : that.entityNames != null) return false; return true; } @@ -69,12 +69,12 @@ public class AnnotatedTrackingRevisionEntity { public int hashCode() { int result = customId; result = 31 * result + (int) (customTimestamp ^ (customTimestamp >>> 32)); - result = 31 * result + (entityTypes != null ? entityTypes.hashCode() : 0); + result = 31 * result + (entityNames != null ? entityNames.hashCode() : 0); return result; } @Override public String toString() { - return "AnnotatedTrackingRevisionEntity(customId = " + customId + ", customTimestamp = " + customTimestamp + ", entityTypes=" + entityTypes + ")"; + return "AnnotatedTrackingRevisionEntity(customId = " + customId + ", customTimestamp = " + customTimestamp + ", entityNames=" + entityNames + ")"; } } diff --git a/hibernate-envers/src/test/java/org/hibernate/envers/test/entities/reventity/trackmodifiedentities/ExtendedRevisionEntity.java b/hibernate-envers/src/test/java/org/hibernate/envers/test/entities/reventity/trackmodifiedentities/ExtendedRevisionEntity.java index 18ad074233..ccf308e077 100644 --- a/hibernate-envers/src/test/java/org/hibernate/envers/test/entities/reventity/trackmodifiedentities/ExtendedRevisionEntity.java +++ b/hibernate-envers/src/test/java/org/hibernate/envers/test/entities/reventity/trackmodifiedentities/ExtendedRevisionEntity.java @@ -1,7 +1,6 @@ package org.hibernate.envers.test.entities.reventity.trackmodifiedentities; -import org.hibernate.envers.DefaultRevisionEntity; -import org.hibernate.envers.DefaultTrackingModifiedTypesRevisionEntity; +import org.hibernate.envers.DefaultTrackingModifiedEntitiesRevisionEntity; import org.hibernate.envers.RevisionEntity; import javax.persistence.Entity; @@ -11,14 +10,14 @@ import javax.persistence.Entity; */ @Entity @RevisionEntity(ExtendedRevisionListener.class) -public class ExtendedRevisionEntity extends DefaultTrackingModifiedTypesRevisionEntity { - private String commnent; +public class ExtendedRevisionEntity extends DefaultTrackingModifiedEntitiesRevisionEntity { + private String comment; - public String getCommnent() { - return commnent; + public String getComment() { + return comment; } - public void setCommnent(String commnent) { - this.commnent = commnent; + public void setComment(String comment) { + this.comment = comment; } } diff --git a/hibernate-envers/src/test/java/org/hibernate/envers/test/entities/reventity/trackmodifiedentities/ExtendedRevisionListener.java b/hibernate-envers/src/test/java/org/hibernate/envers/test/entities/reventity/trackmodifiedentities/ExtendedRevisionListener.java index aebe66edde..d78317497a 100644 --- a/hibernate-envers/src/test/java/org/hibernate/envers/test/entities/reventity/trackmodifiedentities/ExtendedRevisionListener.java +++ b/hibernate-envers/src/test/java/org/hibernate/envers/test/entities/reventity/trackmodifiedentities/ExtendedRevisionListener.java @@ -9,6 +9,6 @@ public class ExtendedRevisionListener implements RevisionListener { public static final String COMMENT_VALUE = "Comment"; public void newRevision(Object revisionEntity) { - ((ExtendedRevisionEntity)revisionEntity).setCommnent(COMMENT_VALUE); + ((ExtendedRevisionEntity)revisionEntity).setComment(COMMENT_VALUE); } } diff --git a/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/AnnotatedTrackingEntitiesTest.java b/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/AnnotatedTrackingEntitiesTest.java index 04daab141b..3bbbec2fef 100644 --- a/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/AnnotatedTrackingEntitiesTest.java +++ b/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/AnnotatedTrackingEntitiesTest.java @@ -1,11 +1,11 @@ package org.hibernate.envers.test.integration.reventity.trackmodifiedentities; import org.hibernate.ejb.Ejb3Configuration; -import org.hibernate.envers.ModifiedEntityTypes; +import org.hibernate.envers.ModifiedEntityNames; import org.hibernate.envers.test.entities.reventity.trackmodifiedentities.AnnotatedTrackingRevisionEntity; /** - * Tests proper behavior of revision entity that utilizes {@link ModifiedEntityTypes} annotation. + * Tests proper behavior of revision entity that utilizes {@link ModifiedEntityNames} annotation. * @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com) */ public class AnnotatedTrackingEntitiesTest extends DefaultTrackingEntitiesTest { diff --git a/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/CustomTrackingEntitiesTest.java b/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/CustomTrackingEntitiesTest.java index 33573bd92d..ecfd829ad7 100644 --- a/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/CustomTrackingEntitiesTest.java +++ b/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/CustomTrackingEntitiesTest.java @@ -1,7 +1,6 @@ package org.hibernate.envers.test.integration.reventity.trackmodifiedentities; import org.hibernate.ejb.Ejb3Configuration; -import org.hibernate.envers.AuditReader; import org.hibernate.envers.EntityTrackingRevisionListener; import org.hibernate.envers.exception.AuditException; import org.hibernate.envers.test.AbstractEntityTest; @@ -19,7 +18,7 @@ import javax.persistence.EntityManager; /** * Tests proper behavior of entity listener that implements {@link EntityTrackingRevisionListener} * interface. {@link CustomTrackingRevisionListener} shall be notified whenever an entity instance has been - * added, modified or removed, so that changed entity type can be persisted. + * added, modified or removed, so that changed entity name can be persisted. * @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com) */ public class CustomTrackingEntitiesTest extends AbstractEntityTest { @@ -69,8 +68,7 @@ public class CustomTrackingEntitiesTest extends AbstractEntityTest { ModifiedEntityTypeEntity steDescriptor = new ModifiedEntityTypeEntity(StrTestEntity.class.getName()); ModifiedEntityTypeEntity siteDescriptor = new ModifiedEntityTypeEntity(StrIntTestEntity.class.getName()); - AuditReader vr = getAuditReader(); - CustomTrackingRevisionEntity ctre = vr.findRevision(CustomTrackingRevisionEntity.class, 1); + CustomTrackingRevisionEntity ctre = getAuditReader().findRevision(CustomTrackingRevisionEntity.class, 1); assert ctre.getModifiedEntityTypes() != null; assert ctre.getModifiedEntityTypes().size() == 2; @@ -81,8 +79,7 @@ public class CustomTrackingEntitiesTest extends AbstractEntityTest { public void testTrackModifiedEntities() { ModifiedEntityTypeEntity siteDescriptor = new ModifiedEntityTypeEntity(StrIntTestEntity.class.getName()); - AuditReader vr = getAuditReader(); - CustomTrackingRevisionEntity ctre = vr.findRevision(CustomTrackingRevisionEntity.class, 2); + CustomTrackingRevisionEntity ctre = getAuditReader().findRevision(CustomTrackingRevisionEntity.class, 2); assert ctre.getModifiedEntityTypes() != null; assert ctre.getModifiedEntityTypes().size() == 1; @@ -94,8 +91,7 @@ public class CustomTrackingEntitiesTest extends AbstractEntityTest { ModifiedEntityTypeEntity steDescriptor = new ModifiedEntityTypeEntity(StrTestEntity.class.getName()); ModifiedEntityTypeEntity siteDescriptor = new ModifiedEntityTypeEntity(StrIntTestEntity.class.getName()); - AuditReader vr = getAuditReader(); - CustomTrackingRevisionEntity ctre = vr.findRevision(CustomTrackingRevisionEntity.class, 3); + CustomTrackingRevisionEntity ctre = getAuditReader().findRevision(CustomTrackingRevisionEntity.class, 3); assert ctre.getModifiedEntityTypes() != null; assert ctre.getModifiedEntityTypes().size() == 2; diff --git a/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/DefaultTrackingEntitiesTest.java b/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/DefaultTrackingEntitiesTest.java index df28c9b7a9..27ba587e0e 100644 --- a/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/DefaultTrackingEntitiesTest.java +++ b/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/DefaultTrackingEntitiesTest.java @@ -7,6 +7,7 @@ import org.hibernate.envers.test.Priority; import org.hibernate.envers.test.entities.StrIntTestEntity; import org.hibernate.envers.test.entities.StrTestEntity; import org.hibernate.envers.test.tools.TestTools; +import org.hibernate.envers.tools.Pair; import org.hibernate.mapping.Column; import org.hibernate.mapping.Table; import org.junit.Test; @@ -17,7 +18,7 @@ import java.util.List; import java.util.Map; /** - * Tests proper behavior of tracking modified entity types when {@code org.hibernate.envers.track_entities_changed_in_revision} + * Tests proper behavior of tracking modified entity names when {@code org.hibernate.envers.track_entities_changed_in_revision} * parameter is set to {@code true}. * @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com) */ @@ -71,7 +72,7 @@ public class DefaultTrackingEntitiesTest extends AbstractEntityTest { if ("REVCHANGES".equals(table.getName())) { assert table.getColumnSpan() == 2; assert table.getColumn(new Column("REV")) != null; - assert table.getColumn(new Column("ENTITYTYPE")) != null; + assert table.getColumn(new Column("ENTITYNAME")) != null; return; } } @@ -163,8 +164,15 @@ public class DefaultTrackingEntitiesTest extends AbstractEntityTest { @Test public void testFindEntityTypesChangedInRevision() { - assert TestTools.makeSet(StrTestEntity.class, StrIntTestEntity.class).equals(getAuditReader().findEntityTypesChangedInRevision(1)); - assert TestTools.makeSet(StrIntTestEntity.class).equals(getAuditReader().findEntityTypesChangedInRevision(2)); - assert TestTools.makeSet(StrTestEntity.class, StrIntTestEntity.class).equals(getAuditReader().findEntityTypesChangedInRevision(3)); + assert TestTools.makeSet(Pair.make(StrTestEntity.class.getName(), StrTestEntity.class), + Pair.make(StrIntTestEntity.class.getName(), StrIntTestEntity.class)) + .equals(getAuditReader().findEntityTypesChangedInRevision(1)); + + assert TestTools.makeSet(Pair.make(StrIntTestEntity.class.getName(), StrIntTestEntity.class)) + .equals(getAuditReader().findEntityTypesChangedInRevision(2)); + + assert TestTools.makeSet(Pair.make(StrTestEntity.class.getName(), StrTestEntity.class), + Pair.make(StrIntTestEntity.class.getName(), StrIntTestEntity.class)) + .equals(getAuditReader().findEntityTypesChangedInRevision(3)); } } diff --git a/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/EntityNamesTest.java b/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/EntityNamesTest.java index aa755d49e2..c3260ef5b0 100644 --- a/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/EntityNamesTest.java +++ b/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/EntityNamesTest.java @@ -6,13 +6,13 @@ import org.hibernate.envers.test.Priority; import org.hibernate.envers.test.integration.entityNames.manyToManyAudited.Car; import org.hibernate.envers.test.integration.entityNames.manyToManyAudited.Person; import org.hibernate.envers.test.tools.TestTools; +import org.hibernate.envers.tools.Pair; import org.junit.Test; import java.io.File; import java.net.URISyntaxException; import java.net.URL; import java.util.ArrayList; -import java.util.Arrays; import java.util.List; /** @@ -62,7 +62,11 @@ public class EntityNamesTest extends AbstractSessionTest { @Test @SuppressWarnings("unchecked") public void testModifiedEntityTypes() { - assert TestTools.makeSet(Car.class, Person.class).equals(getAuditReader().findEntityTypesChangedInRevision(1)); - assert TestTools.makeSet(Car.class, Person.class).equals(getAuditReader().findEntityTypesChangedInRevision(2)); + assert TestTools.makeSet(Pair.make(Car.class.getName(), Car.class), + Pair.make("Personaje", Person.class)) + .equals(getAuditReader().findEntityTypesChangedInRevision(1)); + assert TestTools.makeSet(Pair.make(Car.class.getName(), Car.class), + Pair.make("Personaje", Person.class)) + .equals(getAuditReader().findEntityTypesChangedInRevision(2)); } } \ No newline at end of file diff --git a/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/ExtendedRevisionEntityTest.java b/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/ExtendedRevisionEntityTest.java index 140129134f..824f2750cf 100644 --- a/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/ExtendedRevisionEntityTest.java +++ b/hibernate-envers/src/test/java/org/hibernate/envers/test/integration/reventity/trackmodifiedentities/ExtendedRevisionEntityTest.java @@ -1,14 +1,13 @@ package org.hibernate.envers.test.integration.reventity.trackmodifiedentities; import org.hibernate.ejb.Ejb3Configuration; -import org.hibernate.envers.AuditReader; -import org.hibernate.envers.DefaultTrackingModifiedTypesRevisionEntity; +import org.hibernate.envers.DefaultTrackingModifiedEntitiesRevisionEntity; import org.hibernate.envers.test.entities.reventity.trackmodifiedentities.ExtendedRevisionEntity; import org.hibernate.envers.test.entities.reventity.trackmodifiedentities.ExtendedRevisionListener; import org.junit.Test; /** - * Tests proper behavior of revision entity that extends {@link DefaultTrackingModifiedTypesRevisionEntity}. + * Tests proper behavior of revision entity that extends {@link DefaultTrackingModifiedEntitiesRevisionEntity}. * @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com) */ public class ExtendedRevisionEntityTest extends DefaultTrackingEntitiesTest { @@ -21,9 +20,8 @@ public class ExtendedRevisionEntityTest extends DefaultTrackingEntitiesTest { @Test public void testCommentPropertyValue() { - AuditReader vr = getAuditReader(); - ExtendedRevisionEntity ere = vr.findRevision(ExtendedRevisionEntity.class, 1); + ExtendedRevisionEntity ere = getAuditReader().findRevision(ExtendedRevisionEntity.class, 1); - assert ExtendedRevisionListener.COMMENT_VALUE.equals(ere.getCommnent()); + assert ExtendedRevisionListener.COMMENT_VALUE.equals(ere.getComment()); } } From f3a6476a66cfa4576301f7eb98890ad502034d7a Mon Sep 17 00:00:00 2001 From: Lukasz Antoniak Date: Sun, 12 Jun 2011 14:15:10 +0200 Subject: [PATCH 2/2] HHH-5580 - Refactoring --- .../org/hibernate/envers/reader/AuditReaderImpl.java | 12 +++++++----- .../revisioninfo/ModifiedEntityNamesReader.java | 3 +-- 2 files changed, 8 insertions(+), 7 deletions(-) diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/reader/AuditReaderImpl.java b/hibernate-envers/src/main/java/org/hibernate/envers/reader/AuditReaderImpl.java index 60de24205c..05aafba24a 100644 --- a/hibernate-envers/src/main/java/org/hibernate/envers/reader/AuditReaderImpl.java +++ b/hibernate-envers/src/main/java/org/hibernate/envers/reader/AuditReaderImpl.java @@ -304,12 +304,14 @@ public class AuditReaderImpl implements AuditReaderImplementor { if (revisionInfo != null) { // If revision exists. Set entityNames = verCfg.getModifiedEntityNamesReader().getModifiedEntityNames(revisionInfo); - // Generate result that contains entity names and corresponding Java classes. - Set> result = new HashSet>(); - for (String entityName : entityNames) { - result.add(Pair.make(entityName, Tools.getEntityClass(sessionImplementor, session, entityName))); + if (entityNames != null) { + // Generate result that contains entity names and corresponding Java classes. + Set> result = new HashSet>(); + for (String entityName : entityNames) { + result.add(Pair.make(entityName, Tools.getEntityClass(sessionImplementor, session, entityName))); + } + return result; } - return result; } return Collections.EMPTY_SET; } diff --git a/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/ModifiedEntityNamesReader.java b/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/ModifiedEntityNamesReader.java index 7d7bb8b5a1..d140be6095 100644 --- a/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/ModifiedEntityNamesReader.java +++ b/hibernate-envers/src/main/java/org/hibernate/envers/revisioninfo/ModifiedEntityNamesReader.java @@ -21,7 +21,6 @@ public class ModifiedEntityNamesReader { @SuppressWarnings({"unchecked"}) public Set getModifiedEntityNames(Object revisionEntity) { - Set modifiedEntityNames = (Set) modifiedEntityNamesGetter.get(revisionEntity); - return modifiedEntityNames != null ? modifiedEntityNames : Collections.EMPTY_SET; + return (Set) modifiedEntityNamesGetter.get(revisionEntity); } }