对于传统关系型数据库来说,Spring Boot使用JPA(Java Persistence API)资源库提供持久化的标准规范,即将Java的普通对象通过对象关系映射(ORM)持久化到数据库中。

项目代码地址:https://github.com/AndyFlower/Spring-Boot-Learn/tree/master/spring-boot-database

一、使用MySQL是maven中的依赖配置

        <dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>

二、建立数据实体

1、假设有部门、用户、角色三个实体,且关系为一个用户只能隶属于一个部门,一个用户可以拥有多个角色

2、Java类

User.java

 package com.slp.entity;

 import com.fasterxml.jackson.annotation.JsonBackReference;
import org.springframework.format.annotation.DateTimeFormat; import javax.persistence.*;
import java.util.Date;
import java.util.List; /**
* Created by sangliping on 2017/8/18.
* @ManyToOne定义User与Department的多对一关系,并用中间表user_role来存储他们的ID
* @DateTimeFormat日期进行格式化
* @JsonBackReference用了方式关系对象的递归访问
*/ @Entity
@Table(name = "user")
public class User implements java.io.Serializable{
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
private String name;
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
private Date createdate; @ManyToOne
@JoinColumn(name = "did")
@JsonBackReference
private Department deparment; @ManyToMany(cascade = {}, fetch = FetchType.EAGER)
@JoinTable(name = "user_role",
joinColumns = {@JoinColumn(name = "user_id")},
inverseJoinColumns = {@JoinColumn(name = "roles_id")})
private List<Role> roles; public User() {
} public Long getId() {
return id;
} public void setId(Long id) {
this.id = id;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} public Date getCreatedate() {
return createdate;
} public void setCreatedate(Date createdate) {
this.createdate = createdate;
} public Department getDeparment() {
return deparment;
} public void setDeparment(Department deparment) {
this.deparment = deparment;
} public List<Role> getRoles() {
return roles;
} public void setRoles(List<Role> roles) {
this.roles = roles;
}
}

Role.java

 package com.slp.entity;

 import javax.persistence.*;
import java.io.Serializable; /**
* Created by sangliping on 2017/8/18.
*/
import javax.persistence.*; @Entity
@Table(name = "role")
public class Role implements java.io.Serializable{
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
private String name; public Role() {
} public Long getId() {
return id;
} public void setId(Long id) {
this.id = id;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
}
}

Department.java

 package com.slp.entity;

 import javax.persistence.*;

 /**
* Created by sangliping on 2017/8/18.
* @Table指定关联的数据库的表名
* @Id定义一条记录的唯一标识
* @GeneratedValue设置为自动增长
*/ @Entity
@Table(name = "department")
public class Department {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
private String name; public Department() {
} public Long getId() {
return id;
} public void setId(Long id) {
this.id = id;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
}
}

三、使用JPA实体进行持久化

1、持久化实体

UserRepository.java

 package com.slp.repository;

 import com.slp.entity.User;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.stereotype.Repository; /**
* Created by sangliping on 2017/8/18.
* @Repository将该接口定义为一个资源库,使它能被其他程序引用,为其他程序提供存储数据的功能
*/
@Repository
public interface UserRepository extends JpaRepository<User,Long> { }

RoleRepository.java

 package com.slp.repository;

 import com.slp.entity.Role;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.stereotype.Repository; /**
* Created by sangliping on 2017/8/18.
*/
@Repository
public interface RoleRepository extends JpaRepository<Role,Long> {
}

DepartmentRepository.java

 package com.slp.repository;

 import com.slp.entity.Department;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.stereotype.Repository; /**
* Created by sangliping on 2017/8/18.
*/
@Repository
public interface DepartmentRepository extends JpaRepository<Department,Long> {
}

使用以上的实现我们不用写任何一句Sql语句就可以执行一些基本的操作,这是因为JpaRepository实现了一些方法,JpaRepository继承与PagingAndSortingRepository它提供了扥也和排序的功能,PageAndSortingRepository又继承与CurdRepository它提供了最简单的增删改查操作。

比如JpaRepository的方法包括:

 package org.springframework.data.jpa.repository;

 import java.io.Serializable;
