Spring Boot 集成 JPA

JPA简介

JPA全称Java Persistence API,JPA通过JDK 5.0注解或XML描述对象-关系表的映射关系,并将运行期的实体对象持久化到数据库中。

JPA的目标之一是制定一个可以由很多供应商实现的API,并且开发人员可以编码来实现该API,而不是使用私有供应商特有的API。

JPA是需要Provider来实现其功能的,Hibernate就是JPA Provider中很强的一个,应该说无人能出其右。从功能上来说,JPA就是Hibernate功能的一个子集。

JPA实战

本文实现功能:

  • Spring BootSpring Data JPA整合
  • JpaRepository接口快捷开发
  • MVC架构+分页功能实战

pom依赖

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.21</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
<version>2.3.3.RELEASE</version>
</dependency>
<!--阿里巴巴数据库连接池,专为监控而生 -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid</artifactId>
<version>1.1.23</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>

application.properties配置

1
2
3
4
5
6
7
8
9
10
11
12
13
# 通用数据源配置
spring.datasource.url=jdbc:mysql://localhost:3306/test
spring.datasource.username=root
spring.datasource.password=root
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.type=com.alibaba.druid.pool.DruidDataSource

# JPA 相关配置
spring.jpa.database-platform=org.hibernate.dialect.MySQL5InnoDBDialect
spring.jpa.show-sql=true
# 重启应用后数据库不清空
spring.jpa.hibernate.ddl-auto=update
#spring.jpa.hibernate.ddl-auto=create

实体类

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
import lombok.Data;

import javax.persistence.*;
import java.util.Date;

/**
* @author http://www.appblog.cn
*/
@Data
@Entity
@Table(name = "user")
public class User {
public User() {
}

@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Integer id;

@Column(nullable = false)
private String username;
@Column(nullable = false)
private Date birthday;
@Column(nullable = false)
private String sex;
@Column(nullable = false)
private String address;
// @Column(nullable = false)
// private String memo;
}

实现DAO层

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
import me.yezhou.springboot.jpa.model.User;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.Modifying;
import org.springframework.data.jpa.repository.Query;
import org.springframework.data.repository.query.Param;
import org.springframework.stereotype.Repository;

/**
* @author http://www.appblog.cn
*/
@Repository
public interface UserRepository extends JpaRepository<User, Integer> {

//自定义repository, 手写sql
@Query(value = "update user set name=?1 where id=?4", nativeQuery = true) //占位符传值形式
@Modifying
int updateById(String name, int id);

@Query("from User u where u.username=:username")
//SPEL表达式
User findUser(@Param("username") String username); //参数username 映射到数据库字段username
}

注意:只有@Query的注解下不能使用update,我们需要在上面再添加个@Modifying注解,nativeQuery是询问是否使用原生sql语句。多表查询也是在这里手写sql,建议使用更好的支持多表查询的工具框架QueryDSL实现。

实现Service层

UserService .java

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
import me.yezhou.springboot.jpa.model.User;

import java.util.Iterator;

/**
* @author http://www.appblog.cn
*/
public interface UserService {
/**
* 删除
*/
public void delete(int id);

/**
* 增加
*/
public void insert(User user);

/**
* 更新
*/
public int update(User user);

/**
* 查询单个
*/
public User selectById(int id);

/**
* 查询全部列表
*/
public Iterator<User> selectAll(int pageNum, int pageSize);
}

UserServiceImpl.java

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
import me.yezhou.springboot.jpa.dao.UserRepository;
import me.yezhou.springboot.jpa.model.User;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Sort;
import org.springframework.stereotype.Service;

import java.util.Iterator;
import java.util.Optional;

/**
* @author http://www.appblog.cn
*/
@Service
public class UserServiceImpl implements UserService {

@Autowired
private UserRepository userRepository;

/**
* 删除
*
* @param id
*/
@Override
public void delete(int id) {
userRepository.deleteById(id);
}

/**
* 增加
*
* @param user
*/
@Override
public void insert(User user) {
userRepository.save(user);
}

/**
* 更新
*
* @param user
*/
@Override
public int update(User user) {
userRepository.save(user);
return 1;
}

/**
* 查询单个
*
* @param id
*/
@Override
public User selectById(int id) {
Optional<User> optional = userRepository.findById(id);
User user = optional.get();
return user;
}

/**
* 查询全部列表,并做分页
*
* @param pageNum 开始页数
* @param pageSize 每页显示的数据条数
*/
@Override
public Iterator<User> selectAll(int pageNum, int pageSize) {
//将参数传给这个方法就可以实现物理分页了,非常简单。
Sort sort = Sort.by(Sort.Direction.DESC, "id");
Pageable pageable = PageRequest.of(pageNum, pageSize, sort);
Page<User> users = userRepository.findAll(pageable);
Iterator<User> userIterator = users.iterator();
return userIterator;
}
}

分页不止可以这样做,也可以在Controller层进行实例化和初始化然后将Pageable对象传给Service
当然也可以对分页进行封装,封装后的展示。

1
Page<User> datas = userRepository.findAll(PageableTools.basicPage(1, 5, new SortDto("id")));

实现Controller

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
import me.yezhou.springboot.jpa.model.User;
import me.yezhou.springboot.jpa.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

/**
* @author http://www.appblog.cn
*/
@RestController
@RequestMapping("/user")
public class UserController {

@Autowired
private UserService userService;

@RequestMapping(method = RequestMethod.GET, value = "/delete/{id}")
public void delete(@PathVariable("id") int id) {
userService.delete(id);
}

@RequestMapping(method = RequestMethod.POST, value = "/insert")
public void insert(@RequestBody User user) {
userService.insert(user);
}

@RequestMapping(method = RequestMethod.POST, value = "/update/{id}")
public void update(@RequestBody User user) {
userService.update(user);
}

@RequestMapping(method = RequestMethod.GET, value = "/{id}/select")
public User select(@PathVariable("id") int id) {
return userService.selectById(id);
}

@RequestMapping(method = RequestMethod.GET, value = "/selectAll/{pageNum}/{pageSize}")
public List<User> selectAll(@PathVariable("pageNum") int pageNum, @PathVariable("pageSize") int pageSize) {
Iterator<User> userIterator = userService.selectAll(pageNum, pageSize);
List<User> list = new ArrayList<>();
while (userIterator.hasNext()) {
list.add(userIterator.next());
}
return list;
}
}

Powered by AppBlog.CN     浙ICP备14037229号

Copyright © 2012 - 2021 APP开发技术博客 All Rights Reserved.

访客数 : | 访问量 :