版本—maven  3.6.3

  1. <properties>
  2. <spring.version>5.2.5.RELEASE</spring.version> Spring的版本
  3. <hibernate.version>5.4.10.Final</hibernate.version> hibernate的版本
  4. <slf4j.version>1.7.30</slf4j.version>
  5. <log4j.version>2.12.1</log4j.version>
  6. <druid.version>1.1.21</druid.version>
  7. <mysql.version>5.1.6</mysql.version>
  8.  
  9. </properties>
  1. <dependencies>
  2. <!-- spring beg -->
  3. <dependency>
  4. <groupId>org.springframework</groupId>
  5. <artifactId>spring-aop</artifactId>
  6. <version>${spring.version}</version>
  7. </dependency>
  8.  
  9. <dependency>
  10. <groupId>org.aspectj</groupId>
  11. <artifactId>aspectjweaver</artifactId>
  12. <version>1.9.5</version>
  13. </dependency>
  14. <dependency>
  15. <groupId>org.springframework</groupId>
  16. <artifactId>spring-context</artifactId>
  17. <version>${spring.version}</version>
  18. </dependency>
  19.  
  20. <dependency>
  21. <groupId>org.springframework</groupId>
  22. <artifactId>spring-context-support</artifactId>
  23. <version>${spring.version}</version>
  24. </dependency>
  25. <dependency>
  26. <groupId>org.springframework</groupId>
  27. <artifactId>spring-test</artifactId>
  28. <version>${spring.version}</version>
  29. </dependency>
  30.  
  31. <!-- spring对orm框架的支持包-->
  32. <dependency>
  33. <groupId>org.springframework</groupId>
  34. <artifactId>spring-orm</artifactId>
  35. <version>${spring.version}</version>
  36. </dependency>
  37. <dependency>
  38. <groupId>org.springframework</groupId>
  39. <artifactId>spring-beans</artifactId>
  40. <version>${spring.version}</version>
  41. </dependency>
  42. <dependency>
  43. <groupId>org.springframework</groupId>
  44. <artifactId>spring-core</artifactId>
  45. <version>${spring.version}</version>
  46. </dependency>
  47.  
  48. <!-- hibernate beg -->
  49. <dependency>
  50. <groupId>org.hibernate</groupId>
  51. <artifactId>hibernate-entitymanager</artifactId>
  52. <version>${hibernate.version}</version>
  53. </dependency>
  54. <dependency>
  55. <groupId>org.hibernate</groupId>
  56. <artifactId>hibernate-core</artifactId>
  57. <version>${hibernate.version}</version>
  58. </dependency>
  59. <dependency>
  60. <groupId>org.hibernate.validator</groupId>
  61. <artifactId>hibernate-validator</artifactId>
  62. <version>6.1.2.Final</version>
  63. <exclusions>
  64. <exclusion>
  65. <artifactId>classmate</artifactId>
  66. <groupId>com.fasterxml</groupId>
  67. </exclusion>
  68. </exclusions>
  69. </dependency>
  70.  
  71. <!-- hibernate end -->
  72. <dependency>
  73. <groupId>mysql</groupId>
  74. <artifactId>mysql-connector-java</artifactId>
  75. <version>${mysql.version}</version>
  76. </dependency>
  77. <dependency>
  78. <groupId>com.alibaba</groupId>
  79. <artifactId>druid</artifactId>
  80. <version>${druid.version}</version>
  81. </dependency>
  82. <!-- spring data jpa 的坐标 -->
  83. <dependency>
  84. <groupId>org.springframework.data</groupId>
  85. <artifactId>spring-data-jpa</artifactId>
  86. <version>2.2.6.RELEASE</version>
  87. <exclusions>
  88. <exclusion>
  89. <artifactId>slf4j-api</artifactId>
  90. <groupId>org.slf4j</groupId>
  91. </exclusion>
  92. </exclusions>
  93. </dependency>
  94. <dependency>
  95. <groupId>org.springframework</groupId>
  96. <artifactId>spring-test</artifactId>
  97. <version>${spring.version}</version>
  98. </dependency>
  99.  
  100. <!-- el beg 使用spring data jpa 必须引入 -->
  101. <dependency>
  102. <groupId>javax.el</groupId>
  103. <artifactId>javax.el-api</artifactId>
  104. <version>3.0.0</version>
  105. </dependency>
  106. <dependency>
  107. <groupId>org.glassfish</groupId>
  108. <artifactId>javax.el</artifactId>
  109. <version>3.0.0</version>
  110. </dependency>
  111. <dependency>
  112. <groupId>org.slf4j</groupId>
  113. <artifactId>slf4j-api</artifactId>
  114. <version>${slf4j.version}</version>
  115. </dependency>
  116. <dependency>
  117. <groupId>org.apache.logging.log4j</groupId>
  118. <artifactId>log4j-api</artifactId>
  119. <version>${log4j.version}</version>
  120. </dependency>
  121. <dependency>
  122. <groupId>junit</groupId>
  123. <artifactId>junit</artifactId>
  124. <version>4.12</version>
  125. </dependency>
  126.  
  127. </dependencies>
  1. <?xml version="1.0" encoding="UTF-8"?>
  2. <beans xmlns="http://www.springframework.org/schema/beans"
  3. xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop"
  4. xmlns:context="http://www.springframework.org/schema/context"
  5. xmlns:jdbc="http://www.springframework.org/schema/jdbc" xmlns:tx="http://www.springframework.org/schema/tx"
  6. xmlns:jpa="http://www.springframework.org/schema/data/jpa"
  7. xmlns:task="http://www.springframework.org/schema/task"
  8. xmlns:contxt="http://www.springframework.org/schema/context"
  9. xsi:schemaLocation="
  10. http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
  11. http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd
  12. http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd
  13. http://www.springframework.org/schema/jdbc http://www.springframework.org/schema/jdbc/spring-jdbc.xsd
  14. http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd
  15. http://www.springframework.org/schema/data/jpa
  16. http://www.springframework.org/schema/data/jpa/spring-jpa.xsd">
  17.  
  18.  
  19. <!-- 配置实体类管理工厂 -->
  20. <bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
  21.  
  22. <!-- 配置数据源 -->
  23. <property name="dataSource" ref="dataSource"/>
  24. <!-- 配置实体类包扫描 -->
  25. <property name="packagesToScan" value="com.ytfs.entity"/>
  26. <!-- 配置jpa提供方 -->
  27. <property name="persistenceProvider">
  28. <bean class="org.hibernate.jpa.HibernatePersistenceProvider"/>
  29. </property>
  30.  
  31.  
  32.  
  33. <!-- 配置JPA提供方的适配器 -->
  34.  
  35. <property name="jpaVendorAdapter">
  36. <bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
  37. <!-- 是否显示sql语句 -->
  38. <property name="showSql" value="true"/>
  39. <!-- 数据库的类型 -->
  40. <property name="database" value="MYSQL"/>
  41. <!-- 数据库的方言 -->
  42. <property name="databasePlatform" value="org.hibernate.dialect.MySQLDialect"/>
  43. <!-- 是否自动创建表 -->
  44. <property name="generateDdl" value="false"/>
  45. </bean>
  46. </property>
  47. </bean>
  48.  
  49. <!-- 配置数据源 -->
  50.  
  51. <contxt:property-placeholder location="classpath:jdbcConfig.properties"/>
  52. <bean id="dataSource" class="com.alibaba.druid.pool.DruidDataSource">
  53. <property name="username" value="${jdbc.username}"/>
  54. <property name="driverClassName" value="${jdbc.driver}"/>
  55. <property name="url" value="${jdbc.url}"/>
  56. <property name="password" value="${jdbc.password}"/>
  57. </bean>
  58.  
  59. <!-- 配置事务管理器 -->
  60. <bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
  61. <property name="entityManagerFactory" ref="entityManagerFactory"/>
  62. </bean>
  63.  
  64. <!-- 整合jpa -->
  65. <jpa:repositories base-package="com.ytfs.dao"
  66. transaction-manager-ref="transactionManager"
  67. entity-manager-factory-ref="entityManagerFactory"/>
  68.  
  69. <!-- 配置上spring包扫描器 -->
  70. <context:component-scan base-package="com.ytfs"/>
  1. jdbc.driver=com.mysql.jdbc.Driver
  2. jdbc.url=jdbc:mysql://localhost:3306/jpa
  3. jdbc.username=root
  4. jdbc.password=root

  1. package com.ytfs.entity;
  2. import javax.persistence.*;
  3. import java.io.Serializable;
  4. /**
  5. * @Classname Customer
  6. * @Description TODO(客户实体类)
  7. * @Date 2020/4/29 21:34
  8. * @Created by ytfs
  9. */
  10. @Entity
  11. @Table(name = "cst_customer")
  12. public class Customer implements Serializable {
  13. @Id
  14. @GeneratedValue(strategy = GenerationType.IDENTITY)
  15. @Column(name = "cust_id")
  16. private Long custId;
  17. /**
  18. * cust_id` bigint(32) NOT NULL AUTO_INCREMENT COMMENT '客户编号(主键)',
  19. * `cust_name` varchar(32) NOT NULL COMMENT '客户名称(公司名称)',
  20. * `cust_source` varchar(32) DEFAULT NULL COMMENT '客户信息来源',
  21. * `cust_industry` varchar(32) DEFAULT NULL COMMENT '客户所属行业',
  22. * `cust_level` varchar(32) DEFAULT NULL COMMENT '客户级别',
  23. * `cust_address` varchar(128) DEFAULT NULL COMMENT '客户联系地址',
  24. * `cust_phone` v
  25. */
  26. @Column(name = "cust_name")
  27. private String custName;
  28. @Column(name = "cust_source")
  29. private String custSource;
  30. @Column(name = "cust_industry")
  31. private String custIndustry;
  32. @Column(name = "cust_level")
  33. private String custLevel;
  34. @Column(name = "cust_address")
  35. private String custAddress;
  36. @Column(name = "cust_phone")
  37. private String custPhone;
  38. public Long getCustId() {
  39. return custId;
  40. }
  41. public void setCustId(Long custId) {
  42. this.custId = custId;
  43. }
  44. public String getCustName() {
  45. return custName;
  46. }
  47. public void setCustName(String custName) {
  48. this.custName = custName;
  49. }
  50. public String getCustSource() {
  51. return custSource;
  52. }
  53. public void setCustSource(String custSource) {
  54. this.custSource = custSource;
  55. }
  56. public String getCustIndustry() {
  57. return custIndustry;
  58. }
  59. public void setCustIndustry(String custIndustry) {
  60. this.custIndustry = custIndustry;
  61. }
  62. public String getCustLevel() {
  63. return custLevel;
  64. }
  65. public void setCustLevel(String custLevel) {
  66. this.custLevel = custLevel;
  67. }
  68. public String getCustAddress() {
  69. return custAddress;
  70. }
  71. public void setCustAddress(String custAddress) {
  72. this.custAddress = custAddress;
  73. }
  74. public String getCustPhone() {
  75. return custPhone;
  76. }
  77. public void setCustPhone(String custPhone) {
  78. this.custPhone = custPhone;
  79. }
  80. @Override
  81. public String toString() {
  82. return "Customer{" +
  83. "custId=" + custId +
  84. ", custName='" + custName + '\'' +
  85. ", custSource='" + custSource + '\'' +
  86. ", custIndustry='" + custIndustry + '\'' +
  87. ", custLevel='" + custLevel + '\'' +
  88. ", custAddress='" + custAddress + '\'' +
  89. ", custPhone='" + custPhone + '\'' +
  90. '}';
  91. }
  92. }

