首页 > 其他分享 >如何在Spring Boot中使用Hibernate Natural ID

如何在Spring Boot中使用Hibernate Natural ID

时间:2023-06-15 12:36:08浏览次数:32  
标签:Hibernate Natural 袜子 Spring public productRepository tshirt T恤 ID

首先,让我们关注所需类的实现。完成所有这些后,我们将能够为具有自然ID的实体提供存储库。


用自然ID编写实体

让我们考虑以下具有自动生成ID和自然ID(code列)的实体。这只是一个使用一个自然ID的典型实体@NaturalId:


@实体
public  class  Product  implements  Serializable {
 
    private  static  final  long  serialVersionUID  =  1L ;
 
    @ID
    @GeneratedValue(策略 =  GenerationType。IDENTITY)
    私人 长 身份 ;
 
    私有 字符串 名称 ;
 
    @NaturalId(mutable  =  false)
    @Column(nullable  =  false,updatable  =  false,unique  =  true,length  =  50)
    私有 字符串 代码 ;
 
    // getter和setter
 
    @覆盖
    public  boolean  equals(Object  o){
        if(this  ==  o){
            返回 true ;
        }
        if(!(o  instanceof  Product)){
            返回 false ;
        }
        产品 naturalIdProduct  =(产品)o ;
        返回 对象。等于(引用代码(),naturalIdProduct。引用代码());
    }
 
    @覆盖
    public  int  hashCode(){
        返回 对象。hash(getCode());
    }
 
    @覆盖
    public  String  toString(){
        返回 “Product {”  +  “id =”  +  id  +  “,name =”  +  name  +  “,code =”  +  code  +  '}' ;
    }
}


编写NaturalRepository合同

我们首先编写一个名为的接口NaturalRepository。基本上,当我们想要微调存储库时,我们可以依赖  @NoRepositoryBean注释。在我们的例子中,我们想要用另外两个来丰富Spring Data方法库,  findBySimpleNaturalId()并且findByNaturalId() :


@NoRepositoryBean
public  interface  NaturalRepository < T,ID  extends  Serializable >  extends  JpaRepository < T,ID > {
 
    //当您的实体具有使用@NaturalId注释的单个字段时,请使用此方法
    可选< T >  findBySimpleNaturalId(ID  naturalId);
 
    //当您的实体具有多个使用@NaturalId注释的字段时,请使用此方法
    可选< T >  findByNaturalId(Map < String,Object >  naturalIds);        
}

编写NaturalRepository实现

此外,我们扩展了SimpleJpaRepository 类并实现了NaturalRepository。通过扩展,SimpleJpaRepository我们可以通过添加我们需要的方法来定制基本存储库。主要是,我们扩展了特定于持久性技术的存储库基类,并将此扩展用作存储库代理的自定义基类:


@Transactional(readOnly  =  true)
public  class  NaturalRepositoryImpl < T,ID  扩展 Serializable >
        扩展 SimpleJpaRepository < T,ID >  实现 NaturalRepository < T,ID > {
 
    private  final  EntityManager  entityManager ;
 
    公共 NaturalRepositoryImpl(JpaEntityInformation  entityInformation,
            EntityManager  entityManager){
        super(entityInformation,entityManager);
 
        这个。entityManager  =  entityManager ;
    }
 
    @覆盖
    public  Optional < T >  findBySimpleNaturalId(ID  naturalId){
 
        可选< T >  entity  =  entityManager。解包(会话。类)
                。bySimpleNaturalId(此。getDomainClass())
                。loadOptional(naturalId);
 
        回报 实体 ;
    }
 
    @覆盖
    public  Optional < T >  findByNaturalId(Map < String,Object >  naturalIds){
 
        NaturalIdLoadAccess < T >  loadAccess
                =  entityManager。解包(会话。类)。byNaturalId(此。getDomainClass());
        naturalIds。forEach(loadAccess :: using);
 
        return  loadAccess。loadOptional();
    }
 
}

将NaturalRepositoryImpl设置为基类

接下来,我们必须指示Spring Data依赖于我们的自定义存储库基类。在Java配置中,您可以repositoryBaseClass通过@EnableJpaRepositories注释使用该属性来执行此操作  :


@SpringBootApplication
@EnableJpaRepositories(repositoryBaseClass  =  NaturalRepositoryImpl。类)
公共 类 NaturalIdApplication {
    ...
}

让我们看看它是如何工作的

现在,让我们看看它是否按预期工作。首先,让我们定义ProductRepository:


@Repository
public  interface  ProductRepository < T,ID >  extends  NaturalRepository < Product,Long > {    
}

一个自然身份证

此外,让我们保存两个具有唯一代码(自然ID)的产品:


产品 tshirt  =  新 产品();

T恤。setName(“T-Shirt”);

T恤。setCode(“014-tshirt-2019”);

产品 袜子 =  新 产品();

袜子。setName(“袜子”);

袜子。setCode(“012-socks-2018”);

productRepository。保存(T 恤);

productRepository。保存(袜子);

最后,让我们通过它的自然ID 找到T-Shirt产品:


//这应该返回包装在Optional中的T恤产品

可选< Product >  tshirt  =  productRepository。findBySimpleNaturalId(“014-tshirt-2019”);

注意:productRepository.findById(Object id)如果要按自动生成的ID进行搜索,仍可以使用  。


更多自然ID

实体可以使用多个自然ID。例如,让我们假设code 我们旁边还有  sku自然ID:


@NaturalId(mutable  =  false)

@Column(nullable  =  false,updatable  =  false,unique  =  true)

私人 龙 sku ;

现在,当我们坚持我们的产品时,它们将如下所示:


产品 tshirt  =  新 产品();

T恤。setName(“T-Shirt”);

T恤。setCode(“014-tshirt-2019”);

T恤。setSku(1L);

产品 袜子 =  新 产品();

袜子。setName(“袜子”);

袜子。setCode(“012-socks-2018”);

袜子。setSku(2L);

productRepository。保存(T 恤);

productRepository。保存(袜子);

找到T恤产品可以这样做:


Map < String,Object >  ids  =  new  HashMap <>();

ids。put(“code”,“014-tshirt-2019”);

ids。put(“sku”,1L);

可选< Product >  tshirt  =  productRepository。findByNaturalId(ids);


标签:Hibernate,Natural,袜子,Spring,public,productRepository,tshirt,T恤,ID
From: https://blog.51cto.com/u_16145034/6486208

相关文章

