初入spring boot(五 )Spring Data JPA

  Spring Data JPA通过提供基于JPA的Repository极大地减少JPA作为数据访问方案的代码量。

1.定义数据访问层

使用Spring Data JPA建立数据访问层十分简单,只需定义一个继承JpaRepository的接口即可,接口如下:

1 @RepositoryRestResource(path = "people")
2 public interface PersonRepository extends JpaRepository<Person, Long> {
3
4     @RestResource(path = "nameStartsWith", rel = "nameStartsWith")
5     Person findByNameStartsWith(@Param("name")String name);
6
7 }

继承JpaRepository接口意味着我们默认已经有了下面的数据访问操作方法:

 1 @NoRepositoryBean
 2 public interface JpaRepository<T, ID extends Serializable> extends PagingAndSortingRepository<T, ID>, QueryByExampleExecutor<T> {
 3     List<T> findAll();
 4
 5     List<T> findAll(Sort var1);
 6
 7     List<T> findAll(Iterable<ID> var1);
 8
 9     <S extends T> List<S> save(Iterable<S> var1);
10
11     void flush();
12
13     <S extends T> S saveAndFlush(S var1);
14
15     void deleteInBatch(Iterable<T> var1);
16
17     void deleteAllInBatch();
18
19     T getOne(ID var1);
20
21     <S extends T> List<S> findAll(Example<S> var1);
22
23     <S extends T> List<S> findAll(Example<S> var1, Sort var2);
24 }

2.配置使用Spring Data JPA

在Spring环境中,使用Spring Data JPA可通过@EnableJpaRepositories注解来开启Spring Data JPA的支持,@EnableJpaRepositories接收的value参数用来扫描数据访问层所在包下的数据访问的接口定义。

 1 @Configuration
 2 @EnableJpaRepositories("com.test.dao")
 3 public class JpaConfiguration {
 4     @Bean
 5     public EntityManagerFactory entityManagerFactory(){
 6         //...
 7         return null;
 8     }
 9
10     //还需配置DataSource、PlatformTransactionManager等相关必须bean
11 }

3.定义查询方法

(1)根据属性名查询

  1)常规查询。根据属性名来定义查询方法

 1 public interface PersonRepository extends CustomRepository<Person, Long> {
 2
 3     /**
 4      * 通过名字相等查询,参数name
 5      * 相当于JPQL:select p from Person p where p.name=?
 6      */
 7     List<Person> findByName(String name);
 8
 9     /**
10      * 通过名字like查询,参数为name
11      * 相当于JPQL:select p from Person p where p.name like ?
12      */
13     List<Person> findByNameLike(String name);
14
15     /**
16      * 通过名字和地址查询,参数为name和address
17      * 相当于JPQL:select p from Person p where p.name = ? and p.address = ?
18      */
19     List<Pserson> findByNameAndAddress(String name,String address);
20 }

  从代码可以看出,这里使用了findBy、like、And这样的关键字。其中findBy可以用find、read、readBy、query、queryBy、get、getBy来代替。

2)限制结果数量。结果数量是用top和first关键字来实现的:\

 1 public interface PersonRepository extends CustomRepository<Person, Long> {
 2
 3     /**
 4      * 获取查询条件的前10条数据
 5      * 通过名字相等查询,参数name
 6      * 相当于JPQL:select p from Person p where p.name=?
 7      */
 8     List<Person> findFirst10ByName(String name);
 9
10     /**
11      * 获取查询条件的前10条数据
12      * 通过名字like查询,参数为name
13      * 相当于JPQL:select p from Person p where p.name like ?
14      */
15     List<Person> findTop10ByNameLike(String name);
16
17 }

(2)使用JPA的NamedQuery查询

Spring Data JPA支持用JPA的NameQuery来定义查询方法,即一个名称映射一个查询语句。

 1 @Entity
 2 @NamedQuery(name = "Person.withNameAndAddressNamedQuery",
 3 query = "select p from Person p where p.name=? and address=?")
 4 public class Person {
 5     @Id
 6     @GeneratedValue
 7     private Long id;
 8
 9     private String name;
10
11     private Integer age;
12
13     private String address;
14
15
16
17     public Person() {
18         super();
19     }
20
21     public Long getId() {
22         return id;
23     }
24     public void setId(Long id) {
25         this.id = id;
26     }
27     public String getName() {
28         return name;
29     }
30     public void setName(String name) {
31         this.name = name;
32     }
33     public Integer getAge() {
34         return age;
35     }
36     public void setAge(Integer age) {
37         this.age = age;
38     }
39     public String getAddress() {
40         return address;
41     }
42     public void setAddress(String address) {
43         this.address = address;
44     }
45
46
47 }

这时在接口里使用 Person withNameAndAddressNamedQuery(String name,String address); 时是使用的在上面定义的sql语句,而不是根据方法名称查询

(3)使用@Query查询

  1)使用命名参数,使用名称来匹配查询参数。Spring Data JPA还支持@Query注解在接口的方法上实现查询

    @Query("select p from Person p where p.name= :name and p.address= :address")
    Person withNameAndAddressQuery(@Param("name")String name,@Param("address")String address);

  2)使用参数索引

    @Query("select p from Person p where p.name= ? and p.address= ?")
    Person withNameAndAddressNamedQuery(String name,String address);

  3)更新查询。Spring Data JPA支持@Modifying和@Query注解组合事件来更新查询

  4)JPA提供了基于准则查询方式,即Criteria查询。而Spring Data JPA提供了一个Specification(规范)接口让我们可以更方便的构造准则查询,Specification接口定义了一个toPredicate方法用来构造查询条件。

4.自定义Repository的实现

spring data提供了CrudRepository和PagingAndSortingRepository,spring data JPA也提供了JpaRepository。如果我们想把自己常用的数据库操作封装起来,像JpaRepository一样提供给我们领域类的Repository接口使用,应该怎么做?

  1)定义自定义Repository接口

@NoRepositoryBean
public interface CustomRepository<T, ID extends Serializable>extends JpaRepository<T, ID> ,JpaSpecificationExecutor<T>{

    Page<T> findByAuto(T example,Pageable pageable);

}1. @NoRepositoryBean指明当前这个接口不是我们领域类的接口(例如PersonRepository)2. 我们自定义的Repository实现JpaRepository接口(这里也可以实现PagingAndSortingRepository接口,看具体需求),具备JpaRepository的能力3. 要定义的数据操作方法在接口中的定义

  2)定义接口实现

public class CustomRepositoryImpl <T, ID extends Serializable>
                    extends SimpleJpaRepository<T, ID>  implements CustomRepository<T,ID> {

    private final EntityManager entityManager;

    public CustomRepositoryImpl(Class<T> domainClass, EntityManager entityManager) {
        super(domainClass, entityManager);
        this.entityManager = entityManager;
    }

    @Override
    public Page<T> findByAuto(T example, Pageable pageable) {
        return findAll(byAuto(entityManager, example),pageable);  //在此处定义数据访问操作
} }

1. 首先要实现CustomRepository接口,继承SimpleJpaRepository类让我们可以使用其提供的方法(例如:findAll)2. 让数据库操作方法中可以使用entityManager3. CustomRepositoryImpl的构造函数,需当前处理的领域类类型和entityManager作为构造函数

  3)自定义RepositoryFactoryBean。自定义JpaRepositoryFactoryBean替代默认RepositoryFactoryBean,我们会获得一个RepositoryFactory,RepositoryFactory将会注册我们自定义的Repository的实现

public class CustomRepositoryFactoryBean<T extends JpaRepository<S, ID>, S, ID extends Serializable>
        extends JpaRepositoryFactoryBean<T, S, ID> {// 1

    @Override
    protected RepositoryFactorySupport createRepositoryFactory(EntityManager entityManager) {// 2
        return new CustomRepositoryFactory(entityManager);  
    }

    private static class CustomRepositoryFactory extends JpaRepositoryFactory {// 3

        public CustomRepositoryFactory(EntityManager entityManager) {
            super(entityManager);
        }

        @Override
        @SuppressWarnings({"unchecked"})
        protected <T, ID extends Serializable> SimpleJpaRepository<?, ?> getTargetRepository(
                RepositoryInformation information, EntityManager entityManager) {// 4
            return new CustomRepositoryImpl<T, ID>((Class<T>) information.getDomainType(), entityManager);

        }

        @Override
        protected Class<?> getRepositoryBaseClass(RepositoryMetadata metadata) {// 5
            return CustomRepositoryImpl.class;
        }
    }
}

1. 自定义RepositoryFactoryBean,继承JpaRepositoryFactoryBean2. 重写createRepositoryFactory方法,用当前的CustomRepositoryFactory创建实例3. 创建CustomRepositoryFactory,并继承JpaRepositoryFactory4. 重写getTargetRepository方法,获得当前自定义的Repository实现5. 重写getRepositoryBaseClass,获得当前自定义的Repository实现的类型

4)开启自定义支持使用@EnableJpaRepositories的repositoryFactoryBeanClass来指定FactoryBean即可

@SpringBootApplication
@EnableJpaRepositories(repositoryFactoryBeanClass = CustomRepositoryFactoryBean.class)
public class TestApplication {
    @Autowired
    PersonRepository personRepository;

    public static void main(String[] args) {
        SpringApplication.run(Ch82Application.class, args);

    }
}
时间: 2024-10-12 10:40:58

初入spring boot(五 )Spring Data JPA的相关文章

spring boot系列(五)spring boot 配置spring data jpa (查询方法)