View Code

Spring Data JPA是spring提供的一款对于数据访问层(Dao层)的框架,使用Spring Data JPA,只需要按照框架的规范提供dao接口,不需要实现类就可以完成数据库的增删改查、分页查询等方法的定义,极大的简化了我们的开发过程。

 

在Spring Data JPA中,对于定义符合规范的Dao层接口,我们只需要遵循以下几点就可以了:

 

1.创建一个Dao层接口,并实现JpaRepositoryJpaSpecificationExecutor

    2.提供相应的泛型

  1. package com.ytfs.dao;
  2. import com.alibaba.druid.sql.visitor.functions.If;
  3. import com.ytfs.entity.Customer;
  4. import org.hibernate.mapping.Value;
  5. import org.springframework.data.jpa.repository.JpaRepository;
  6. import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
  7. import org.springframework.data.jpa.repository.Modifying;
  8. import org.springframework.data.jpa.repository.Query;
  9. import java.lang.invoke.VarHandle;
  10. import java.security.spec.NamedParameterSpec;
  11. import java.util.List;
  12. /**
  13. * @Classname CustomerDao
  14. * @Description TODO(客户的数据库访问层)
  15. * @Date 2020/4/29 21:46
  16. * @Created by ytfs
  17. * JpaRepository<实体类类型,主键类型>:用来完成基本CRUD操作
  18. * JpaSpecificationExecutor<实体类类型>:用于复杂查询(分页等查询操作)
  19. */
  20.  
  21.  
  22. public interface CustomerDao extends JpaRepository<Customer, Long>, JpaSpecificationExecutor<Customer> {
  23. /**
  24. * JPQL的方式查询全部客户
  25. *
  26. * @return
  27. */
  28. @Query(value = "from Customer")
  29. List<Customer> findAllByJPQL();
  30. /**
  31. * 根据客户名称和客户id查询客户
  32. * jpql: from Customer where custName = ? and custId = ?
  33. * <p>
  34. * 对于多个占位符参数
  35. * 赋值的时候,默认的情况下,占位符的位置需要和方法参数中的位置保持一致
  36. * <p>
  37. * 可以指定占位符参数的位置
  38. * ? 索引的方式,指定此占位的取值来源
  39. */
  40. @Query("from Customer where custName = ?2 and custId = ?1")
  41. Customer findCustomerById(Long custId, String custName);
  42. /**
  43. * 使用jpql完成更新操作
  44. * 案例 : 根据id更新,客户的名称
  45. * 更新4号客户的名称,将名称改为“黑马程序员”
  46. *
  47. * sql :update cst_customer set cust_name = ? where cust_id = ?
  48. * jpql : update Customer set custName = ? where custId = ?
  49. *
  50. * @Query : 代表的是进行查询
  51. * * 声明此方法是用来进行更新操作
  52. * @Modifying
  53. * * 当前执行的是一个更新操作
  54. *
  55. */
  56. @Query("update Customer set custName = ?1 where custId = ?2")
  57. @Modifying
  58. void updateCustomerById(String custName,Long Id);
  59. /**
  60. * 使用sql的形式查询:
  61. * 查询全部的客户
  62. * sql : select * from cst_customer;
  63. * Query : 配置sql查询
  64. * value : sql语句
  65. * nativeQuery : 查询方式
  66. * true : sql查询
  67. * false:jpql查询 默认值
  68. *
  69. */
  70. @Query(value = "select * from cst_customer", nativeQuery = true)
  71. List<Customer> findAllBySql();
  72. /**
  73. * 使用sql的形式查询:
  74. * 条件查询
  75. * sql : select * from cst_customer where cust_name like ?;
  76. * Query : 配置sql查询
  77. * value : sql语句
  78. * nativeQuery : 查询方式
  79. * true : sql查询
  80. * false:jpql查询 默认值
  81. *
  82. */
  83. @Query(value = "select * from cst_customer where cust_name like ?1", nativeQuery = true)
  84. Customer FindCustomerByLikeCustName(String custName);
  85. /**
  86. * @author 雨听风说
  87. * @param
  88. * @updateTime 2020/4/30 23:45
  89. * 方法名的约定:
  90. * findBy : 查询
  91. * 对象中的属性名(首字母大写) : 查询的条件
  92. * CustName
  93. * * 默认情况 : 使用 等于的方式查询
  94. * 特殊的查询方式
  95. *
  96. * findByCustName -- 根据客户名称查询
  97. *
  98. * 再springdataJpa的运行阶段
  99. * 会根据方法名称进行解析 findBy from xxx(实体类)
  100. * 属性名称 where custName =
  101. *
  102. * 1.findBy + 属性名称 (根据属性名称进行完成匹配的查询=)
  103. * 2.findBy + 属性名称 + “查询方式(Like | isnull)”
  104. * findByCustNameLike
  105. * 3.多条件查询
  106. * findBy + 属性名 + “查询方式” + “多条件的连接符(and|or)” + 属性名 + “查询方式”
  107. */
  108.  
  109.  
  110. /**
  111. * 根据名称精准查询客户
  112. * @param CustName
  113. * @return
  114. */
  115. Customer findByCustName(String CustName);
  116. /**
  117. * 根据客户名称进行模糊查询
  118. * @param CustName
  119. * @return
  120. */
  121. List<Customer> findByCustNameLike(String CustName);
  122. /**
  123. * 根据客户名称模糊查询,并且通过id精确查询
  124. * @param name
  125. * @param Id
  126. * @return
  127. */
  128. List<Customer> findByCustNameLikeAndCustId(String name, Long Id);
  129. }

