Spring 对 JPA 的支持已经非常强大,开发者只需关心核心业务逻辑的实现代码,无需过多关注 EntityManager 的创建、事务处理等 JPA 相关的处理。Spring Data JPA更是能够根据方法名字自动实现持久层。

目标

这次我们的目标还是实现前面几节的功能,即对Category的数据层操作。完整和的代码结构:

首先添加实体类Category.java

Entity
@Table(name = "Category")
public class Category implements Serializable {
@Override
public String toString() {
return "id="+id+" name="+name;
} private Integer id; @Id
public Integer getId() {
return id;
} public void setId(Integer id) {
this.id = id;
} private String name; public String getName() {
return name;
} public void setName(String name) {
this.name = name;
}
}

  

引入JPA

JPA 规范要求,配置文件必须命名为 persistence.xml,并存在于类路径下的 META-INF 目录中。该文件通常包含了初始化 JPA 引擎所需的全部信息。Spring 提供的 LocalContainerEntityManagerFactoryBean 提供了非常灵活的配置,persistence.xml 中的信息都可以在此以属性注入的方式提供。

<?xml version="1.0" encoding="UTF-8"?>
<persistence xmlns="http://java.sun.com/xml/ns/persistence" version="2.0">
<persistence-unit name="category" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<class>demoJPA.entity.Category</class>
<properties>
<property name="hibernate.connection.driver_class" value="com.mysql.jdbc.Driver"/>
<property name="hibernate.connection.url" value="jdbc:mysql://localhost:3306/store"/>
<property name="hibernate.connection.username" value="root"/>
<property name="hibernate.connection.password" value="root"/>
<property name="hibernate.dialect" value="org.hibernate.dialect.MySQL5Dialect"/>
<property name="hibernate.show_sql" value="true"/>
<property name="hibernate.format_sql" value="true"/>
<property name="hibernate.use_sql_comments" value="false"/>
<property name="hibernate.hbm2ddl.auto" value="update"/>
</properties>
</persistence-unit>
</persistence>

  

实现数据持久层

接下来到了最核心的部分,就是对于数据持久层的支持。使用 Spring Data JPA 进行持久层开发大致需要的三个步骤:

1.首先引入依赖,这里主要用到spring data commons和spring data jpa两个包。

        <dependency>
<groupId>org.springframework.data</groupId>
<artifactId>spring-data-commons</artifactId>
<version>1.13.3.RELEASE</version>
</dependency> <dependency>
<groupId>org.springframework.data</groupId>
<artifactId>spring-data-jpa</artifactId>
<version>1.11.3.RELEASE</version>
</dependency>

完整的pom:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion> <groupId>DemoStore</groupId>
<artifactId>DemoJPA</artifactId>
<version>1.0-SNAPSHOT</version>
<properties>
<hibernate.version>3.5.6-Final</hibernate.version>
<hibernate.annotations.version>5.0.1.Final</hibernate.annotations.version>
</properties>
<dependencies>
<!-- https://mvnrepository.com/artifact/org.springframework.data/spring-data-commons -->
<dependency>
<groupId>org.springframework.data</groupId>
<artifactId>spring-data-commons</artifactId>
<version>1.13.3.RELEASE</version>
</dependency> <dependency>
<groupId>org.springframework.data</groupId>
<artifactId>spring-data-jpa</artifactId>
<version>1.11.3.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-test</artifactId>
<version>4.3.5.RELEASE</version>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.30</version>
</dependency>
<!-- hibernate相关项目依赖 start -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-core</artifactId>
<version>${hibernate.version}</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<version>${hibernate.version}</version>
</dependency>
<dependency>
<groupId>org.hibernate.common</groupId>
<artifactId>hibernate-commons-annotations</artifactId>
<version>${hibernate.annotations.version}</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.hibernate.javax.persistence/hibernate-jpa-2.0-api -->
<dependency>
<groupId>org.hibernate.javax.persistence</groupId>
<artifactId>hibernate-jpa-2.0-api</artifactId>
<version>1.0.1.Final</version>
</dependency> <!-- hibernate相关项目依赖 end --> </dependencies> </project>

  

