Spring Data概述

  - Spring Data : Spring 的一个子项目。用于简化数据库访问,支持NoSQL 和 关系数据存储。其主要目标是使数据库的访问变得方便快捷。

  - SpringData 项目所支持 NoSQL 存储: MongoDB (文档数据库)、 Neo4j(图形数据库)、 Redis(键/值存储)、 Hbase(列族数据库)

  - SpringData 项目所支持的关系数据存储技术: JDBC、 JPA

  - JPA Spring Data : 致力于减少数据访问层 (DAO) 的开发量. 开发者唯一要做的,就只是声明持久层的接口,其他都交给 Spring Data JPA 来帮你完成!

  - 框架怎么可能代替开发者实现业务逻辑呢?比如:当有一个 UserDao.findUserById() 这样一个方法声明,大致应该能判断出这是根据给定条件的 ID 查询出满足条件的 User 对象。

   Spring Data JPA 做的便是规范方法的名字,根据符合规范的名字来确定方法需要实现什么样的逻辑。

Spring Data Jpa HelloWorld

  - 使用 Spring Data JPA 进行持久层开发需要的四个步骤:

    1、 配置 Spring 整合 JPA

    2、 在 Spring 配置文件中配置 Spring Data,让 Spring 为声明的接口创建代理对象。配置了 <jpa:repositories> 后,Spring 初始化容器时将会扫描 base-package  指定的包目录及其子目录,

      为继承 Repository 或其子接口的接口创建代理对象,并将代理对象注册为 Spring Bean,业务层便可以通过 Spring 自动封装的特性来直接使用该对象。

    3、声明持久层的接口,该接口继承  Repository,Repository 是一个标记型接口,它不包含任何方法,如必要,Spring Data 可实现 Repository 其他子接口,其中定义了一些常用的增删改查,以及分页相关的方法。

    4、在接口中声明需要的方法。Spring Data 将根据给定的策略(具体策略稍后讲解)来为其生成实现代码。

  - 搭建环境:

    1、同时下载 Spring Data Commons 和 Spring Data JPA 两个发布包:

      > Commons 是 Spring Data 的基础包

      > 并把相关的依赖 JAR 文件加入到 CLASSPATH 中

    2、在 Spring 的配置文件中配置 Spring Data:

      

  - 示例代码:

      

Repository 接口概述

  - Repository 接口是 Spring Data 的一个核心接口,它不提供任何方法,开发者需要在自己定义的接口中声明需要的方法 ,public interface Repository<T, ID extends Serializable> { }

  - Spring Data可以让我们只定义接口,只要遵循 Spring Data的规范,就无需写实现类。

  - 与继承 Repository 等价的一种方式,就是在持久层接口上使用 @RepositoryDefinition 注解,并为其指定 domainClass 和 idClass 属性。两种方式是完全等价的

  - Repository 的子接口:

    > 基础的 Repository 提供了最基本的数据访问功能,其几个子接口则扩展了一些功能。它们的继承关系如下:

      >> Repository: 仅仅是一个标识,表明任何继承它的均为仓库接口类

      >> CrudRepository: 继承 Repository,实现了一组 CRUD 相关的方法

      >> PagingAndSortingRepository: 继承 CrudRepository,实现了一组分页排序相关的方法

      >> JpaRepository: 继承 PagingAndSortingRepository,实现一组 JPA 规范相关的方法

      >> 自定义的 XxxxRepository 需要继承 JpaRepository,这样的 XxxxRepository 接口就具备了通用的数据访问控制层的能力。

      >> JpaSpecificationExecutor: 不属于Repository体系,实现一组 JPA Criteria 查询相关的方法