View Code

完成了Spring Data JPA的环境搭建,并且编写了符合Spring Data JPA 规范的Dao层接口之后,就可以使用定义好的Dao层接口进行客户的基本CRUD操作

  1. package com.ytfs.test;
  2. import com.ytfs.dao.CustomerDao;
  3. import com.ytfs.entity.Customer;
  4. import org.junit.Test;
  5. import org.junit.runner.RunWith;
  6. import org.springframework.beans.factory.annotation.Autowired;
  7. import org.springframework.test.context.ContextConfiguration;
  8. import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
  9. import java.util.List;
  10. /**
  11. * @Classname SpringDataJpaTest
  12. * @Description TODO(springDataJpa的测试案例)
  13. * @Date 2020/4/29 21:58
  14. * @Created by ytfs
  15. */
  16. @RunWith(SpringJUnit4ClassRunner.class)
  17. @ContextConfiguration(locations = "classpath:applicationContext.xml")
  18. public class SpringDataJpaTest {
  19. @Autowired
  20. private CustomerDao customerDao;
  21. /**
  22. * @description 查询全部
  23. * @author 雨听风说
  24. * @updateTime 2020/4/29 22:44
  25. */
  26. @Test
  27. public void testFindALl() {
  28. List<Customer> list = this.customerDao.findAll();
  29. list.forEach(System.out::println);
  30. }
  31. /**
  32. * @description 根据id查询客户
  33. * @author 雨听风说
  34. * @updateTime 2020/4/29 22:49
  35. */
  36. @Test
  37. public void testFindById() {
  38. System.out.println(this.customerDao.findById(1L));
  39. }
  40. /**
  41. * @description 根据Id删除
  42. * @author 雨听风说
  43. * @updateTime 2020/4/29 22:53
  44. */
  45. @Test
  46. public void testDelete() {
  47. this.customerDao.deleteById(4l);
  48. }
  49. /**
  50. * @description 保存客户, save, 保存并且返回保存的对象
  51. * @author 雨听风说
  52. * @updateTime 2020/4/29 23:03
  53. */
  54. @Test
  55. public void testSave() {
  56. Customer customer = new Customer();
  57. customer.setCustName("雨听风说");
  58. this.customerDao.save(customer);
  59. }
  60. /**
  61. * @description 当保存方法执行的时候, 如果需要保存的对象有id, 那么将自动更新这个id的对象
  62. * 并且将该对象为设置的参数置为null
  63. * @author 雨听风说
  64. * @updateTime 2020/4/29 23:07
  65. */
  66. @Test
  67. public void testUpdate() {
  68. Customer customer = new Customer();
  69. customer.setCustId(5l);
  70. customer.setCustName("雨听风说修改");
  71. this.customerDao.save(customer);
  72. }
  73. }

