简体   繁体   English

Hibernate Envers 因@Converter 和 AttributeConverter (JPA 2.1) 而失败

[英]Hibernate Envers fails with @Converter and AttributeConverter (JPA 2.1)

I am using Hibernate 4.3.4 with Envers, and MySql 5.6.我正在使用带有 Envers 的 Hibernate 4.3.4 和 MySql 5.6。

Without a JPA 2.1 converter, the Party entity below fails at Configuration.buildSessionFactory() as it should, since Hibernate doesn't know what to do with the Name class:如果没有 JPA 2.1 转换器,下面的Party实体会在Configuration.buildSessionFactory()失败,因为 Hibernate 不知道如何处理名称 class:

@Entity
@Audited
public class Party
    {
    protected Name name;
    ...
    }

The exception is:例外是:

org.hibernate.MappingException: 
  Could not determine type for: 
    ModuloADM.Party.Name, 
    at table: Party, for columns: [org.hibernate.mapping.Column(name)]

To fix this, I then add this converter:为了解决这个问题,我添加了这个转换器:

@Converter (autoApply=true)
public class NametoStringConverter
      implements AttributeConverter<Name, String>
    { ... }

And the exception now changes to:异常现在变为:

org.hibernate.MappingException: 
  Could not determine type for: 
    BasicType adapter for AttributeConverter<Name,String>, 
    at table: History_Party, for columns: [org.hibernate.mapping.Column(name)]

This is now failing at the Envers auditing table for the Party entity.现在,这在Party实体的 Envers 审计表中失败了。 Note that History_Party is the name of the audit table, as chosen by config.setProperty("org.hibernate.envers.audit_table_prefix", "History_") .请注意, History_Party是审计表的名称,由config.setProperty("org.hibernate.envers.audit_table_prefix", "History_")选择。

The complete stacktrace is:完整的堆栈跟踪是:

org.hibernate.MappingException: 
  Could not determine type for: 
    BasicType adapter for AttributeConverter<Name,String>, 
    at table: History_Party, for columns: [org.hibernate.mapping.Column(name)]

  at org.hibernate.mapping.SimpleValue.getType(SimpleValue.java:336)
    at org.hibernate.tuple.PropertyFactory.buildEntityBasedAttribute(PropertyFactory.java:246)
    at org.hibernate.tuple.entity.EntityMetamodel.<init>(EntityMetamodel.java:227)
    at org.hibernate.persister.entity.AbstractEntityPersister.<init>(AbstractEntityPersister.java:520)
    at org.hibernate.persister.entity.SingleTableEntityPersister.<init>(SingleTableEntityPersister.java:148)
    at sun.reflect.GeneratedConstructorAccessor43.newInstance(Unknown Source)
    at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
    at java.lang.reflect.Constructor.newInstance(Constructor.java:525)
    at org.hibernate.persister.internal.PersisterFactoryImpl.create(PersisterFactoryImpl.java:163)
    at org.hibernate.persister.internal.PersisterFactoryImpl.createEntityPersister(PersisterFactoryImpl.java:135)
    at org.hibernate.internal.SessionFactoryImpl.<init>(SessionFactoryImpl.java:401)
    at org.hibernate.cfg.Configuration.buildSessionFactory(Configuration.java:1857)

How do I solve this?我该如何解决这个问题? Is Envers even compatible with AttributeConverters? Envers 甚至与 AttributeConverters 兼容吗?

Try using @Convert in Party Entity. 尝试在Party实体中使用@Convert。 Sometimes autoApply flag will not work 有时autoApply标志不起作用

@Entity
@Audited
public class Party
    {
    @Convert(converter = NametoStringConverter.class)
    protected Name name;
    ...
    }

This seems to be a known problem with Hibernate Envers (HHH-9042) . 这似乎是休眠Envers(HHH-9042)已知问题

A simple workaround would be a manual invocation of the Convter and an additional transient field, like this: 一个简单的解决方法是手动调用Convter和其他瞬态字段,如下所示:

@Entity
public class Party {

  protected Name name;

  @Transient
  protected String nameString;

  //...

  public void setName(Name name) {
    this.nameString = (new NametoStringConverter()).convertToDatabaseColumn(name);
    this.name = name;
  }

  //...

  public void setNameString(String nameString) {
    this.name = (new NametoStringConverter()).convertToEntityAttribute(nameString);
    this.nameString = nameString;
  }

}

Depending on the conversion functions, the code could be further simplified by making them static and importing them. 根据转换功能的不同,可以通过将其设置为static并导入来进一步简化代码。

I see the text "GeneratedConstructorAccessor43" in the exception. 我在例外中看到了文本“ GeneratedConstructorAccessor43”。 May be you need a public void constructor so that JPA can create an instance of NametoStringConverter. 可能是您需要一个公共void构造函数,以便JPA可以创建NametoStringConverter的实例。

The default constructor should work but check if you have another one with receives parameters or not public. 默认的构造函数应该可以工作,但是请检查您是否有另一个带有接收参数的对象,或者是否不公开。

I had the same problem, what I found out that it only occured when I didn't put the @Column annotation with columnDefinition = "VARCHAR(255)" to the Enum. 我遇到了同样的问题,发现它仅在没有将带有columnDefinition =“ VARCHAR(255)”的@Column注释放入枚举时才发生。 So I think that is a better work around than what in hibernate tracker has. 因此,我认为这是比休眠跟踪器更好的解决方法。

In case you need to specify a column name for the column (in this example "C_NAME") you need to add @Column annotation.如果您需要为列指定列名(在此示例中为“C_NAME”),则需要添加 @Column 注释。

@Entity
@Audited
public class Party
    {
    @Convert(converter = NametoStringConverter.class)
    @Column( name = "C_NAME" )
    protected Name name;
    ...
    }

Note below code will not work and will result in "Could not determine type for: " error because Converter annotation will be ignored.注意下面的代码将不起作用,并会导致“无法确定类型:”错误,因为转换器注释将被忽略。

@Entity
@Audited
public class Party
    {
    @Convert(converter = NametoStringConverter.class)
    @Column( name = "C_NAME", nullable=true )   // DOESN'T WORK
    protected Name name;
    ...
    }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 加载spring-boot和spring-data-jpa时,Hibernate无法加载JPA 2.1 Converter - Hibernate fails to load JPA 2.1 Converter when loaded with spring-boot and spring-data-jpa 在 InheritanceType.JOINED 中使用 AttributeConverter 映射 MySQL ENUM 在 Hibernate 5.3.6 (JPA 2.1+) 上抛出 IllegalArgumentException:没有枚举常量 - Mapping MySQL ENUM with AttributeConverter in InheritanceType.JOINED throwing IllegalArgumentExceptionon Hibernate 5.3.6 (JPA 2.1+): No enum constant JPA +休眠Envers - JPA + Hibernate Envers JPA 2.1转换器注释 - JPA 2.1 Converter Annotation 如何在JPA XML映射文件中使用AttributeConverter(JPA 2.1)? - How to use AttributeConverter(JPA 2.1) in JPA XML mapping file? 如果在JOIN中使用自定义查询,则Hibernate AttributeConverter会失败 - Hibernate AttributeConverter fails if using custom query with JOIN Hibernate JPA 2.1依赖 - Hibernate JPA 2.1 dependency JPA / Hibernate:在复杂类上使用AttributeConverter时创建UserType是否明显? - JPA/Hibernate: is it obvious to create UserType when using AttributeConverter on complex class? 如何在Hibernate-Mapping XML(HBM 4.3)中使用JPA AttributeConverter? - How to use JPA AttributeConverter with Hibernate-Mapping XML (HBM 4.3)? JPA AttributeConverter 使休眠在事务中的整个表上生成更新语句 - JPA AttributeConverter makes hibernate generate update statements on whole table in transaction
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM