Spring data jpa(java persistence API), Spring Data JPA是更大的Spring data系列的一部分,可以轻松实现基于JPA的存储库。此模块处理对基于JPA的数据访问层的增强支持。它使构建使用数据访问技术的Spring驱动应用程序变得更加容易。下面直接来介绍干货。
1、Spring-data-jpa的基本介绍
JPA诞生的缘由是为了整合第三方ORM框架,建立一种标准的方式,百度百科说是JDK为了实现ORM的天下归一,目前也是在按照这个方向发展,但是还没能完全实现。在ORM框架中,Hibernate是一支很大的部队,使用很广泛,也很方便,能力也很强,同时Hibernate也是和JPA整合的比较良好,我们可以认为JPA是标准,JPA几乎都是接口,实现都是Hibernate在做,宏观上面看,在JPA的统一之下Hibernate很良好的运行。
2、基本使用
2.1 CrudRepository接口
顾名思义,这个接口的功能就是帮助使用者完成各种各样的crud操作。
public interface CrudRepository<T, ID extends Serializable>
extends Repository<T, ID> {
<S extends T> S save(S entity);
T findOne(ID primaryKey);
Iterable<T> findAll();
Long count();
void delete(T entity);
boolean exists(ID primaryKey);
}
1、保存给定的实体(该实体对应的是数据库中的table,实体中的属性对应table中的colomn)
2、返回由给定id标识的实体。(主键)
3、返回所有实体
4、返回实体数量
5、删除给定的实体。
6、指示是否存在具有给定id的实体。
2.2 PagingAndSortingRepository
public interface PagingAndSortingRepository<T, ID extends Serializable>
extends CrudRepository<T, ID> {
Iterable<T> findAll(Sort sort);
Page<T> findAll(Pageable pageable);
}
PagingAndSortingRepository接口是Jpa提供的分页接口,Pageable类型在创建时,需要传入页码page、该页的最大item数量size,还可以传入一个Sort类型的对象,指定好升序降序以及排序字段(可传入多个排序字段),完成分页。
2.3 创建对应数据库表的DTO
下图是一张数据库表所对应的DTO(data transform object),id对应的是主键,@GeneratedValue对应的是主键的生成策略。GenerationType.IDENTITY的意思是主键由数据库自动生成(自增型),AUTO的意思是主键由程序生成。@Column指的是表中的字段名。
@Table(name = "partner")
public class PartnerDTO {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@Column(name = "partner_name")
private String partnerName;
@Column(name = "operator")
private String operator;
@Column(name = "password")
private String password;
@Column(name = "create_time")
private String createTime;
@Column(name = "partner_type")
private String partnerType;
@Column(name = "update_time")
private Timestamp updateTime;
@Column(name = "product_type")
private Integer productType;
@Column(name = "status")
private Integer status;
2.4 创建jpa的数据库访问对象Repository
这里的Repository和我们平常理解的DAO层是一个概念,和mybatis中叫它为mapper一样,在spring data jpa中我们叫它Repository。我们现在只需要创建一个接口,让它实现上述的CRUDRepository、PagingAndSortingRepository或者是JpaRepository中的一种。如下图所示:
public interface PartnerDao extends PagingAndSortingRepository<PartnerDTO, Long> {
List<PartnerDTO> findAllByStatusAndPartnerType(Integer status, String partnerType);
List<PartnerDTO> findAllByPartnerType(String type);
}
Java8以后,允许我们直接调用接口中的方法,不需要我们再额外提供实现类。现在我们可以在service层中调用这两个方法,jpa就会将方法翻译成语句对数据库进行CRUD操作。
2.5 @Query
使用 @Query 创建查询
@Query 注解的使用非常简单,只需在声明的方法上面标注该注解,同时提供一个 JP QL 查询语句即可,如下所示:
清单 16. 使用 @Query 提供自定义查询语句示例
public interface UserDao extends Repository<AccountInfo, Long> {
@Query("select a from AccountInfo a where a.accountId = ?1")
public AccountInfo findByAccountId(Long accountId);
@Query("select a from AccountInfo a where a.balance > ?1")
public Page<AccountInfo> findByBalanceGreaterThan(Integer balance, Pageable pageable);
}
很多开发者在创建 JP QL 时喜欢使用命名参数来代替位置编号,@Query 也对此提供了支持。JP QL 语句中通过": 变量"的格式来指定参数,同时在方法的参数前面使用 @Param 将方法参数与 JP QL 中的命名参数对应,示例如下:
清单 17. @Query 支持命名参数示例
public interface UserDao extends Repository<AccountInfo, Long> {
public AccountInfo save(AccountInfo accountInfo);
@Query("from AccountInfo a where a.accountId = :id")
public AccountInfo findByAccountId(@Param("id")Long accountId);
@Query("from AccountInfo a where a.balance > :balance")
public Page<AccountInfo> findByBalanceGreaterThan(@Param("balance")Integer balance, Pageable pageable);
}
此外,开发者也可以通过使用 @Query 来执行一个更新操作,为此,我们需要在使用 @Query 的同时,用 @Modifying 来将该操作标识为修改查询,这样框架最终会生成一个更新的操作,而非查询。如下所示:
清单 18. 使用 @Modifying 将查询标识为修改查询
@Modifying
@Query("update AccountInfo a set a.salary = ?1 where a.salary < ?2")
public int increaseSalary(int after, int before);
简单的Jpa使用就介绍到这儿了,下一篇文章会介绍在使用jpa过程遇到的一些问题,以及解决方式。
网友评论