Spring Data MongoDB如何不使用@Version注解配置版本属性?
Spring Data MongoDB 无@Version注解配置乐观锁方案
Spring Data MongoDB提供两种不需要给POJO加@Version注解的方式配置乐观锁版本属性,完全不侵入你的POJO代码,不需要引入Spring Data MongoDB依赖:
1. 全局配置版本属性探测规则
通过自定义MongoMappingContext的属性识别逻辑,统一约定版本字段规则,比如指定所有名为version、类型为数值类型的字段自动识别为乐观锁版本字段:
@Configuration public class MongoCustomConfig extends AbstractMongoClientConfiguration { @Override protected String getDatabaseName() { return "your_database_name"; } @Bean @Override public MongoMappingContext mongoMappingContext() throws ClassNotFoundException { MongoMappingContext mappingContext = new MongoMappingContext(); // 注入你之前自定义的ConfigurableTypeInformationMapper mappingContext.setTypeInformationMapper(yourCustomTypeInformationMapper); // 重写持久化属性探测逻辑,自定义版本字段识别规则 mappingContext.setPersistentPropertyCreator((property, owner) -> new CachingMongoPersistentProperty(property, owner, mappingContext.getSimpleTypeHolder(), mappingContext) { @Override public boolean isVersionProperty() { // 自定义规则:字段名是version,且类型为Long/long时识别为版本字段 return "version".equals(getName()) && (getType() == Long.class || getType() == long.class); } } ); return mappingContext; } }
该方案适合所有实体遵循统一版本字段命名规则的场景,不需要修改任何POJO代码。
2. 针对指定实体手动配置版本属性
如果只有部分实体需要乐观锁,不需要全局生效,可以通过自定义Repository实现,手动指定实体的版本属性:
// 自定义Repository基类 public class CustomBaseMongoRepository<T, ID> extends SimpleMongoRepository<T, ID> { public CustomBaseMongoRepository(MongoEntityInformation<T, ID> entityInfo, MongoOperations mongoOperations) { // 手动构造带指定版本字段的实体元信息 super( MappingMongoEntityInformation.of(entityInfo.getJavaType()) .withVersionProperty("version", Long.class), mongoOperations ); } } // 启用自定义Repository @EnableMongoRepositories(repositoryBaseClass = CustomBaseMongoRepository.class) public class MongoConfig { // 其他配置 }
注意事项
- 两种方案都完全兼容你已配置的
ConfigurableTypeInformationMapper继承映射逻辑,无冲突 - 版本属性类型需符合Spring Data MongoDB规范:支持
Long/long、Integer/int、Short/short三类数值类型,推荐优先使用Long避免溢出 - 乐观锁触发逻辑与使用
@Version注解完全一致,更新时版本不匹配会抛出OptimisticLockingFailureException
内容的提问来源于stack exchange,提问作者evgenivanovi
相关产品推荐
相关产品推荐

