SpringBoot整合Spring Data JPA、MySQL、Druid并使用Mockito实现单元测试

一、Maven依赖


<parent>
    <groupId>org.springframework.bootgroupId>
    <artifactId>spring-boot-starter-parentartifactId>
    <version>1.5.7.RELEASEversion>
    <relativePath />
parent>


<properties>
    <project.build.sourceEncoding>UTF-8project.build.sourceEncoding>
    <project.reporting.outputEncoding>UTF-8project.reporting.outputEncoding>
    <java.version>1.8java.version>
    <druid.version>1.0.29druid.version>
    
    <lombok.version>1.16.20lombok.version>
properties>


<build>
    <plugins>
        
        <plugin>
            <groupId>org.springframework.bootgroupId>
            <artifactId>spring-boot-maven-pluginartifactId>
            <configuration>
                
                <fork>truefork>
            configuration>
        plugin>
    plugins>
build>

<dependencies>
    
    <dependency>
        <groupId>org.springframework.bootgroupId>
        <artifactId>spring-boot-starter-tomcatartifactId>
        <scope>providedscope>
    dependency>

    
    <dependency>
        <groupId>org.springframework.bootgroupId>
        <artifactId>spring-boot-starter-webartifactId>
    dependency>

    
    <dependency>
        <groupId>org.springframework.bootgroupId>
        <artifactId>spring-boot-starter-testartifactId>
        <scope>testscope>
    dependency>

    
    <dependency>
        <groupId>org.springframework.bootgroupId>
        <artifactId>spring-boot-devtoolsartifactId>
        <optional>trueoptional>
        <scope>truescope>
    dependency>

    
    <dependency>
        <groupId>org.springframework.bootgroupId>
        <artifactId>spring-boot-starter-data-jpaartifactId>
    dependency>

    
    <dependency>
        <groupId>mysqlgroupId>
        <artifactId>mysql-connector-javaartifactId>
    dependency>

    
    <dependency>
        <groupId>com.alibabagroupId>
        <artifactId>druidartifactId>
        <version>${druid.version}version>
    dependency>

    
    <dependency>
        <groupId>org.projectlombokgroupId>
        <artifactId>lombokartifactId>
        <version>${lombok.version}version>
        <scope>providedscope>
    dependency>
dependencies>

二、配置文件(这里使用yml)

application.yml中:

spring:
  profiles:
    active: dev

application-dev.yml中:

server:
  # 端口号
  port: 8080
spring:
  # 数据源配置
  datasource:
    driver-class-name: com.mysql.jdbc.Driver
    url: jdbc:mysql://localhost:3306/spring-dev
    username: root
    password: 123456

    # Druid连接池配置
    type: com.alibaba.druid.pool.DruidDataSource
    # 初始化
    initialSize: 3
    # 最大
    maxActive: 20
    # 最小
    minIdle: 3
    # 最大连接等待超时时间
    maxWait: 60000
    # 打开PSCache,并且指定每个连接PSCache的大小
    poolPreparedStatements: true
    maxPoolPreparedStatementPerConnectionSize: 20
    validationQuery: select 'x'
    testWhileIdle: true
    testOnBorrow: false
    testOnReturn: false 
    # 配置间隔多久才进行一次检测,检测需要关闭的空闲连接,单位是毫秒
    timeBetweenEvictionRunsMillis: 60000
    # 配置一个连接在池中最小生存的时间,单位是毫秒
    minEvictableIdleTimeMillis: 300000
    # 配置监控统计拦截的filters,去掉后监控界面sql将无法统计,'wall'用于防火墙
    filters: stat, wall, log4j
  # spring data jpa配置
  jpa:
    hibernate:
      # 实体类有更新时,数据库表更新
      ddl-auto: update
    show-sql: true
    format_sql: true
    database-platform: org.hibernate.dialect.MySQL5InnoDBDialect
  http:
    # 过滤字符编码
    encoding:
      charset: UTF-8
      enabled: true
      force: true

三、配置代码类

Druid监控

@Configuration
public class DruidConfig {

    @Bean
    public ServletRegistrationBean statViewServlet() {
        // 创建servlet注册实体
        ServletRegistrationBean servletRegistrationBean = new ServletRegistrationBean(new StatViewServlet(),
                "/druid/*");
        // 设置ip白名单
        servletRegistrationBean.addInitParameter("allow", "127.0.0.1");
        // 设置ip黑名单,如果allow与deny共同存在时,deny优先于allow
        servletRegistrationBean.addInitParameter("deny", "192.168.0.1");
        // 设置控制台管理用户
        servletRegistrationBean.addInitParameter("loginUsername", "admin");
        servletRegistrationBean.addInitParameter("loginPassword", "123456");
        // 是否可以重置数据
        servletRegistrationBean.addInitParameter("resetEnable", "false");
        return servletRegistrationBean;
    }