SpringData 方法定义规范

  - 简单条件查询:

    > 简单条件查询: 查询某一个实体类或者集合

    > 按照 Spring Data 的规范,查询方法以 find | read | get 开头, 涉及条件查询时,条件的属性用条件关键字连接,要注意的是:条件属性以首字母大写。

    > 例如:定义一个 Entity 实体类

         class User{

            private String firstName;

            private String lastName;

         }      

      >> 使用And条件连接时,应这样写: findByLastNameAndFirstName(String lastName,String firstName);

      >> 条件的属性名称与个数要与参数的位置与个数一一对应

  - 支持的关键字

    > 直接在接口中定义查询方法,如果是符合规范的,可以不用写实现,目前支持的关键字写法如下:

      

      

  - 查询方法解析流程

    > 假如创建如下的查询:findByUserDepUuid(),框架在解析该方法时,首先剔除 findBy,然后对剩下的属性进行解析,假设查询实体为Doc:

      >> 先判断 userDepUuid (根据 POJO 规范,首字母变为小写)是否为查询实体的一个属性,如果是,则表示根据该属性进行查询;如果没有该属性,继续第二步;

      >> 从右往左截取第一个大写字母开头的字符串(此处为Uuid),然后检查剩下的字符串是否为查询实体的一个属性,如果是,则表示根据该属性进行查询;如果没有该属性,则重复第二步,继续从右往左截取;最后假设 user 为查询实体的一个属性;

      >> 接着处理剩下部分(DepUuid),先判断 user 所对应的类型是否有depUuid属性,如果有,则表示该方法最终是根据 “ Doc.user.depUuid” 的取值进行查询;否则继续按照步骤 2 的规则从右往左截取,最终表示根据 “Doc.user.dep.uuid” 的值进行查询。

      >> 可能会存在一种特殊情况,比如 Doc包含一个 user 的属性,也有一个 userDep 属性,此时会存在混淆。可以明确在属性之间加上 "_" 以显式表达意图,比如 "findByUser_DepUuid()" 或者 "findByUserDep_uuid()"

    > 特殊的参数: 还可以直接在方法的参数上加入分页或排序的参数,比如:

      >> Page<UserModel> findByName(String name, Pageable pageable);

      >> List<UserModel> findByName(String name, Sort sort);

使用 @Query 注解

  - 使用@Query自定义查询

    > 这种查询可以声明在 Repository 方法中,摆脱像命名查询那样的约束,将查询直接在相应的接口方法中声明,结构更为清晰,这是 Spring data 的特有实现。

      

  - 索引参数与命名参数

    > 索引参数如下所示,索引值从1开始,查询中 ”?X” 个数需要与方法定义的参数个数相一致,并且顺序也要一致

    > 命名参数(推荐使用这种方式):可以定义好参数名,赋值时采用@Param("参数名"),而不用管顺序。

      

    > 如果是 @Query 中有 LIKE 关键字,后面的参数需要前面或者后面加 %,这样在传递参数值的时候就可以不加 %:

      >> @Query("select o from UserModel o where o.name like ?1%")

         public List<UserModel> findByUuidOrAge(String name);

      >> @Query("select o from UserModel o where o.name like %?1")

        public List<UserModel> findByUuidOrAge(String name);

      >> @Query("select o from UserModel o where o.name like %?1%")   

        public List<UserModel> findByUuidOrAge(String name);

  - 用@Query来指定本地查询

    > 还可以使用@Query来指定本地查询,只要设置nativeQuery为true,比如:

      >> @Query(value="select * from tbl_user where name like %?1" ,nativeQuery=true)

         public List<UserModel> findByUuidOrAge(String name);

@Modifying 注解和事务

  - @Query 与 @Modifying 执行更新操作

    > @Query 与 @Modifying 这两个 annotation一起声明,可定义个性化更新操作,例如只涉及某些字段更新时最为常用,示例如下:

      

    > 注意:

      >> 方法的返回值应该是 int,表示更新语句所影响的行数

      >> 在调用的地方必须加事务,没有事务不能正常执行

事务

  - Spring Data 提供了默认的事务处理方式,即所有的查询均声明为只读事务。

  - 对于自定义的方法,如需改变 Spring Data 提供的事务默认方式,可以在方法上注解 @Transactional 声明

  - 进行多个 Repository 操作时,也应该使它们在同一个事务中处理,按照分层架构的思想,这部分属于业务逻辑层,因此,需要在 Service 层实现对多个 Repository 的调用,并在相应的方法上声明事务。

