Java:(二)自己动手实现一个好用的SpringBoot后端框架(集成代码生成工具、Swagger)

前言

本篇文章是《自己动手实现一个好用的SpringBoot后端框架》系列的第二篇文章

上一篇地址:《(一)自己动手实现一个好用的SpringBoot后端框架(项目搭建、组件依赖)》

上一篇讲到了配置文件的部分,接下来我们继续讲组件具体怎么在代码中集成和配置

正式开始

下面关于配置的部分,我们统一放在/src/main/java/com/yinchd/web/config目录中

1、ConfigCenter

配置中心,我们将Druid的配置信息配置在其中

package com.yinchd.web.config;

import com.alibaba.druid.pool.DruidDataSource;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import javax.sql.DataSource;

/**
 * 配置中心
 */
@Configuration
public class ConfigCenter {
     

    /**
     * Druid数据源配置
     */
    @Bean
    @ConfigurationProperties(prefix = "spring.datasource.druid")
    public DataSource druidDataSource() {
     
        return new DruidDataSource();
    }

}

接下来我们把代码生成工具集成进来

2、CodeGenerator

CodeGenerator的集成方法我在另一篇文章:《自己动手实现一个好用的MybatisPlus代码生成器》 中有详解,建议大家参照文章进行集成,这里我就不再细述

下图为集成好的效果
Java:(二)自己动手实现一个好用的SpringBoot后端框架(集成代码生成工具、Swagger)_第1张图片
3、建用户表,生成用户相关的代码

用户表结构