  • 从 SpringApplication 认识 Spring 应用启动过程
    一、SpringApplication是什么?Spring应用的启动类。二、SpringApplication执行了什么?创建ApplicationContext实例ApplicationContext就是我们所说的容器实例。注册CommandLinePropertySourceCommandLinePropertySource的作用是将命令行参数输出为Spring属性。......
  • 解惑 spring 嵌套事务
    解惑spring嵌套事务/***@author王政*@date2006-11-24*/在所有使用spring的应用中,声明式事务管理可能是使用率最高的功能了,但是,从我观察到的情况看,绝大多数人并不能深刻理解事务声明中不同事务传播属性配置的的含义,让我们来看一下Trans......
  • 解析Spring内置作用域及其在实践中的应用
    摘要:本文详细解析了Spring的内置作用域,包括Singleton、Prototype、Request、Session、Application和WebSocket作用域,并通过实例讲解了它们在实际开发中的应用。本文分享自华为云社区《Spring高手之路4——深度解析Spring内置作用域及其在实践中的应用》,作者:砖业洋__。本文详细解析......
  • 详解spring事务属性
    Spring声明式事务让我们从复杂的事务处理中得到解脱。使得我们再也无需要去处理获得连接、关闭连接、事务提交和回滚等这些操作。再也无需要我们在与事务相关的方法中处理大量的try…catch…finally代码。我们在使用Spring声明式事务时,有一个非常重要的概念就是事务属性。事务......
  • 最近学习spring声明式事务小结
    在一些需要同时操作几个更新的业务逻辑中,而这几个更新又是互相关联的,也就是说我们希望它成功就一起成功,失败就一起失败。这样我们就需要使用事务。关于如何配置spring声明式事务就不说了,需要的人可以在网上找下,肯定会配置一个类似下面的bean<beanid="cao"class......
  • 使用Spring Boot和H2完全工作的原型
    我们在Spring中使用了很多H2,特别是用于单元测试。但是,我们可能希望拥有一个包含数据的全功能原型,而不是单元测试。H2是完美的候选者。它适用于Spring,与大多数数据库具有很强的语法兼容性,并提供用于检查数据的UI。想象一下面试任务的情景。您希望您的示例开箱即用,尽可能少的配置为审......
  • Mongodb - org.springframework.dao.DuplicateKeyException
    首先明确场景为mongodb,此异常在进行mongodb的插入操作时抛出,插入的主键已经存在。衍生场景,使用upsert时抛出,此处的包括了$set和$setOnInsert由于upsert非原子操作,如果在多线程环境下:线程A和线程B同时对数据库未存在的记录record1进行upsert,有可能会出现两个线程都判断为应该进行......
  • SpringBoot+druid+dynamic+clickhouse+mysql实现读写分离
    背景:clickhouse+mysql实现读写分离1.配置mysql2.安装clickhouse3.使用可视化工具连接clickhouse4.创建clickhouse的数据库并连接mysql5.SpringBoot+druid+dynamic配置多数据源实现读写分离一.背景由于系统数据量过大,查询条件自定义过多,mysql在查询时响应太慢,所以使用cli......
  • 顶奢好文:3W字,穿透Spring事务原理、源码,至少读10遍
    文章很长,且持续更新,建议收藏起来,慢慢读!疯狂创客圈总目录博客园版为您奉上珍贵的学习资源:免费赠送:《尼恩Java面试宝典》持续更新+史上最全+面试必备2000页+面试必备+大厂必备+涨薪必备免费赠送:《尼恩技术圣经+高并发系列PDF》,帮你实现技术自由,完成职业升级,薪......
  • springboot启动流程 (1) 流程概览
    本文将通过阅读源码方式分析SpringBoot应用的启动流程,不涉及Spring启动部分(有相应的文章介绍)。本文不会对各个流程做展开分析,后续会有文章介绍详细流程。SpringApplication类应用启动入口使用以下方式启动一个SpringBoot应用:@SpringBootApplicationpublicclassSpringBoo......