如何重写Spring Data JPA存储库的基本方法?

时间:2018-07-27 10:36:42

标签: java spring hibernate spring-data-jpa

我有一些实体类型在保存时需要其他逻辑(确切地说,我想在保存时保存位置)。我不想使用任何特定于数据库的功能,例如触发器,因为我不确定将来将使用什么数据存储。

所以我想重写save()方法。

在Spring Data JPA文档中,我可以看到两种为存储库类提供自己的实现的方法:

  1. 扩展基本存储库类,并告诉Spring Data使用它。
  2. 使用实现类(PositionedRepository)定义一个接口(在我的情况下,我假设为PositionedRepositoryImpl)。

第一种方法的问题-我不想在所有存储库中实现它,只定位了两种实体类型。

第二种方法的问题-我无权访问基本存储库方法,因此除了位置计算之外,我还需要以某种方式构建通常由基本存储库提供的所有查询。

有什么方法可以仅针对特定存储库类型扩展基本存储库类吗?

3 个答案:

答案 0 :(得分:3)

不要在存储库本身中执行该逻辑。将存储库视为Java和数据库之间的愚蠢层。它只是将数据从一端传递到另一端。

相反,您应该在不同的层中处理这种情况。更聪明的一个。业务逻辑层。

请参见以下示例:

@Service
public class MyEntityService{

     private final MyEntityRepository myEntityRepository;
     private final OtherEntityRepository otherEntityRepository;

     @Autowired
     public MyEntityService(MyEntityRepository myEntityRepository, 
                          OtherEntityRepository otherEntityRepository){
         this.myEntityRepository = myEntityRepository;
         this.otherEntityRepository = otherEntityRepository;
     }

     public void save(MyEntity myEntity){
          // do stuff with otherEntityRepository
          myEntitiyRepository.save(myEntity);
     }
}

答案 1 :(得分:1)

作为第三个选项,您可以扩展实现SimpleJpaRepositoryJpaRepository的{​​{1}}。 这样,您可以受益于JpaSpecificationExecutor的默认实现,同时可以覆盖这些方法。

例如:

JpaRepository

作为第四个选项,您还可以定义自己的@Repository public class PositionedRepository extends SimpleJpaRepository<Positioned, Long> { @Override public Positioned save(Positioned positioned) { ... } } 方法,该方法在savePositioned()的幕后使用。

答案 2 :(得分:1)

您可以:

public class CustomJpaRepository<T, ID extends Serializable> extends SimpleJpaRepository<T, ID> {
  private final JpaEntityInformation<T, ?> entityInformationWrap;
  private final EntityManager emWrap;
  public CustomJpaRepository(JpaEntityInformation entityInformation, EntityManager entityManager) {
    super(entityInformation, entityManager);
    entityInformationWrap=entityInformation;
    emWrap=entityManager;
  }

  @Override
  public <S extends T> S save(S entity) {
    //doing
  }

}

然后在主类中添加:   @EnableJpaRepositories(repositoryBaseClass = CustomJpaRepository.class)