在學習 JPA Spring Data之前,我們有必要了解一下JPA和Spring Data。
JPA
JPA全稱Java Persistence API。即java持久化規范。JPA通過注解或XML描述對象-關系表的映射關系,並將運行期的實體對象持久化到數據庫中。
Spring Data
Spring Data是Spring框架的一個子項目,就像Spring MVC是Spring的一部分一樣。使得數據庫訪問變得方便和快捷。Spring Data 支持JPA。
JPA Spring Data
JPA Spring Data致力於減少數據訪問層(DAO)的開發量。使用Spring Data JPA,開發人員只需要聲明持久層的接口。
JPA Spring Data與JPA的關系
JPA Spring Data是JPA規范的一種上層實現。
下面我們通過一個簡單的Hello World案例來學習Spring Data JPA的相關技術。
使用 Spring Data JPA 進行持久層開發需要的四個步驟:
第一步:配置 Spring 整合 JPA
第二步:在 Spring 配置文件中配置 Spring Data,讓 Spring 為聲明的接口創建代理對象。配置了 <jpa:repositories> 後,Spring 初始化容器時將會掃描 base-package 指定的包目錄及其子目錄,為繼承 Repository 或其子接口的接口創建代理對象,並將代理對象注冊為 Spring Bean,業務層便可以通過 Spring 自動封裝的特性來直接使用該對象。
第三步:聲明持久層的接口,該接口繼承 Repository,Repository 是一個標記型接口,它不包含任何方法,如必要,Spring Data 可實現 Repository 其他子接口,其中定義了一些常用的增刪改查,以及分頁相關的方法。
第四步:在接口中聲明需要的方法。Spring Data 將根據給定的策略(具體策略稍後講解)來為其生成實現代碼。
第一步的具體過程如下:
第一步:新建一個java工程命名為springDataJpa

第二步:在工程下新建libs文件夾,用來存放外部jar包

第三步:引入jar包
spring框架相關jar包: hibernate相關jar包 jpa相關jar包

c3p0相關jar包: mysql驅動包

將上面的jar包拷入第二步中新建的libs文件夾中,右鍵-->構建路徑-->添加至構建路徑,將jar包加入到classpath下。
第四步:新建spring配置文件,命名為applicationContext.xml
在配置文件中配置:數據源、JPA 的EntityManagerFactory、spring事務管理器、支持注解的事務、Spring Data
applicationContext.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.0.xsd
http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-4.0.xsd">
<!-- 1. 配置數據源 -->
<context:property-placeholder location="classpath:db.properties"/>
<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
<property name="user" value="${jdbc.user}"></property>
<property name="password" value="${jdbc.password}"></property>
<property name="driverClass" value="${jdbc.driverClass}"></property>
<property name="jdbcUrl" value="${jdbc.jdbcUrl}"></property>
<!-- 配置其他屬性 -->
</bean>
<!-- 2. 配置 JPA 的 EntityManagerFactory -->
<!-- 3. 配置事務管理器 -->
<!-- 4. 配置支持注解的事務 -->
<!-- 5. 配置 SpringData -->
</beans>
第五步:新建db.properties文件,裡面用key-value形式存儲數據源相關信息

db.properties
jdbc.user=root jdbc.password=mysql jdbc.driverClass=com.mysql.jdbc.Driver jdbc.jdbcUrl=jdbc:mysql:///jpa
此處使用的是mysql數據庫,我們需要根據各自環境來配置自己的用戶名、密碼和url這些信息。
到這一步的時候,我們可以先進行一下單元測試,看看之前的配置是否存在問題。
第六步:新建SpringDataTest測試類
SpringDataTest.java
package com.springdata.jpa.test;
import java.sql.SQLException;
import javax.sql.DataSource;
import org.junit.Test;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class SpringDataTest {
private ApplicationContext ctx = null;
{
ctx = new ClassPathXmlApplicationContext("applicationContext.xml");
}
/**
* 測試數據源配置是否正確
* @throws SQLException
*/
@Test
public void testSpringData() throws SQLException {
DataSource dataSource = ctx.getBean(DataSource.class);
System.out.println(dataSource.getConnection());
}
}
如果控制台打印如下信息

