SpringBoot学习笔记三之SpringBoot整合第三方技术

85 阅读3分钟

持续创作,加速成长!这是我参与「掘金日新计划 · 10 月更文挑战」的第19天,点击查看活动详情

整合第三方技术

1、SpringBoot整合junit

可以形象的理解:@SpringBootTest 包含了 @RunWith(SpringJUnit4ClassRunner.class) 和 @ContextConfiguration(classes = SpringConfig.class)

属性注解
名称@SpringBootTest
类型测试类注解
位置测试类定义上方
作用设置JUnit加载的SpringBoot启动类

引导类:带有@SpringBootApplication注解的 java 类 这里的引导类所在包必须是测试类所在包及其子包 因为引导类中的注解能够解析其所在包及其子包的配置类

例如:

  • 引导类所在包是 com.kaf
  • 测试类所在包是 com.kaf

如果不满足这个要求的话,就需要在使用 @SpringBootTest 注解时,使用 classes 属性指定引导类的字节码对象。 如 @SpringBootTest(classes = Application.class(引导类))

2、SpringBoot整合mybatis

1. 创建模块 导入MyBatis、MySQL相关依赖

2. 定义实体类

3. 设置数据源参数

spring.datasource.driver-class-name=com.mysql.jdbc.Driver
spring.datasource.url=jdbc:mysql://localhost:3306/test
spring.datasource.username=root
spring.datasource.password=123456
# 注意 这里我用1.0.9的 druid 加载很慢很怪,可能会报错; 换成1.1.16就可以了
spring.datasource.type=com.alibaba.druid.pool.DruidDataSource

image.png

4. 定义数据层接口与映射配置

package com.kaf.dao;

import com.kaf.domain.Book;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Select;

@Mapper // 定义数据层接口与映射配置
public interface BookDao {
    @Select("select * from book where id=#{id}")
    public Book getById(Integer id);

}

注意:这里的Dao层需要为它配置一个@Mapper映射(为了让容器能够帮我们创建该接口的实现类对象)

3、SpringBoot整合SSM

1. 创建工程 导入SpringWeb、MyBatis、MySQL、Druid相关依赖

2. 定义实体类

3. 设置数据源参数

# 配置数据源相关信息
server:
  port: 80

spring:
  datasource:
    driver-class-name: com.mysql.cj.jdbc.Driver
    url: jdbc:mysql://localhost:3306/test?serverTimezone=UTC
    username: root
    password: 123456
    type: com.alibaba.druid.pool.DruidDataSource

4. 导入静态资源 将静态资源放在 resources 下的 static 中 image.png

5. 创建dao层

package com.kaf.dao;

import com.kaf.domain.Book;
import org.apache.ibatis.annotations.*;

import java.util.List;

@Mapper //TODO 让你的SpringBoot能够扫描到这个组件,然后生成它的自动代理对象
public interface BookDao {
    @Insert("insert into book (type,name,description) values(#{type},#{name},#{description})")
    public int save(Book book);

    @Update("update book set type = #{type}, name = #{name}, description = #{description} where id = #{id}")
    public int update(Book book);

    @Delete("delete from book where id = #{id}")
    public int delete(Integer id);

    @Select("select * from book where id = #{id}")
    public Book getById(Integer id);

    @Select("select * from book")
    public List<Book> getAll();
}

6. 定义service层的实现类

package com.kaf.service.impl;

import com.kaf.dao.BookDao;
import com.kaf.domain.Book;
import com.kaf.service.BookService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;

@Service
public class BookServiceImpl implements BookService{

    @Autowired
    private BookDao bookDao;
/*TODO 我们发现了一个很有意思的问题:在使用Idea进行SSM整合的时候,如果你要注入的这个东西,在你的整个系统当中目前还不存在
    TODO (也就是: Spring容器还没有配置该对象(BookDao)的Bean。为什么没配?因为我们用的是自动代理,所以就没有对应的Bean给它自动装配)
    不改也是OK的...只是让人看着别扭罢了
 */

    @Override
    public boolean save(Book book) {
/*
        bookDao.save(book);
        return true; // todo 当你抛异常的时候 就会 return false
*/
    return bookDao.save(book) > 0;
    }

    @Override
    public boolean update(Book book) {
        return bookDao.update(book) > 0;
    }

    @Override
    public boolean delete(Integer id) {
        return bookDao.delete(id) > 0;
    }

    @Override
    public Book getById(Integer id) {
        return bookDao.getById(id);
    }

    @Override
    public List<Book> getAll() {
        return bookDao.getAll();
    }
}

7. 实现表现层

package com.kaf.controller;

import com.kaf.domain.Book;
import com.kaf.exception.BusinessException;
import com.kaf.exception.SystemException;
import com.kaf.service.BookService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import java.util.List;

//TODO 统一每一个控制器方法的返回值 ==> 为了实现 表现层与前端数据传输间的统一格式
@RestController // @Controller + @ResponseBody
@RequestMapping("/books")
public class BookController {
    @Autowired
    private BookService bookService;

    @PostMapping
    public Result save(@RequestBody Book book) { // book从提交过来的json数据中获取 所以用 @RequestBody
        boolean flag = bookService.save(book);
        return new Result(flag ? Code.SAVE_OK : Code.SAVE_ERR, flag);
    }

    @PutMapping
    public Result update(@RequestBody Book book) {
        boolean flag = bookService.update(book);
        return new Result(flag ? Code.UPDATE_OK : Code.UPDATE_ERR, flag);
    }

    @DeleteMapping("/{id}") // 删除的ID 与 查询的ID均是通过路径来获取的 所以使用 /{id}
    public Result delete(@PathVariable Integer id) {
        if(id < 0){
            throw new BusinessException(Code.BUSINESS_ERR, "请勿进行非法操作!");
        }
        boolean flag = bookService.delete(id);
        return new Result(flag ? Code.DELETE_OK : Code.DELETE_ERR, flag);
    }

    @GetMapping("/{id}")
    public Result getById(@PathVariable Integer id) {
        // 业务异常,包装成自定义异常
        if(id < 0){
            throw new BusinessException(Code.BUSINESS_ERR, "请勿进行非法操作!");
        }

        // 模拟系统异常,将可能出现的异常进行包装,转换成自定义异常
        try {
            Book book = bookService.getById(id);
            Integer code = book != null ? Code.GET_OK : Code.GET_ERR;
            String msg = book != null ? "" : "数据查询失败,请重试!";
            return new Result(code, book, msg);
        }catch (Exception e){
            throw new SystemException(Code.SYSTEM_TIMEOUT_ERR,"服务器访问超时,请重试!", e);
        }
    }

    @GetMapping
    public Result getAll() {
        List<Book> bookList = bookService.getAll();
        Integer code = bookList != null ? Code.GET_OK : Code.GET_ERR;
        String msg = bookList != null ? "" : "数据查询失败,请重试!";
        return new Result(code, bookList, msg);
    }

}