View Code

顾名思义,方法命名规则查询就是根据方法的名字,就能创建查询。只需要按照Spring Data JPA提供的方法命名规则定义方法的名称,就可以完成查询工作。Spring Data JPA在程序执行的时候会根据方法名称进行解析,并自动生成查询语句进行查询

 

按照Spring Data JPA 定义的规则,查询方法以findBy开头,涉及条件查询时,条件的属性用条件关键字连接,要注意的是:条件属性首字母需大写。框架在进行方法名解析时,会先把方法名多余的前缀截取掉,然后对剩下部分进行解析。

 

    //方法命名方式查询(根据客户名称查询客户)

    public Customer findByCustName(String custName);

 

 

具体的关键字,使用方法和生产成SQL如下表所示

 

         

Keyword

Sample

JPQL

   

And

findByLastnameAndFirstname

… where x.lastname = ?1 and x.firstname = ?2

   

Or

findByLastnameOrFirstname

… where x.lastname = ?1 or x.firstname = ?2

   

Is,Equals

findByFirstnameIs,

findByFirstnameEquals

… where x.firstname = ?1

   

Between

findByStartDateBetween

… where x.startDate between ?1 and ?2

   

LessThan

findByAgeLessThan

… where x.age < ?1

   

LessThanEqual

findByAgeLessThanEqual