則說明測試成功
測試成功之後,我們需要繼續在applicationContext.xml中配置JPA 的 EntityManagerFactory
<!-- 2. 配置 JPA 的 EntityManagerFactory -->
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="dataSource" ref="dataSource"></property>
<property name="jpaVendorAdapter">
<bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter"></bean>
</property>
<property name="packagesToScan" value="com.springdata.jpa"></property>
<property name="jpaProperties">
<props>
<!-- 二級緩存相關 -->
<!--
<prop key="hibernate.cache.region.factory_class">org.hibernate.cache.ehcache.EhCacheRegionFactory</prop>
<prop key="net.sf.ehcache.configurationResourceName">ehcache-hibernate.xml</prop>
-->
<!-- 生成的數據表的列的映射策略 -->
<prop key="hibernate.ejb.naming_strategy">org.hibernate.cfg.ImprovedNamingStrategy</prop>
<!-- hibernate 基本屬性 -->
<prop key="hibernate.dialect">org.hibernate.dialect.MySQL5InnoDBDialect</prop>
<prop key="hibernate.show_sql">true</prop>
<prop key="hibernate.format_sql">true</prop>
<prop key="hibernate.hbm2ddl.auto">update</prop>
</props>
</property>
</bean>
配置玩EntityManagerFactory後,我們可以建一個Person類來驗證一下,配置是否正確
Person.java
package com.springdata.jpa.entity;
import java.util.Date;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.Table;
@Table(name="JPA_PERSONS")
@Entity
public class Person {
private Integer id;
private String lastName;
private String email;
private Date birth;
@GeneratedValue
@Id
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public Date getBirth() {
return birth;
}
public void setBirth(Date birth) {
this.birth = birth;
}
}
測試:在SpringDataTest測試類中添加tespJpa方法
@Test
public void testJpa(){
}
以junit方式運行testJpa方法,運行之後查看數據庫中是否生成了jpa_persons表,如果有則配置成功,可以繼續下一步。
下面的圖片中是jpa_persons表結構


接下來我們需要繼續在applicationContext.xml中配置事務管理器和支持注解的事務
<!-- 3. 配置事務管理器 -->
<bean id="transactionManager"
class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="entityManagerFactory" ref="entityManagerFactory"></property>
</bean>
<!-- 4. 配置支持注解的事務 -->
<!-- 此處transaction-manager屬性值與事務管理器的bean的id保持一致 -->
<tx:annotation-driven transaction-manager="transactionManager"/>
到這裡,Spring 整合 JPA這一步就結束了。
接下來我們開始配置第二步:在 Spring 配置文件中配置 Spring Data
過程如下:
第一步:引入spring data 相關jar包

將上面的jar包拷入第二步中新建的libs文件夾中,右鍵-->構建路徑-->添加至構建路徑,將jar包加入到classpath下。
第二步:在applicationContext.xml中配置SpringData
<!-- 5. 配置 SpringData -->
<!-- 加入 jpa 的命名空間 -->
<!-- base-package: 掃描 Repository Bean 所在的 package -->
<jpa:repositories base-package="com.springdata.jpa"
entity-manager-factory-ref="entityManagerFactory"></jpa:repositories>
第三步:創建PersonRepository接口來測試一下配置是否正確
package com.springdata.jpa.repository;
import org.springframework.data.repository.Repository;
import com.springdata.jpa.entity.Person;
public interface PersonRepository extends Repository<Person, Integer>{
//根據 lastName 來獲取對應的 Person
Person getByLastName(String lastName);
}
在測試之前我們需要先向數據庫表jpa_persons中插入一條數據,例如:

然後在在SpringDataTest測試類中添加testGetByLastName方法
@Test
public void testGetByLastName(){
PersonRepository personRepository = ctx.getBean(PersonRepository.class);
Person person = personRepository.getByLastName("AA");
System.out.println(person);
}
以junit方式運行testGetByLastName方法,發現報了如下錯誤:
Caused by: java.lang.ClassNotFoundException: org.slf4j.LoggerFactory
at java.net.URLClassLoader$1.run(URLClassLoader.java:366)
at java.net.URLClassLoader$1.run(URLClassLoader.java:355)
at java.security.AccessController.doPrivileged(Native Method)
at java.net.URLClassLoader.findClass(URLClassLoader.java:354)
at java.lang.ClassLoader.loadClass(ClassLoader.java:425)
at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:308)
at java.lang.ClassLoader.loadClass(ClassLoader.java:358)
... 46 more
原因是Spring Data依賴slf4j的jar包,所以我們還需要引入如下jar包,並將其加入classpath下

再次以junit方式運行testGetByLastName方法,控制台打印消息如下:

到此為止,在 Spring 配置文件中配置 Spring Data這一步也完成了。
利用第一個小程序helloworld的搭建到此也就完成了。
此博文是觀看尚硅谷的jpa教學視頻後所做學習筆記,如果有博友需要這套視頻,可以訪問如下網址進行下載:
http://pan.baidu.com/s/1DJHIe