import java.util.List;
import org.springframework.data.domain.Example;
import org.springframework.data.domain.Sort;
import org.springframework.data.repository.NoRepositoryBean;
import org.springframework.data.repository.PagingAndSortingRepository;
import org.springframework.data.repository.query.QueryByExampleExecutor; @NoRepositoryBean
public interface JpaRepository<T, ID extends Serializable> extends PagingAndSortingRepository<T, ID>, QueryByExampleExecutor<T> {
List<T> findAll(); List<T> findAll(Sort var1); List<T> findAll(Iterable<ID> var1); <S extends T> List<S> save(Iterable<S> var1); void flush(); <S extends T> S saveAndFlush(S var1); void deleteInBatch(Iterable<T> var1); void deleteAllInBatch(); T getOne(ID var1); <S extends T> List<S> findAll(Example<S> var1); <S extends T> List<S> findAll(Example<S> var1, Sort var2);
}

JPA定义声明方法的规则:

在接口中使用findBy、readBy、getBy作为方法名的前缀,拼接实体中类的属性字段(首字母大写)并可选择拼接一些SQL查询关键字来合成一个查询方法

 And           findByIdAndName(Long id,String name);
Or findByIdOrName(Long id,String name);
Between findByCreatedateBetween(Date start,Date end);
LessThan findByCreatedateLessThan(Date start);
GreaterThan findByCreatedateGreaterThan(Date start);
IsNull findByNameIsNull();
IsNotNull findByNameIsNotNull();
NotNull findByNameNotNull();
Like findByNameLike(String name);
NotLike findByNameNotLike(String name);
orderBy findByNameOrderByIdAsc(String name);
Not findByNameNot(String name);
In findByNameIn(Collection<String> nameList);
NotIn findByNameNotIn(Collection<String> nameList);

四、Spring Boot参数配置

 spring.datasource.url=jdbc:mysql://localhost:3306/dev?characterEncoding=utf-8
spring.datasource.username=root
spring.datasource.driver-class-name=com.mysql.jdbc.Driver
spring.datasource.password=123456
spring.jpa.database=mysql
spring.jpa.show-sql=true
#配置此选项会自动检查表是否创建,如果没有创建则创建,如果已经创建则更新
spring.jpa.hibernate.ddl-auto=update
spring.jpa.hibernate.naming.strategy=org.hibernate.cfg.ImprovedNamingStrategy
spring.jpa.propertie.hibernate.dialect=org.hibernate.dialect.MySQLDialect

五、创建JPA配置类

 package com.slp.config;

 import org.springframework.boot.autoconfigure.domain.EntityScan;
import org.springframework.context.annotation.Configuration;
import org.springframework.core.Ordered;
import org.springframework.core.annotation.Order;
import org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor;
import org.springframework.data.jpa.repository.config.EnableJpaRepositories;
import org.springframework.transaction.annotation.EnableTransactionManagement; /**
* Created by sangliping on 2017/8/18.
* @EnableTransactionManagement启用了JPA的事务管理
* @EnableJpaRepositories启用了JPA资源库并指定了定义的接口资源库的位置
* @EntityScan指定了定义实体的位置
*/
@Order(Ordered.HIGHEST_PRECEDENCE)
@Configuration
@EnableTransactionManagement(proxyTargetClass = true)
@EnableJpaRepositories(basePackages = "com.slp.repository")
@EntityScan(basePackages = "com.slp.entity")
public class JpaConfiguration { PersistenceExceptionTranslationPostProcessor persistenceExceptionTranslationPostProcessor(){
return new PersistenceExceptionTranslationPostProcessor();
}
}

六、测试准备

1、在pom.xml文件中加入测试依赖

 <dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>

