我正在使用hibernate版本5.2.12.Final jar。我想在hibernate Envers中使用getEntityName。我有一个用@Audited注释的Book类。
@Audited
@Entity(name="Book")
//hib envers to audit and revision for handle ddl/dml operation.
/*@RevisionEntity // to get revision entity
*/
@Table(name = "Book")
public class Book /*extends DefaultRevisionEntity*/{
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private long id;
private String title;
private String author;
public long getId() {
return id;
}
我在尝试:
AuditReader reader = AuditReaderFactory.get(HibernateUtil.getSessionFactory().openSession());
String entityName = reader.getEntityName(3, 1,"Book");
System.out.println("Entity Name : " + entityName);
但抛出异常:
org.hibernate.HibernateException: Envers can't resolve entityName for historic entity. The id, revision and entity is not on envers first level cache.
at org.hibernate.envers.internal.reader.AuditReaderImpl.getEntityName(AuditReaderImpl.java:327)
at com.boraji.tutorial.hibernate.MainApp.main(MainApp.java:119)
帮助将表示感谢,谢谢。
答案 0 :(得分:1)
为了获取您的审计实体名称,您应该参考此post,其中介绍了如果您事先了解自己的ORM实体名称,如何获取该名称。
为了获得ORM实体名称,实际上有几种方法可以获得它。一种可能非常便携的方法是访问给定实体类的Metamodel
并获取其名称。
Session session = // get your session from somewhere
String name = session.getMetamodel().entity( YourEntityClass.class ).getName();
另一种选择是从EntityPersister
界面访问它。请注意,这不一定可以在次要版本中移植,因为这是使用SPI但它是一个选项。您首先需要获取上面post所示的SessionImplementor
。一旦你有了persister,它就是一个简单的方法调用
String name = sessionImplementor.getFactory()
.locateEntityPersister( YourEntityClass.class )
.getEntityName();
现在阅读AuditReader#getEntityName()
的java-doc,文档确实声明该方法应该返回null
,因为它无法确定实体名称,而方法签名指定它可以抛出a HibernateException
,没有文档说明为什么可以抛出该异常。
也就是说,当您调用AuditReader
的{{1}}实例尚未读取和缓存提供的对象,修订版本和标识符时,抛出该异常。这意味着如果您打开一个阅读器,获取实例,然后使用新的#getEntityName()
实例获取实体名称,您将收到此错误。
我添加了一个JIRA HHH-12373,以便解决java-doc误解。