2.声明持久层接口 CategoryDao继承 Repository 接口。Spring Data JPA 在后台为持久层接口创建代理对象时,会解析方法名字,并自动实现相应的功能。

public interface CategoryDao extends Repository<Category, Integer> {
void save(Category category); Iterable<Category> findAll(); long count(); void delete(int id); }

  

3.在 Spring 配置文件中增加一行声明,让 Spring 为声明的接口创建代理对象。配置了 <jpa:repositories> 后,Spring 初始化容器时将会扫描 base-package 指定的包目录及其子目录,为继承 Repository 或其子接口的接口创建代理对象,并将代理对象注册为 Spring Bean,业务层便可以通过 Spring 自动封装的特性来直接使用该对象。

<context:component-scan base-package="demoJPA"/>

    <tx:annotation-driven transaction-manager="transactionManager"/>

    <jpa:repositories base-package="demoJPA.dao"  repository-impl-postfix="Impl" entity-manager-factory-ref="entityManagerFactory" transaction-manager-ref="transactionManager"/>

    <bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="entityManagerFactory" ref="entityManagerFactory"/>
</bean> <bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="jpaVendorAdapter">
<bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
<property name="generateDdl" value="false"/>
<property name="showSql" value="true"/>
</bean>
</property>
</bean>

  

使用 @Query 创建查询

除了通过解析方法名实现功能外,开发者还可以直接在声明的方法上面使用 @Query 注解,并提供一个查询语句作为参数。Spring Data JPA 在创建代理对象时,便会用提供的查询语句来实现其功能。

@Query 注解的使用非常简单,只需在声明的方法上面标注该注解,同时提供一个 JPQL 查询语句即可。JPQL 语句中通过": 变量"的格式来指定参数,同时在方法的参数前面使用 @Param 将方法参数与 JP QL 中的命名参数对应。

    @Query("from Category where id=:id")
Category findOne(@Param("id") int id);

开发者也可以通过使用 @Query 来执行一个更新操作,为此,我们需要在使用 @Query 的同时,用 @Modifying 来将该操作标识为修改查询,这样框架最终会生成一个更新的操作,而非查询。

    @Transactional
@Modifying
@Query("update Category set name=:name where id=:id")
void updateName(@Param("id")int id,@Param("name")String name);

  

单元测试

@ContextConfiguration(locations = "classpath:applicationContext.xml")
@RunWith(SpringJUnit4ClassRunner.class)
public class testJpa { int id=5; @Autowired
private CategoryDao categoryDao; @Test
public void testSave(){
Category category=new Category();
category.setId(id);
category.setName("test");
categoryDao.save(category);
} @Test
public void testUpdateName(){
String name="test111";
categoryDao.updateName(id,name);
} @Test
public void testFindById(){
Category category=categoryDao.findOne(id);
System.out.println(category);
} @Test
public void count(){
long count=categoryDao.count();
System.out.println(count);
} @Test
public void testFindAll(){
Iterable<Category> categories=categoryDao.findAll();
for(Category category:categories){
System.out.println(category);
}
} @Test
public void delete(){
categoryDao.delete(id);
} }

源码地址https://github.com/cathychen00/learnjava/tree/master/DemoJPA  

参考资料:

JAVA入门[20]-Spring Data JPA简单示例的更多相关文章

  1. SpringBoot入门:Spring Data JPA 和 JPA(理论)

    参考链接: Spring Data JPA - Reference Documentation Spring Data JPA--参考文档 中文版 纯洁的微笑:http://www.ityouknow ...

  2. Spring Data JPA简单使用

    用Spring Data JPA操作数据库 这份教程教你用Spring Data JPA从关系数据库mysql中存储和提取数据.总结来自https://spring.io/guides/gs/acce ...

  3. spring data jpa 简单使用

    通过解析方法名创建查询 通过前面的例子,读者基本上对解析方法名创建查询的方式有了一个大致的了解,这也是 Spring Data JPA 吸引开发者的一个很重要的因素.该功能其实并非 Spring Da ...

  4. Spring Data JPA 简单查询--接口方法

    一.接口方法整理速查 下表针对于简单查询,即JpaRepository接口(继承了CrudRepository接口.PagingAndSortingRepository接口)中的可访问方法进行整理.( ...

  5. Spring Data JPA简单查询接口方法速查

    下表针对于简单查询,即JpaRepository接口(继承了CrudRepository接口.PagingAndSortingRepository接口)中的可访问方法进行整理.(1)先按照功能进行分类 ...

  6. Spring Data Jpa简单了解

    原文来源:http://www.cnblogs.com/xuyuanjia/p/5707681.html 以下是自己简单整理原有文章,其实就是在原来文章基础上化重点以及可能会有所删减的方式进行整理,需 ...

  7. Spring Data JPA 简单查询--方法定义规则

    一.常用规则速查 1  And 并且2  Or  或3  Is,Equals 等于4  Between  两者之间5  LessThan 小于6  LessThanEqual   小于等于7  Gre ...

  8. Spring Data JPA 简单查询

    一.常用规则速查 1  And 并且2  Or  或3  Is,Equals 等于4  Between  两者之间5  LessThan 小于6  LessThanEqual   小于等于7  Gre ...

  9. Spring Data Jpa 简单使用事务

    对于两张表,需要顺序操作,必须全部表均操作成功才可,否则两张表不操作. 例如,现在有device,collectionpoint两张表,向两张表顺序执行insert操作 SQL如下 INSERT IN ...

随机推荐

  1. 【3】测试搭建成功的单机hadoop环境

    1.关闭防火墙service iptables stop,(已经设置开机关闭的忽略) 2.进入hadoop目录,修改hadoop配置文件(4个) core-site.xml(核心配置,fs.defau ...

  2. Python - SIP参考指南 - 介绍

    介绍 本文是SIP4.18的参考指南.SIP是一种Python工具,用于自动生成Python与C.C++库的绑定.SIP最初是在1998年用PyQt开发的,用于Python与Qt GUI toolki ...

  3. 【开源】canvas图像裁剪、压缩、旋转

    前言 前段时间遇到了一个移动端对图像进行裁剪.压缩.旋转的需求. 考虑到已有各轮子的契合度都不高,于是自己重新造了一个轮子. 关于图像裁剪.压缩 在HTML5时代,canvas的功能已经非常强大了,可 ...

  4. 初始MyBatis

    初始MyBatis 框架的概念: 框架是一个提供可重复的功用结构的半成品.它为我们构建新的应用程序提供了极大的便利,一方面提供了可以拿来就用的工具,更重要的是提供了可重用的设计.D 框架技术的优势: ...

  5. SQL Server多表同时查询

    今天在练sql server发现多条语句同时使用可以多表同时查询,具体操作如下: 代码示例: USE teachingGOSELECT *FROM dbo.teach_classORDER BY cl ...

  6. Python之matplotlib学习(三)

    例子11-1:横坐标时间的处理 from matplotlib.dates import datestr2num,DateFormatter import matplotlib.dates as da ...

  7. Linux运维正则表达式之grep

    一.什么是正则表达式?简单的说,正则表达式就是一套处理大量的字符串而定义的规则和方法.例如:假设 @代表12345通过正则表达式这些特殊符号,我们可以快速过滤.替换需要的内容.linux正则表达式一般 ...

  8. Python Base64 编码

    0x00 Base64简介 0x01 常用场景举例 0x02 编.解码流程 0x03 Python中Base64编码与解码 0x00 Base64简介 我们知道在计算机中任何数据都是按ascii码存储 ...

  9. Android 个推 踩坑小结

    公司一个项目之前在手机上一直可以正常运行,后来在平板上运行了一下,在欢迎页面卡出了,一直没有反应. 于是我就将项目在电脑上用Android Studio往平板上运行了一遍,看了下打印的Log日志,发现 ...

  10. struts2对于处理JSON的配置

    由于最近几年日益流行前后端分离模式,JSON作为数据载体也变得不可或缺.几乎所有的web框架都需要支持JSON,下面咱就一起了解下struts2是如何支持JSON的. 对于JSON的发送 这里有两种方 ...