… where x.age ⇐ ?1

   

GreaterThan

findByAgeGreaterThan

… where x.age > ?1

   

GreaterThanEqual

findByAgeGreaterThanEqual

… where x.age >= ?1

   

After

findByStartDateAfter

… where x.startDate > ?1

   

Before

findByStartDateBefore

… where x.startDate < ?1

   

IsNull

findByAgeIsNull

… where x.age is null

   

IsNotNull,NotNull

findByAge(Is)NotNull

… where x.age not null

   

Like

findByFirstnameLike

… where x.firstname like ?1

   

NotLike

findByFirstnameNotLike

… where x.firstname not like ?1

   

StartingWith

findByFirstnameStartingWith

… where x.firstname like ?1 (parameter bound with appended %)

   

EndingWith

findByFirstnameEndingWith

… where x.firstname like ?1 (parameter bound with prepended %)

   

Containing

findByFirstnameContaining

… where x.firstname like ?1 (parameter bound wrapped in %)

   

OrderBy

findByAgeOrderByLastnameDesc

… where x.age = ?1 order by x.lastname desc

   

Not

findByLastnameNot

… where x.lastname <> ?1

   

In

findByAgeIn(Collection ages)

… where x.age in ?1

   

NotIn

findByAgeNotIn(Collection age)