CREATE TABLE `sys_user` (
  `id` int(10) unsigned NOT NULL AUTO_INCREMENT COMMENT '编号',
  `account` varchar(50) CHARACTER SET utf8 NOT NULL COMMENT '账号',
  `user_name` varchar(50) NOT NULL COMMENT '姓名',
  `password` varchar(100) NOT NULL COMMENT '密码',
  `avatar` varchar(200) DEFAULT NULL COMMENT '头像',
  `sex` int(1) DEFAULT '1' COMMENT '用户性别(1男 2女)',
  `email` varchar(100) DEFAULT NULL COMMENT '邮箱',
  `mobile` varchar(11) DEFAULT NULL COMMENT '手机号',
  `telephone` varchar(15) DEFAULT NULL COMMENT '座机号码',
  `nation` varchar(10) CHARACTER SET utf8 DEFAULT '汉族' COMMENT '民族',
  `status` int(1) NOT NULL DEFAULT '1' COMMENT '状态(0:禁用 1:正常)',
  `dept` varchar(1024) DEFAULT NULL COMMENT '用户所属部门,多个部门id之间用|线分隔',
  `create_by` varchar(50) CHARACTER SET utf8 DEFAULT 'admin' COMMENT '创建人',
  `create_time` datetime DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
  `last_update_by` varchar(50) DEFAULT NULL COMMENT '更新人',
  `last_update_time` datetime DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
  `del_flag` int(1) DEFAULT '0' COMMENT '逻辑删除(0未删,1已删)',
  PRIMARY KEY (`id`) USING BTREE,
  UNIQUE KEY `idx_account` (`account`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8mb4 ROW_FORMAT=DYNAMIC COMMENT='用户管理'

id为主键,account我设置了唯一索引,用户表大家可以根据实际情况来设计,不一定是这些字段

这里我插入一条管理员数据,密码我使用了加密算法进行加密,加密算法我后面会讲,大家先照样子初始化一条

INSERT INTO `sys_user`(`id`, `account`, `user_name`, `password`, `avatar`, `sex`, `email`, `mobile`, `telephone`, `nation`, `status`, `dept`, `create_by`, `create_time`, `last_update_by`, `last_update_time`, `del_flag`) VALUES (1, 'admin', '管理员', '$2a$10$7LKovEeC0DfPCNKuBNMOtuaWpT13Lvkm7CQU5kngEOIWXf830i/Cq', '', 1, '', '', NULL, '汉族', 1, '', 'admin', '2020-02-13 08:20:22', 'admin', '2021-03-29 14:15:37', 0);

接下来我们使用上一步的CodeGenerator来生成用户相关的代码

在CodeGenerator的main方法的配置好要生成的信息

public static void main(String[] args) {
     
    // 待生成的表名
    String tableName = "sys_user";
    // 生成的时候要去掉的表前缀,如果不需要去除什么前缀,则这里为空就行
    String trimTablePrefix = "sys_";
    // 生成文件的父包路径
    String codeGeneratePath = "com.yinchd.web";
    System.out.println("开始生成如下表:" + tableName + " 到 " + codeGeneratePath + " 目录中...");
    // 后面三个boolean值分别代表是否生成Controller、Service、Dao和实体,有时我们改了表结构,这里可以方便控制生成哪些,不生成哪些
    generate(tableName, trimTablePrefix, codeGeneratePath, true, true, true);
    System.out.println("生成成功...");
}

生成效果如下
Java:(二)自己动手实现一个好用的SpringBoot后端框架(集成代码生成工具、Swagger)_第2张图片
可以看到成功生成了ModelControllerServiceMapperXml等文件

接下来我们在Controller里写个接口测试一下能否查到数据,能查到数据证明项目基础框架搭建成功

UserController

package com.yinchd.web.controller;


import com.yinchd.web.model.UserModel;
import com.yinchd.web.service.UserService;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.annotation.Resource;

/**
 * 

* 用户管理 前端控制器 *

* * @author yinchd * @since 2021-04-25 */
@RestController @RequestMapping("user") public class UserController { @Resource UserService userService; @GetMapping("get") public UserModel getUser() { return userService.getById(1); } }

我们把项目跑起来测试一下,运行入口类WebBootApplication的main方法启动项目
Java:(二)自己动手实现一个好用的SpringBoot后端框架(集成代码生成工具、Swagger)_第3张图片
看到成功运行了项目,项目运行在520端口,我们去浏览器中调一下UserController中刚建的测试接口

在浏览器地址栏输入如下地址

http://localhost:520/user/get

结果如下
Java:(二)自己动手实现一个好用的SpringBoot后端框架(集成代码生成工具、Swagger)_第4张图片
可以看到成功的返回了数据库里的我们初始化的这条数据

但是在实际项目开发中,我们不可能写完一个接口直接给前端,让前端自己去看接口中字段的含义,特别是当接口很多的时候,如果没有一个统一的接口管理界面就不是很方便

Swagger就是为了解决这个问题而设计的,只要我们在接口上加上一些注解说明,项目启动的时候Swagger就会自动去帮我们生成接口信息,很是方便

下一步我们就把Swagger给集成进来

4、集成Swagger

这里我们使用Swagger的最新版,3.x的版本

package com.yinchd.web.config;

import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import springfox.documentation.builders.ApiInfoBuilder;
import springfox.documentation.builders.PathSelectors;
import springfox.documentation.builders.RequestHandlerSelectors;
import springfox.documentation.service.ApiInfo;
import springfox.documentation.service.Contact;
import springfox.documentation.spi.DocumentationType;
import springfox.documentation.spring.web.plugins.Docket;

/**
 * Swagger配置
 */
@Configuration
public class SwaggerConfig {
     

    /**
     * 控制swagger是否开启,开关在application.yml文件中,
     * 上线后可以在配置文件中将开关改为false,这样线上就不会生成swagger文档了
     */
    @Value("${web.swagger.enable}")
    private final boolean swaggerEnabled = true;

    @Bean
    public Docket createRestApi() {
     
        return new Docket(DocumentationType.OAS_30)
                .apiInfo(apiInfo())
                .enable(swaggerEnabled)
                .select()
                .apis(RequestHandlerSelectors.basePackage("com.yinchd.web"))
                .paths(PathSelectors.any())
                .build()
                .pathMapping("/");
    }

    private ApiInfo apiInfo() {
     
        return new ApiInfoBuilder().title("WebBoot统一API服务")
                .contact(new Contact("yinchd", "#", "[email protected]"))
                .version("v1.0")
                .build();
    }

}

我们来改造一下UserController,将Swagger注解添加进来,这样我们就可以让Swagger帮我们生成API接口文档

package com.yinchd.web.controller;


import com.yinchd.web.model.UserModel;
import com.yinchd.web.service.UserService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.annotation.Resource;

/**
 * 

* 用户管理 前端控制器 *

* * @author yinchd * @since 2021-04-25 */
@RestController @RequestMapping("user") @Api(tags = "用户管理") @Slf4j public class UserController { @Resource UserService userService; @GetMapping("get") @ApiOperation("用户列表") public UserModel getUser() { log.info("查询用户列表"); return userService.getById(1); } }

改完后要重启一下项目,重启完成后,我们在浏览器地址栏中输入swagger的地址

http://localhost:520/swagger-ui/index.html

(注意:swagger 3.x版本请求地址和2.x请求地址有些不一样,当然2.x的请求地址在这里也能请求成功,不过返回还是2.x版本的UI界面,而3.x是新的UI界面,新界面如下图)
Java:(二)自己动手实现一个好用的SpringBoot后端框架(集成代码生成工具、Swagger)_第5张图片
可以看到Swagger自动帮我们把接口列表生成出来了,我们来调用测试一下

Java:(二)自己动手实现一个好用的SpringBoot后端框架(集成代码生成工具、Swagger)_第6张图片
可以看到成功查到了数据,证明我们Swagger集成没有问题

注:如果后端只需要用到单体架构(中小型项目),使用基于cookie-session + jsp或者thymeleaf的方案,至此我们只需要再集成一些其它组件就可以专注于业务开发了


接下来我们可以把用户模块的列表、新增、修改、删除、禁用等功能快速写出来,如果对MybatisPlus的使用不熟的同学可以顺便拿用户模块的CRUD练练手,后面讲用户权限设计的时候,用户模块我会重新设计

当我们在用户模块中写了一堆接口后,我们是不是会想:咦,这些接口好像都可以被人直接调用,似乎不太安全,我们能不能想一个方式来解决这个问题呢?

这里可以回顾一下,之前我们做项目,如果是基于cookie-session模式的项目,在用户登录成功后,我们可以把用户信息存在session中,用户接下来的请求,我们都先检查一下session中有没有登录成功的用户信息,如果有,则证明此次请求合法,如果没有,则代表未登录或者没有权限,在前后端分离的项目中,session方案似乎就不太适用了,那我们应该怎么做呢?

这个时候我们可以想到使用token令牌的方式,比如jwt来生成token令牌(对jwt不了解的同学先百度了解一下,或者看我这篇文章里的大致介绍),用户登录成功后,我们颁发一个带过期时间的凭证(token)给用户,用户接下来的请求中,每次都必须在请求头中带上这个凭证(token),我们从凭证(token)中解析出用户信息,如果凭证(token)没过期且能解析出用户信息,则代表此次请求合法,反之则代表没登录或者不合法

目前我们先不考虑通过角色权限来更细粒度的控制接口权限,我们暂且先只通过token来控制接口访问,后续文章中我会将角色权限这添加进来配合jwt token一起来实现接口权限控制


本篇就暂且讲到这里,下一节我们来讲jwt怎么在本项目中具体使用

上一篇地址:《(一)自己动手实现一个好用的SpringBoot后端框架(项目搭建、组件依赖)》

你可能感兴趣的:(Java,spring,boot,java,web)