CrudRepository 接口

  - CrudRepository

    > CrudRepository 接口提供了最基本的对实体类的添删改查操作 :

      >> T save(T entity);//保存单个实体

      >> Iterable<T> save(Iterable<? extends T> entities);//保存集合

      >> T findOne(ID id);//根据id查找实体

      >> boolean exists(ID id);//根据id判断实体是否存在

      >> Iterable<T> findAll();//查询所有实体,不用或慎用!

      >> long count();//查询实体数量

      >> void delete(ID id);//根据Id删除实体

      >> void delete(T entity);//删除一个实体

      >> void delete(Iterable<? extends T> entities);//删除一个实体的集合

      >> void deleteAll();//删除所有实体,不用或慎用!

PagingAndSortingRepository接口

  - PagingAndSortingRepository

    > 该接口提供了分页与排序功能 :

      >> Iterable<T> findAll(Sort sort); //排序

      >> Page<T> findAll(Pageable pageable); //分页查询(含排序功能)

JpaRepository接口

  - JpaRepository

    > 该接口提供了JPA的相关功能

      >> List<T> findAll(); //查找所有实体

      >> List<T> findAll(Sort sort); //排序、查找所有实体

      >> List<T> save(Iterable<? extends T> entities);//保存集合

      >> void flush();//执行缓存与数据库同步

      >> T saveAndFlush(T entity);//强制执行持久化

      >> void deleteInBatch(Iterable<T> entities);//删除一个实体集合

JpaSpecificationExecutor接口

  - JpaSpecificationExecutor

    > 不属于Repository体系,实现一组 JPA Criteria 查询相关的方法

      

    > Specification:封装 JPA Criteria 查询条件。通常使用匿名内部类的方式来创建该接口的对象

自定义 Repository 方法

  - 为某一个 Repository 上添加自定义方法

    > 步骤:

      1、 定义一个接口: 声明要添加的, 并自实现的方法

      2、 提供该接口的实现类: 类名需在要声明的 Repository 后添加 Impl, 并实现方法

      3、 声明 Repository 接口, 并继承 1) 声明的接口

      4、 使用.

      >>  注意: 默认情况下, Spring Data 会在 base-package 中查找 "接口名Impl" 作为实现类. 也可以通过 repository-impl-postfix 声明后缀.

  - 为所有的 Repository 都添加自实现的方法

    > 步骤:

      1、声明一个接口, 在该接口中声明需要自定义的方法, 且该接口需要继承 Spring Data 的 Repository.

      2、提供 1) 所声明的接口的实现类. 且继承 SimpleJpaRepository, 并提供方法的实现

      3、定义 JpaRepositoryFactoryBean 的实现类, 使其生成 1) 定义的接口实现类的对象

      4、修改 <jpa:repositories /> 节点的 factory-class 属性指向 3) 的全类名

      >> 注意: 全局的扩展实现类不要用 Imp 作为后缀名, 或为全局扩展接口添加 @NoRepositoryBean 注解告知  Spring Data: Spring Data 不把其作为 Repository

JavaEE高级-Spring Data学习笔记的更多相关文章

  1. JavaEE高级-通用Mapper学习笔记

    通用 Mapper 笔记 1 引入 1.1作用 替我们生成常用增删改查操作的 SQL 语句. 1.2代码官方发布地址 https://gitee.com/free https://gitee.com/ ...

  2. SpringBoot + Spring Security 学习笔记(三)实现图片验证码认证

    整体实现逻辑 前端在登录页面时,自动从后台获取最新的验证码图片 服务器接收获取生成验证码请求,生成验证码和对应的图片,图片响应回前端,验证码保存一份到服务器的 session 中 前端用户登录时携带当 ...

  3. Spring框架学习笔记(1)

    Spring 框架学习笔记(1) 一.简介 Rod Johnson(spring之父) Spring是分层的Java SE/EE应用 full-stack(服务端的全栈)轻量级(跟EJB比)开源框架, ...

  4. JavaEE精英进阶课学习笔记《博学谷》

    JavaEE精英进阶课学习笔记<博学谷> 第1章 亿可控系统分析与设计 学习目标 了解物联网应用领域及发展现状 能够说出亿可控的核心功能 能够画出亿可控的系统架构图 能够完成亿可控环境的准 ...

  5. Spring MVC 学习笔记一 HelloWorld

    Spring MVC 学习笔记一 HelloWorld Spring MVC 的使用可以按照以下步骤进行(使用Eclipse): 加入JAR包 在web.xml中配置DispatcherServlet ...

  6. SpringBoot + Spring Security 学习笔记(五)实现短信验证码+登录功能

    在 Spring Security 中基于表单的认证模式,默认就是密码帐号登录认证,那么对于短信验证码+登录的方式,Spring Security 没有现成的接口可以使用,所以需要自己的封装一个类似的 ...

  7. Spring框架学习笔记(5)——Spring Boot创建与使用

    Spring Boot可以更为方便地搭建一个Web系统,之后服务器上部署也较为方便 创建Spring boot项目 1. 使用IDEA创建项目 2. 修改groupid和artifact 3. 一路n ...

  8. Spring框架学习笔记(8)——spring boot+mybatis plus+mysql项目环境搭建

    之前写的那篇Spring框架学习笔记(5)--Spring Boot创建与使用,发现有多小细节没有提及,,正好现在又学习了mybatis plus这款框架,打算重新整理一遍,并将细节说清楚 1.通过I ...

  9. Spring Boot 学习笔记(六) 整合 RESTful 参数传递

    Spring Boot 学习笔记 源码地址 Spring Boot 学习笔记(一) hello world Spring Boot 学习笔记(二) 整合 log4j2 Spring Boot 学习笔记 ...

随机推荐

  1. 取值函数(getter)和存值函数(setter)

    todo get和set关键字

  2. python学习之路(24)

    访问限制 在Class内部,可以有属性和方法,而外部代码可以通过直接调用实例变量的方法来操作数据,这样,就隐藏了内部的复杂逻辑. 但是,从前面Student类的定义来看,外部代码还是可以自由地修改一个 ...

  3. 安装mariadb报错: Job for mariadb.service failed because the control process exited with error code. See "systemctl status mariadb.service" and "journalctl -xe" for details.

    卸载和删除都使用过了,没有起到效果,然后用了如下的方案,进行解决: CentOS 从 Yum 源安装配置 Mariadb 2017.03.01 WangYan 学习笔记  热度 7℃ 一.安装 Mar ...

  4. Spring boot 自定义一个starter pom

    用过springboot的自动配置会觉得非常方便,我们完全可以自己写一个starter pom,这样不仅可以有自动配置功能,而且具有更通用的的耦合度低的配置, 新建一个starter的maven项目, ...

  5. Android下Native的so编译:使用cmakelists.txt

    android studio的CMakeLists.txt写好后,在Studio中编译没问题,在命令编译时则需要配置很多参数才能成功 示例CMakeLists.txt文件: cmake_minimum ...

  6. cocos2dx基础篇(20) 扩展动作CCGridAction

    [3.x]     (1)去掉"CC" [CCGridAction] CCGridAction有两个子类:CCGrid3DAction.CCTiledGrid3DAction.而我 ...

  7. IP地址相关运算(如VLSM,超网汇总)

    1.根据IP地址+子网掩码算出IP地址所在的网段(网络号) 例子: IP地址192.168.10.33,子网掩码为:255.255.255.240 (/28) ,写出所在的网络号 1.得出子网的块大小 ...

  8. 【linux开发】apt源设置

    不同的网络状况连接以下源的速度不同, 建议在添加前手动验证以下源的连接速度(ping下就行),选择最快的源可以节省大批下载时间. 首先备份源列表: sudo cp /etc/apt/sources.l ...

  9. mysql先分组,然后取每个分组中的第2大的记录

    文章参考http://www.xaprb.com/blog/2006/12/07/how-to-select-the-firstleastmax-row-per-group-in-sql/ 首先建表: ...

  10. 刘铁猛-深入浅出WPF-系列资源汇总

    首先奉上原作者刘铁猛博客地址:http://www.cnblogs.com/prism/ 作者讲的很不错,没有之一,另外作者出了一本书,希望大家支持. 送上全套高清晰视频教程(我注册了3个51cto的 ...