… where x.age not in ?1

   

TRUE

findByActiveTrue()

… where x.active = true

   

FALSE

findByActiveFalse()

… where x.active = false

   

IgnoreCase

findByFirstnameIgnoreCase

… where UPPER(x.firstame) = UPPER(?1)

   

 

  1. package com.ytfs.test;
  2. import com.ytfs.dao.CustomerDao;
  3. import com.ytfs.entity.Customer;
  4. import org.junit.Test;
  5. import org.junit.runner.RunWith;
  6. import org.springframework.beans.factory.annotation.Autowired;
  7. import org.springframework.test.annotation.Rollback;
  8. import org.springframework.test.context.ContextConfiguration;
  9. import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
  10. import javax.transaction.Transactional;
  11. import java.util.List;
  12. /**
  13. * @Classname SpringDataJPAJpqlTest
  14. * @Description TODO(SpringDataJpaJpql测试)
  15. * @Date 2020/4/30 21:15
  16. * @Created by ytfs
  17. */
  18.  
  19. /**
  20. * jpql的查询方式
  21. * jpql : jpa query language (jpq查询语言)
  22. * 特点:语法或关键字和sql语句类似
  23. * 查询的是类和类中的属性
  24. * 需要将JPQL语句配置到接口方法上
  25. * 1.特有的查询:需要在dao接口上配置方法
  26. * 2.在新添加的方法上,使用注解的形式配置jpql查询语句
  27. * 3.注解 : @Query
  28. */
  29. @RunWith(SpringJUnit4ClassRunner.class)
  30. @ContextConfiguration(locations = "classpath:applicationContext.xml")
  31. public class SpringDataJPAJpqlTest {
  32. @Autowired
  33. private CustomerDao customerDao;
  34. /**
  35. * @description 通过JPQL的方式查询所有的客户
  36. * @author 雨听风说
  37. * @updateTime 2020/4/30 21:48
  38. */
  39. @Test
  40. public void testFindAll() {
  41. List<Customer> list = this.customerDao.findAllByJPQL();
  42. list.forEach(System.out::println);
  43. }
  44. /**
  45. * @description 通过客户姓名和客户的Id查询一个客户
  46. * @author 雨听风说
  47. * @updateTime 2020/4/30 21:48
  48. */
  49. @Test
  50. public void testFindCustomerByIdAndName() {
  51. Customer customer = this.customerDao.findCustomerById(5L, "雨听风说");
  52. System.out.println("customer = " + customer);
  53. }
  54. /**
  55. * @description 通过Id修改客户的姓名
  56. * @author 雨听风说
  57. * @updateTime 2020/4/30 21:59
  58. * <p>
  59. * 测试jpql的更新操作
  60. * springDataJpa中使用jpql完成 更新/删除操作
  61. * 需要手动添加事务的支持
  62. * 默认会执行结束之后,回滚事务
  63. * @Rollback :设置是否自动回滚
  64. * false|true
  65. */
  66. @Test
  67. @Transactional
  68. @Rollback(value = false)
  69. public void testUpdateCustomerById() {
  70. this.customerDao.updateCustomerById("雨听风说", 5L);
  71. }
  72. /**
  73. * @description 通过sql语句的形式查询全部的客户
  74. * @author 雨听风说
  75. * @updateTime 2020/4/30 22:08
  76. */
  77. @Test
  78. public void testFindAllBySql() {
  79. List<Customer> customers = this.customerDao.findAllBySql();
  80. customers.forEach(System.out::println);
  81. }
  82. /**
  83. * @description 通过sql语句的形式模糊条件查询
  84. * @author 雨听风说
  85. * @updateTime 2020/4/30 22:08
  86. */
  87. @Test
  88. public void testFindCustomerByLikeCustName() {
  89. Customer customer = this.customerDao.FindCustomerByLikeCustName("雨听风说");
  90. System.out.println(customer);
  91. }
  92. /**
  93. * @description 根据名称精准查客户
  94. * @author 雨听风说
  95. * @updateTime 2020/4/30 23:47
  96. */
  97. @Test
  98. public void testByName() {
  99. Customer customer = this.customerDao.findByCustName("雨听风说");
  100. System.out.println("customer = " + customer);
  101. }
  102. /**
  103. * @description 根据客户的名称模糊查询
  104. * @author 雨听风说
  105. * @updateTime 2020/4/30 23:51
  106. */
  107. @Test
  108. public void testFindByNameLike() {
  109. List<Customer> byCustNameLike = this.customerDao.findByCustNameLike("%风说%");
  110. byCustNameLike.forEach(System.out::println);
  111. }
  112. /**
  113. * @description 根据客户名称模糊查询,并且根据id精准查询
  114. * @author 雨听风说
  115. * @updateTime 2020/4/30 23:56
  116. */
  117. @Test
  118. public void testFindCustomerByNameLikeAndId() {
  119. List<Customer> byCustNameLikeAndCustId = this.customerDao.findByCustNameLikeAndCustId("%风说%", 5L);
  120. byCustNameLikeAndCustId.forEach(System.out::println);
  121. }
  122. }