    @Bean
    public FilterRegistrationBean statFilter() {
        // 创建过滤器
        FilterRegistrationBean filterRegistrationBean = new FilterRegistrationBean(new WebStatFilter());
        // 设置过滤器过滤路径
        filterRegistrationBean.addUrlPatterns("/*");
        // 忽略过滤的形式
        filterRegistrationBean.addInitParameter("exclusions", "*.js,*.gif,*.jpg,*.png,*.css,*.ico,/druid/*");
        return filterRegistrationBean;
    }

}

四、实体类

学生实体

@Data
@NoArgsConstructor
@AllArgsConstructor
@Entity(name = "student")
public class StudentEntity implements Serializable {

    /**
     * 序列化ID
     */
    private static final long serialVersionUID = -3967265553147264980L;

    /**
     * 学生id
     */
    @Id
    @GeneratedValue
    private Integer id;

    /**
     * 学生姓名
     */
    private String name;

    /**
     * 学生年龄
     */
    private Integer age;
}

五、dao层

继承自JpaRepository即拥有CRUD
public interface StudentDao extends JpaRepository {

    /**
     * 根据年龄查询学生
     * 
     * @param age
     * @return
     */
    List findStudentByAge(Integer age);

    /**
     * 根据年龄获取学生信息 
* * <@Query是用来配置自定义SQL的注解,后面参数nativeQuery = * true才是表明了使用原生的sql,如果不配置,默认是false,则使用HQL查询方式。> * * @param age * @return */
@Query(value = "select id,name,age from student where age = ?1", nativeQuery = true) List getStudentByAge(Integer age); }

六、使用Mocktio进行单元测试

测试基类
/**
 * 测试基类 . 
* ActiveProfiles表示加载指定配置文件
* SpringBootTest.WebEnvironment.RANDOM_POR 表示使用随机端口号
* Ignore表示本类或本方法不执行测试 * * @author hkb
*/
@ActiveProfiles("test") @RunWith(SpringRunner.class) @SpringBootTest(webEnvironment = WebEnvironment.RANDOM_PORT) @Ignore public class BaseTest { }
接口测试
public class StudentServiceTest extends BaseTest {

    /**
     * 学生信息接口-被测类
     */
    @Autowired
    private StudentService studentService;

    /**
     * 学生信息dao-模拟对象
     */
    @MockBean
    private StudentDao studentDao;

    /**
     * 学生实体
     */
    private StudentEntity student;

    /**
     * 学生id
     */
    private Integer id = -99;

    /**
     * 学生姓名
     */
    private String studentName = "test";

    /**
     * 学生年龄
     */
    private Integer studentAge = 20;

    /**
     * 所有测试方法执行之前执行该方法
     */
    @Before
    public void before() {
        student = new StudentEntity(id, studentName, studentAge);
        // 设置模拟对象的返回预期值
        Mockito.when(studentDao.save(student)).thenReturn(student);
        Mockito.when(studentDao.findOne(id)).thenReturn(student);
        Mockito.when(studentDao.findStudentByAge(studentAge)).thenReturn(Lists.newArrayList(student));
        Mockito.when(studentDao.getStudentByAge(studentAge)).thenReturn(Lists.newArrayList(student));
        Mockito.when(studentDao.findAll()).thenReturn(Lists.newArrayList(student));
    }

    /**
     * 测试添加
     */
    @Test
    public void addStudentTest() {
        // 执行测试
        int studentId = studentService.addStudent(student);
        // 验证
        Assert.assertThat(studentId, Matchers.is(id));
        // 得到一个抓取器
        ArgumentCaptor personCaptor = ArgumentCaptor.forClass(StudentEntity.class);
        // 验证模拟对象的save()是否被调用一次,并抓取调用时传入的参数值
        Mockito.verify(studentDao).save(personCaptor.capture());
        // 获取抓取到的参数值
        StudentEntity addStudent = personCaptor.getValue();
        // 验证调用时的参数值
        Assert.assertThat(studentName, Matchers.is(addStudent.getName()));
    }
}

完整案例请参考:码云

你可能感兴趣的:(spring相关)