接着上面spring boot系列(四)spring boot 配置spring data jpa 保存修改方法继续做查询的测试: 1 创建UserInfo实体类,代码和https://www.cnblogs.com/kxm87/p/9273555.html中的一样. 2 创建数据库操作类相当于dao层,主要创建一个接口UserRepository,继承JpaRepository接口即可.本代码中主要都是自定义方法. 使用findXX 或者countXX(这两个不用编写sql,jpa会自动生成)

spring boot 中Spring data jpa数据库表字段命名策略

spring boot 中Spring data jpa命名策略 数据库,表字段命名是驼峰命名法(UserID),Spring data jpa 自动更新之后是 user_id, 表字段不对照, Spring data jpa基于Hibernate5.0 application.properties 写法 1.无修改命名 spring.jpa.hibernate.naming.physical-strategy=org.hibernate.boot.model.naming.PhysicalNa

Spring Boot 整合Spring Data JPA

Spring Boot整合Spring Data JPA 1)加入依赖 <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-jpa</artifactId> </dependency> <dependency> <groupId>mysql</groupId> &l

spring boot 集成 Mybatis,JPA

相对应MyBatis, JPA可能大家会比较陌生,它并不是一个框架,而是一组规范,其使用跟Hibernate 差不多,原理层面的东西就不多讲了,主要的是应用. Mybatis就不多说了,SSM这三个框架现在基本上都是基本框架了. MyBatis 与 Spring boot 整合时除了添加必要的jar, 插件.在applicatoin.properties/application.yml 中添加相应的配置. 注意的一点就是在启动类中记得添加@MapperScan("com.spSystem.map

spring boot(spring)

一:spring的介绍 Spring是一个开源框架,它由Rod Johnson创建.它是为了解决企业应用开发的复杂性而创建的. 它是一个容器框架,用来装javabean(java对象),中间层框架(万能胶)可以起一个连接作用,比如说把Struts和hibernate粘合在一起运用.简单来说,Spring是一个轻量级的控制反转(IoC)和面向切面(AOP)的容器框架. 二:spring boot 1. Spring Boot简介Spring 诞生时是 Java 企业版(Java Enterpris

spring boot与spring mvc的区别是什么?

Spring 框架就像一个家族,有众多衍生产品例如 boot.security.jpa等等.但他们的基础都是Spring 的 ioc和 aop ioc 提供了依赖注入的容器 aop ,解决了面向横切面的编程,然后在此两者的基础上实现了其他延伸产品的高级功能.Spring MVC是基于 Servlet 的一个 MVC 框架 主要解决 WEB 开发的问题,因为 Spring 的配置非常复杂,各种XML. JavaConfig.hin处理起来比较繁琐.于是为了简化开发者的使用,从而创造性地推出了Spr

Spring Boot集成Spring Scheduler和Quartz Scheduler

本文介绍了Spring Boot集成Spring Scheduler和Quartz Scheduler的基础知识,利用ShedLock解决Spring Scheduler多实例运行冲突,介绍了Quartz ScheduleBuilder.Calendar,介绍了动态创建Quartz Job的方法. GitHub源码 Spring Scheduler Spring Framework提供了简单.易用的Job调度框架Spring Scheduler. 示例 在Spring Boot中,只需两步即可启

eclipse安装spring boot插件spring tool suite

进行spring cloud的学习,要安装spring boot 的spring -tool-suite插件,我在第一次安装时,由于操作不当,两天才完全安装好,真的是要命了,感觉自己蠢死!下面就自己踩过坑以及一些小窍门和大家分享一下. 安装方法:(我使用的是eclipse ,所以就拿eclipse举例了) 提示:安装时,网速不好的话过程会比较漫长,所以最好是选择一个网络好一点的地方进行安装. 方法1.可以自己在eclipse目录:help-->Eclipse Marketplace 下的Sear

Spring、Spring Boot、Spring Frame、Spring MVC的区别

Spring框架就像一个厂商,其下有很多产品,如Spring Boot.Spring Frame.Spring Cloud等等. Spring Boot用于快速.方便.简单的搭建一个Spring项目.之所以说它快速.方便.简单,是因为Spring Boot融合看来很多第三方库,提供了配置这些库及本身的一些简单的方式,从而进行了简化,避免了我们自己对包的导入和繁琐的XML文件配置.我们来看下官方文档. 我们可以看到Spring内嵌了一些serverse等容器,通过Spring Boot的配置,可以

基于 spring boot 和 spring mvc 的快速开发框架 summer-boot

summer-boot 详细介绍此项目目的在于提供一个简化.简洁.迅速的开发架构. 它是基于spring boot和spring mvc高度封装的快速开发框架,数据库操作工具summerDao是基于jdbcTemplate高度封装简化.拥有超级简单实用的ORM功能.和ibatis一样强大但更简单.无需映射配置的dao工具,视图层采用的是Rythm(最简洁的java模板引擎.可以用它来做web项目.微服务.socket服务,且同一套代码同时兼容这三种方式. 它的优点如下:基本建立在spring一套