View Code

在客户的案例中,我们发现在自定义的CustomerDao中,并没有提供任何方法就可以使用其中的很多方法,那么这些方法究竟是怎么来的呢?答案很简单,对于我们自定义的Dao接口,由于继承了JpaRepository和JpaSpecificationExecutor,所以我们可以使用这两个接口的所有方法。

 

 

 

 

在使用Spring Data JPA时,一般实现JpaRepository和JpaSpecificationExecutor接口,这样就可以使用这些接口中定义的方法,但是这些方法都只是一些声明,没有具体的实现方式,那么在 Spring Data JPA中它又是怎么实现的呢?

通过对客户案例,以debug断点调试的方式,通过分析Spring Data JPA的原来来分析程序的执行过程

当程序执行的时候,会通过JdkDynamicAopProxy的invoke方法,对customerDao对象生成动态代理对象。根据对Spring Data JPA介绍而知,要想进行findAll查询方法,最终还是会出现JPA规范的API完成操作,那么这些底层代码存在于何处呢?答案很简单,都隐藏在通过JdkDynamicAopProxy生成的动态代理对象当中,而这个动态代理对象就是SimpleJpaRepository

通过SimpleJpaRepository的源码分析,定位到了getOne方法,在此方法中,返回em.find()的返回结果,那么em又是什么呢?

 

 

带着问题继续查找em对象,我们发现em就是EntityManager对象,而他是JPA原生的实现方式,所以我们得到结论Spring Data JPA只是对标准JPA操作进行了进一步封装,简化了Dao层代码的开发

 

 

说明了是sring data jpa 的执行方式

 

 

 

 

 

  1. private ICustomerDao cusstomerDao;
  2. //接口
  3. 真正发挥作用:
  4. 接口的是接口的实现类
  5. 在程序运行的过程中,自动的使用JdkDynamicProxy代理了接口,动态的生成了接口的实现类对象

 

版权声明:本文为TJ21原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://www.cnblogs.com/TJ21/p/12863358.html