2、编写测试JPA配置类

 package com.slp;

 /**
* Created by sangliping on 2017/8/18.
*/
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor;
import org.springframework.data.jpa.repository.config.EnableJpaRepositories;
import org.springframework.jdbc.datasource.DriverManagerDataSource;
import org.springframework.orm.jpa.JpaTransactionManager;
import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean;
import org.springframework.orm.jpa.vendor.Database;
import org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter;
import org.springframework.transaction.PlatformTransactionManager;
import org.springframework.transaction.support.TransactionTemplate; import javax.sql.DataSource;
import java.util.Properties; @Configuration
@EnableJpaRepositories(basePackages = "com.slp.repository")
public class JpaConfiguration { @Bean
PersistenceExceptionTranslationPostProcessor persistenceExceptionTranslationPostProcessor() {
return new PersistenceExceptionTranslationPostProcessor();
} @Bean
public DataSource dataSource() {
DriverManagerDataSource dataSource = new DriverManagerDataSource();
dataSource.setDriverClassName("com.mysql.jdbc.Driver");
dataSource.setUrl("jdbc:mysql://localhost:3306/dev?characterEncoding=utf8");
dataSource.setUsername("root");
dataSource.setPassword("123456"); return dataSource;
} @Bean
public LocalContainerEntityManagerFactoryBean entityManagerFactory() {
LocalContainerEntityManagerFactoryBean entityManagerFactoryBean = new LocalContainerEntityManagerFactoryBean();
entityManagerFactoryBean.setDataSource(dataSource());
entityManagerFactoryBean.setPackagesToScan("com.slp.entity");
entityManagerFactoryBean.setJpaProperties(buildHibernateProperties());
entityManagerFactoryBean.setJpaVendorAdapter(new HibernateJpaVendorAdapter() {{
setDatabase(Database.MYSQL);
}});
return entityManagerFactoryBean;
} protected Properties buildHibernateProperties() {
Properties hibernateProperties = new Properties(); hibernateProperties.setProperty("hibernate.dialect", "org.hibernate.dialect.MySQL5Dialect");
hibernateProperties.setProperty("hibernate.show_sql", "true");
hibernateProperties.setProperty("hibernate.use_sql_comments", "false");
hibernateProperties.setProperty("hibernate.format_sql", "true");
hibernateProperties.setProperty("hibernate.hbm2ddl.auto", "update");
hibernateProperties.setProperty("hibernate.generate_statistics", "false");
hibernateProperties.setProperty("javax.persistence.validation.mode", "none");
hibernateProperties.setProperty(" spring.jpa.hibernate.ddl-auto", "update");
//Audit History flags
hibernateProperties.setProperty("org.hibernate.envers.store_data_at_delete", "true");
hibernateProperties.setProperty("org.hibernate.envers.global_with_modified_flag", "true"); return hibernateProperties;
} @Bean
public PlatformTransactionManager transactionManager() {
return new JpaTransactionManager();
} @Bean
public TransactionTemplate transactionTemplate() {
return new TransactionTemplate(transactionManager());
} }

3、编写测试类

 package com.slp;
import com.slp.entity.Department;
import com.slp.entity.Role;
import com.slp.entity.User;
import com.slp.repository.DepartmentRepository;
import com.slp.repository.RoleRepository;
import com.slp.repository.UserRepository;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
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.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
import org.springframework.util.Assert; import java.util.*; @RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(classes = {JpaConfiguration.class})
public class MySqlTest {
private static Logger logger = LoggerFactory.getLogger(MySqlTest.class); @Autowired
UserRepository userRepository;
@Autowired
DepartmentRepository departmentRepository;
@Autowired
RoleRepository roleRepository; @Before
public void initData(){
userRepository.deleteAll();
roleRepository.deleteAll();
departmentRepository.deleteAll(); Department department = new Department();
department.setName("开发部");
departmentRepository.save(department);
Assert.notNull(department.getId()); Role role = new Role();
role.setName("slp");
roleRepository.save(role);
Assert.notNull(role.getId()); User user = new User();
user.setName("user");
user.setCreatedate(new Date());
user.setDeparment(department); List<Role> roles = roleRepository.findAll();
Assert.notNull(roles);
user.setRoles(roles); userRepository.save(user);
Assert.notNull(user.getId());
} @Test
public void findPage(){
Pageable pageable = new PageRequest(0, 10, new Sort(Sort.Direction.ASC, "id"));
Page<User> page = userRepository.findAll(pageable);
Assert.notNull(page);
for(User user : page.getContent()) {
logger.info("====user==== user name:{}, department name:{}, role name:{}",
user.getName(), user.getDeparment().getName(), user.getRoles().get(0).getName());
}
} }

注意:

1、不要忘记实体类上的Entity注解

2、不要忘记Repository上的Repository注解

3、测试Jpa配置文件位于test包下

4、如果之前创建了表之后名字变更会新建一个表这样再次执行的之后如果有主外键也会有冲突报错

【Spring Boot&&Spring Cloud系列】Spring Boot中使用数据库之MySql的更多相关文章

  1. 20.翻译系列:Code-First中的数据库迁移技术【EF 6 Code-First系列】

    原文链接:https://www.entityframeworktutorial.net/code-first/migration-in-code-first.aspx EF 6 Code-First ...

  2. 在Docker中体验数据库之MySql

    在上一篇在Docker中体验数据库之Mongodb之后,这次记录一下在docker中安装mysql.过程要比Mongodb麻烦一点…… 参考网址: https://dev.mysql.com/doc/ ...

  3. spring boot 2.x 系列 —— spring boot 实现分布式 session

    文章目录 一.项目结构 二.分布式session的配置 2.1 引入依赖 2.2 Redis配置 2.3 启动类上添加@EnableRedisHttpSession 注解开启 spring-sessi ...

  4. spring boot 2.x 系列 —— spring boot 整合 redis

    文章目录 一.说明 1.1 项目结构 1.2 项目主要依赖 二.整合 Redis 2.1 在application.yml 中配置redis数据源 2.2 封装redis基本操作 2.3 redisT ...

  5. spring boot 2.x 系列 —— spring boot 整合 dubbo

    文章目录 一. 项目结构说明 二.关键依赖 三.公共模块(boot-dubbo-common) 四. 服务提供者(boot-dubbo-provider) 4.1 提供方配置 4.2 使用注解@Ser ...

  6. spring boot 2.x 系列 —— spring boot 整合 druid+mybatis

    源码Gitub地址:https://github.com/heibaiying/spring-samples-for-all 一.说明 1.1 项目结构 项目查询用的表对应的建表语句放置在resour ...

  7. spring boot 2.x 系列 —— spring boot 整合 servlet 3.0

    文章目录 一.说明 1.1 项目结构说明 1.2 项目依赖 二.采用spring 注册方式整合 servlet 2.1 新建过滤器.监听器和servlet 2.2 注册过滤器.监听器和servlet ...

  8. spring boot 2.x 系列 —— spring boot 整合 RabbitMQ

    文章目录 一. 项目结构说明 二.关键依赖 三.公共模块(rabbitmq-common) 四.服务消费者(rabbitmq-consumer) 4.1 消息消费者配置 4.2 使用注解@Rabbit ...

  9. spring boot 2.x 系列 —— spring boot 整合 kafka

    文章目录 一.kafka的相关概念: 1.主题和分区 2.分区复制 3. 生产者 4. 消费者 5.broker和集群 二.项目说明 1.1 项目结构说明 1.2 主要依赖 二. 整合 kafka 2 ...

随机推荐

  1. (原创)OpenStack服务如何使用Keystone(三)---详细配置Keystone中间件

    (一)Keystone端的操作 (二)如何在OpenStack服务上部署Keystone中间件 (三)详细配置keystonemiddleware 前文我们介绍了如何部署Keystone中间件以及中间 ...

  2. application.properties详解 --springBoot配置文件

    本文转载:http://blog.csdn.net/lpfsuperman/article/details/78287265###; # spring boot application.propert ...

  3. 让小区运营再智能一点,EasyRadius正式向WayOs用户提供到期弹出式提示充值页面

    其实一直没向用户提供到期弹出式页面,主要是给VIP群的用户一点优越感,随着这次EasyRadius的更新,海哥就免费向普通easyRadius用户提供这两个模板下载. 有些人会问,什么样的模板.有什么 ...

  4. css3实现小箭头,各种图形

    转:http://blog.csdn.net/tangtang5963/article/details/51490107 https://segmentfault.com/a/119000000278 ...

  5. 正则表达式(Java版整理)

    基础 元字符 代码 说明 . 匹配除换行符以外的任意字符 \w 匹配字母或数字或下划线或汉字 \s 匹配任意的空白符 \d 匹配数字 ^ 匹配字符串的开始 $ 匹配字符串的结束 \b 匹配字符串的结束 ...

  6. 关于WSDL文件

    endpoint Name是在Service节点中指定的. 而非是binding.binding节点只是绑定soapaction.

  7. tablediff工具实用

    1. tablediff 是什么? tablediff 实用工具用于比较两个非收敛的表中的数据,它对于排除复制拓扑中的非收敛故障非常有用. 2. tablediff 用哪些用法? 1) . 在充当复制 ...

  8. android 静默安装 卸载 资料汇总

    1. android + eclipse + 后台静默安装(一看就会) 2. 适用于android1.5以下版本apk静默安装 3. error: INSTALL_FAILED_SHARED_USER ...

  9. Allure Report使用

    https://blog.csdn.net/liuchunming033/article/details/79624474#commentBox https://blog.csdn.net/lihua ...

  10. 如何将会员名单加入LINE@生活圈?

    如何将会员名单加入LINE@生活圈? 我要如何将会员名单加入LINE@生活圈呢?答案是没有办法利用LINE@生活圈直接加入会员名单,LINE@生活圈是许可式行销,必须由LINE好友主动将LINE@生活 ...