Spring Data JDBC中@Lock修饰findAll方法启动报错的原因与解决
问题原因
当你在自定义声明的findAll()方法上加@Lock注解时,Spring Data不会将其识别为对CrudRepository默认方法的覆盖,而是会把它当作派生查询方法处理。
派生查询的逻辑是通过拆解方法名来生成SQL,findAll会被解析为要查找SeatDTO中名为findAll的属性,但你的实体类里显然不存在这个属性,因此抛出PropertyReferenceException。而移除@Lock注解后,Spring Data会识别这是对默认方法的重写,直接使用默认实现,所以应用能正常启动。
解决方法
有两种可行的解决方式:
方式一:配合@Query显式声明查询语句
在findAll()方法上添加@Query注解,明确指定全表查询的JPQL语句,这样Spring Data会跳过派生查询的解析逻辑,直接执行你指定的查询并应用悲观读锁。代码示例:
public interface SeatDAO extends CrudRepository<SeatDTO, Integer> { @Lock(LockMode.PESSIMISTIC_READ) @Query("SELECT s FROM SeatDTO s") Collection<SeatDTO> findAll(); }
方式二:基于JpaRepository的替代实现(可选)
如果项目允许切换为JpaRepository(它继承自CrudRepository),同样可以通过配合@Query和@Lock来实现带锁的全表查询。如果接受Iterable作为返回类型,也可以直接复用JpaRepository的方法,但要加锁仍需显式声明带注解的方法,本质和方式一一致。
注意:悲观锁的生效依赖数据库支持(PostgreSQL完全支持),同时要确保SeatDTO实体类与数据库表的映射关系正确。
内容的提问来源于stack exchange,提问作者Kobi
相关产品推荐
相关产品推荐

