You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Spring Data Envers:如何将修订号作为实体的一部分获取

如何让Hibernate Envers实体始终持有最新修订号

你希望在保存或查询SomeEntity实体时,实体实例中能直接包含当前最新的修订号,尝试通过在实体字段上添加@RevisionNumber注解实现,但该方式无法生效,期望实现如下代码的效果:

@Entity
@Audited
class SomeEntity {
  @Id
  long id;

  String value;

  @RevisionNumber
  int revNum;
}

可行解决方案

方案1:通过Envers API手动获取并绑定最新修订号

Hibernate Envers的@RevisionNumber注解仅作用于审计实体(比如对应REVINFO表的实体),无法直接标注在业务实体字段上。你可以通过Envers提供的AuditReader工具类,手动查询指定实体的最新修订号并赋值给实体:

查询实体时同步获取修订号

当从数据库查询到SomeEntity实例后,调用API获取其最新修订版本号:

// 获取AuditReader实例
AuditReader auditReader = AuditReaderFactory.get(entityManager);

// 查询指定ID实体的最新修订号
Number latestRevNum = auditReader.getLatestRevisionNumber(SomeEntity.class, entityId);

// 将修订号设置到实体对象中
someEntity.setRevNum(latestRevNum.intValue());

保存实体后自动更新修订号

在实体持久化完成后,立即查询最新修订号并更新实体:

entityManager.persist(someEntity);
entityManager.flush(); // 确保实体已写入数据库,生成对应的审计记录

Number latestRevNum = auditReader.getLatestRevisionNumber(SomeEntity.class, someEntity.getId());
someEntity.setRevNum(latestRevNum.intValue());

方案2:通过Hibernate事件监听器自动维护修订号

如果不想每次手动调用API,可以通过Hibernate的事件监听机制,在实体保存/更新后自动查询并设置最新修订号:

  1. 自定义事件监听器:
public class RevisionNumberUpdateListener implements PostInsertEventListener, PostUpdateEventListener {

    @Override
    public void onPostInsert(PostInsertEvent event) {
        updateRevisionNumber(event.getEntity(), event.getSession());
    }

    @Override
    public void onPostUpdate(PostUpdateEvent event) {
        updateRevisionNumber(event.getEntity(), event.getSession());
    }

    private void updateRevisionNumber(Object entity, Session session) {
        if (entity instanceof SomeEntity) {
            SomeEntity someEntity = (SomeEntity) entity;
            AuditReader auditReader = AuditReaderFactory.get(session);
            Number latestRevNum = auditReader.getLatestRevisionNumber(SomeEntity.class, someEntity.getId());
            someEntity.setRevNum(latestRevNum.intValue());
            session.merge(someEntity);
        }
    }

    @Override
    public boolean requiresPostCommitHandling(EntityPersister persister) {
        return false;
    }
}
  1. 将监听器注册到Hibernate配置中:
    在persistence.xml或Spring Boot配置类中添加该监听器,确保Hibernate在实体保存/更新时触发对应的事件逻辑。

注意事项

  • @RevisionNumber是Envers用于标记审计实体修订号字段的注解,无法直接映射到业务实体,Envers不会自动维护业务实体中的该字段。
  • 使用事件监听器时,需注意避免循环触发更新事件(比如设置revNum后再次触发更新逻辑),可通过判断字段变更内容或添加标记位规避。

内容的提问来源于stack exchange,提问作者Oleksandr Cherniaiev

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.21 17:03:21