点击上方蓝色“方志朋”,选择“设为星标”

回复“666”获取独家整理的学习资料!


作者:任务加油站

原文:toutiao.com/i6861456496740270604

1、技术选型

  • 解析器:FastJSON

  • 开发工具:JDK1.8 、Gradle、IDEA

  • 技术框架:SpringBoot 2.1.5.RELEASE

  • ORM技术:MyBatisPlus3.1.2

  • 数据库:MySQL8.0.21

  • Apache 工具:HttpClient、Lang3

  • Git代码版本控制

  • Web服务器:undertow

  • hutool 国产工具类包

  • lombok 简化代码工具 -druid 数据库连接池框架

2、Spring Boot 发展路线简要描述

  • 随着动态语言的流行 (Ruby、Groovy、Scala、Node.js),Java 的开发显得格外的笨重:繁多的配置、低下的开发效率、复杂的部署流程以及第三方技术集成难度大。

  • 在上述环境下,Spring Boot 应运而生。它使用“习惯优于配置”(项目中存在大量的配置,此外还内置了一个习惯性的配置,让你无需手动进行配置)的理念让你的项目快速的运行起来。使用 Spring Boot 很容易创建一个独立运行(运行 Jar,内嵌 Servlet 容器)准生产级别的基于 Spring 框架的项目,使用 Spring Boot 你可以不用或者只需很少的 Spring 配置。

3、SpringBoot插件使用

  • spring-boot-devtools 实现热部署,实际开发过程中,修改应用的业务逻辑时常常需要重启应用,这显得非常繁琐,降低了开发效率,所以热部署对于开发来说显得十分必要了

  • spring-boot-starter-aop 此插件没什么好说的了,aop是spring的两大功能模块之一,功能非常强大,为解耦提供了非常优秀的解决方案。如:面向方面编程

  • spring-boot-starter-undertow 与spring boot 内置undertow 插件

  • spring-boot-starter-test 测试工具

  • mybatis-plus-boot-starter 与spring boot整合MyBatisPlus的jar

  • spring-boot-configuration-processor 整合SpringBoot配置提示

4、fastJson

阿里JSON解析器,详细文档请看官方 https://github.com/alibaba/fastjson

5、Hutool

Hutool是一个Java工具包,也只是一个工具包,它帮助我们简化每一行代码,减少每一个方法,让Java语言也可以“甜甜的”。Hutool最初是我项目中“util”包的一个整理,后来慢慢积累并加入更多非业务相关功能,并广泛学习其它开源项目精髓,经过自己整理修改,最终形成丰富的开源工具集。

6、Gradle

  • Gradle是一个基于Apache Ant和Apache Maven概念的项目自动化构建开源工具。它使用一种基于Groovy的特定领域语言(DSL)来声明项目设置,目前也增加了基于Kotlin语言的kotlin-based DSL,抛弃了基于XML的各种繁琐配置

  • 官方 https://gradle.org/

  • 不会Gradle的先自己补习一下,比如:安装Gradle,配置环境变量,一些jar引入如何配置,基本使用怎么使用

7、工程结构

此工程是通过Kotlin+SpringBoot+MyBatisPlus搭建最简洁的前后端分离框架 框架升级Java语言SpringBoot+MyBatisPlus3.X+Gradle版本的框架,想学习Kotlin版本的请点击蓝色文章进行下载源代码。

8、Gradle配置

plugins {id 'java'id 'idea'
}/*** 使用Groovy语言语法定义版本号变量*/
def spring_boot_version = "2.1.5.RELEASE"
def mybatis_plus_version = "3.1.2"
def mysql_version = "8.0.21"
def druid_version = "1.1.23"
def logback_version = "1.2.1"
def fastjson_version = "1.2.73"
def lombok_version = "1.18.12"
def lang_version = "3.4"
def io_version = "2.6"
def guava_version = "18.0"
def hutool_version = "5.3.10"group = 'com.flong'
version = '0.0.1-SNAPSHOT'//jdk版本
sourceCompatibility = JavaVersion.VERSION_1_8
targetCompatibility = JavaVersion.VERSION_1_8repositories {//指定阿里云镜像maven {url 'http://maven.aliyun.com/nexus/content/groups/public/'}mavenLocal()mavenCentral()
}/*** 1、implementation 履行 、compile 编译* 2、Gradle使用双引号可 ${变量}可以放入引号里面,单引号是不可以的。* 3、Gragle使用lombok需要引入annotationProcessor注解,否则不能使用lombok.* 4、mybatis-plus3.2.x以上版本引用了Kotlin的支持* 5、高版本Springboogt在spring-boot-dependencies-2.3.0.RELEASE.pom里面引入了mysql8.0.2的`<mysql.version>8.0.20</mysql.version>`配置*/
dependencies {implementation "org.springframework.boot:spring-boot-starter:${spring_boot_version}"//排除tomcat使用undertowcompile("org.springframework.boot:spring-boot-starter-web:${spring_boot_version}") {exclude module: "spring-boot-starter-tomcat"}compile "org.springframework.boot:spring-boot-starter-undertow:${spring_boot_version}"//runtime group: 'mysql', name: 'mysql-connector-java', version: '5.1.42'compile "org.springframework.boot:spring-boot-devtools:${spring_boot_version}"compile "org.springframework.boot:spring-boot-configuration-processor:${spring_boot_version}"compile "org.springframework.boot:spring-boot-starter-test:${spring_boot_version}"compile "com.baomidou:mybatis-plus-extension:${mybatis_plus_version}"compile "com.baomidou:mybatis-plus-boot-starter:${mybatis_plus_version}"compile "mysql:mysql-connector-java:${mysql_version}"compile "com.alibaba:druid:${druid_version}"compile "ch.qos.logback:logback-classic:${logback_version}"compile "com.alibaba:fastjson:${fastjson_version}"annotationProcessor "org.projectlombok:lombok:${lombok_version}"compileOnly "org.projectlombok:lombok:${lombok_version}"//testAnnotationProcessor "org.projectlombok:lombok:${lombok_version}"//testCompileOnly "org.projectlombok:lombok:${lombok_version}"compile "org.apache.commons:commons-lang3:${lang_version}"compile "commons-io:commons-io:${io_version}"compile "com.google.guava:guava:${guava_version}"compile  "cn.hutool:hutool-all:${hutool_version}"
}tasks.withType(JavaCompile) {options.encoding = "UTF-8"
}[compileJava, javadoc, compileTestJava]*.options*.encoding = "UTF-8"

9、数据库SQL脚本

  • -- 创建表字段不建议用is开头,在我Kotlin+Springboot+MyBatisPlus2.x整合也提到此问题,

  • -- 故此整合MyBatisPlus3.x版本,把表的is_deleted字段修改成del_flag,阿里开发手册也提到此问题.

DROP TABLE IF EXISTS `t_user`;
CREATE TABLE `t_user` (`id` int(11) NOT NULL AUTO_INCREMENT COMMENT '自增id',`user_id` bigint(20) unsigned NOT NULL DEFAULT '0' COMMENT '用户Id主键,IdWork生成',`user_name` varchar(255) DEFAULT '' COMMENT '用户名',`pass_word` varchar(255) DEFAULT '' COMMENT '密码',`del_flag` int(2) unsigned NOT NULL DEFAULT '0' COMMENT '是否删除,0-不删除,1-删除',`create_time` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',PRIMARY KEY (`user_id`) USING BTREE,UNIQUE KEY `id` (`id`)USING BTREE
)ENGINE=INNODB DEFAULT CHARSET=utf8mb4 COMMENT='用户表';

10、SpringBoot与MyBatisPlus3整合分页代码

@Configuration
public class MyBatisPlusConfig {/*** 分页插件*/@Beanpublic PaginationInterceptor paginationInterceptor() {return new PaginationInterceptor();}
}

11、SpringBoot与MyBatisPlus3分页条件组装器

/*** 将condition数据转换成wrapper*/
public class BuildConditionWrapper {public static <T> QueryWrapper<T> build(List<Condition> conditions, Class<T> clazz) {//初始化mybatis条件构造器QueryWrapper wrapper = Wrappers.query();if (conditions == null || conditions.size() == 0) {return wrapper;}try {for (int i = 0; i < conditions.size(); i++) {Condition condition = conditions.get(i);if (condition.getFieldName() == null) {throw new BaseException("调用搜索接口时,缺少关键字[fieldName]!");}//列名称String columnName = getColumnName(condition.getFieldName(), clazz);if (condition == null || condition.getOperation() == null) {throw new BaseException("操作符不能为空!");}switch (condition.getOperation()) {//等于case EQ:wrapper.eq(columnName, condition.getValue());break;//大于case GT:wrapper.gt(columnName, condition.getValue());break;//小于case LT:wrapper.lt(columnName, condition.getValue());break;//不等于case NEQ:wrapper.ne(columnName, condition.getValue());break;//大于等于case GTANDEQ:wrapper.ge(columnName, condition.getValue());break;//小于等于case LTANDEQ:wrapper.le(columnName, condition.getValue());break;case LIKE:wrapper.like(columnName, condition.getValue());break;case ISNULL:wrapper.isNull(columnName);break;case IN://value :1,2,3,4,5,6wrapper.inSql(columnName, condition.getValue());break;default:break;}if (condition.getJoinType() == JoinType.OR && i < conditions.size() - 1) {//下个条件为or连接且非最后一个条件,使用or进行连接wrapper.or();}}return wrapper;} catch (Exception e) {throw new BaseException("查询条件不存在");}}/*** @Descript 此条件构建包装器方法是支持多个表组装成SQL字段的虚拟表,不支持实际存在的表* @Date 2019/6/21 13:32* @Author liangjl*/public static <T> QueryWrapper<T> buildWarpper(List<Condition> conditions) {//初始化mybatis条件构造器QueryWrapper wrapper = Wrappers.query();if (conditions == null || conditions.size() == 0) {return wrapper;}try {for (int i = 0; i < conditions.size(); i++) {Condition condition = conditions.get(i);if (condition.getFieldName() == null) {throw new BaseException("调用搜索接口时,缺少关键字[fieldName]!");}//列名称String columnName = condition.getFieldName();if (condition == null || condition.getOperation() == null) {throw new BaseException("操作符不能为空!");}switch (condition.getOperation()) {//等于case EQ:wrapper.eq(columnName, condition.getValue());break;//大于case GT:wrapper.gt(columnName, condition.getValue());break;//小于case LT:wrapper.lt(columnName, condition.getValue());break;//不等于case NEQ:wrapper.ne(columnName, condition.getValue());break;//大于等于case GTANDEQ:wrapper.ge(columnName, condition.getValue());break;//小于等于case LTANDEQ:wrapper.le(columnName, condition.getValue());break;case LIKE:wrapper.like(columnName, condition.getValue());break;case IN://value :1,2,3,4,5,6wrapper.inSql(columnName, condition.getValue());break;default:break;}if (condition.getJoinType() == JoinType.OR && i < conditions.size() - 1) {//下个条件为or连接且非最后一个条件,使用or进行连接wrapper.or();}}return wrapper;} catch (Exception e) {throw new BaseException("查询条件不存在");}}/**** @Descript 获取指定实体Bean的字段属性* @Date 2019/6/19 14:51* @Author liangjl*/public static String getColumnName(String fieldName, Class clazz) {try {//获取泛型类型字段Field field = clazz.getDeclaredField(fieldName);TableField tableFieldAnno = field.getAnnotation(TableField.class);String columnName = "";//获取对应数据库字段if (tableFieldAnno != null && StrUtil.isNotBlank(tableFieldAnno.value())) {//已定义数据库字段,取定义值columnName = tableFieldAnno.value();} else {//未指定数据库字段,默认驼峰转下划线columnName = NamingStrategyUtils.camelToUnderline(field.getName());}return columnName;} catch (NoSuchFieldException e) {throw new BaseException("查询条件不存在");}}}

12、 实体

@Data
@Builder
@AllArgsConstructor
@NoArgsConstructor
@EqualsAndHashCode(callSuper=false)
@TableName("t_user")
public class User extends Model<User> implements Serializable {@TableId(type = IdType.ID_WORKER)private Long userId;/*** 用户名*/private String userName;/*** 密码*/private String passWord;/*** 逻辑删除(0-未删除,1-已删除)*/@TableLogicprivate String delFlag;/*** 创建时间,允许为空,让数据库自动生成即可*/private Date createTime;
}

13、 Mapper

BaseMapper是继承了mybatisplus底层的代码

public interface UserMapper extends BaseMapper<User> {}

14、 Service

ServiceImplr是继承了mybatisplus底层的代码

@Service
public class UserService extends ServiceImpl<UserMapper, User> {}

15 、controller

  • 控制层主要实现CURD,增加,修改,查询,删除、分页无大常规操作接口操作

  • 用户分页,参数有多个使用下标索引进行处理.如果有两个参数(如用户名和地址):conditionList[0].fieldName=userName、 conditionList[0].fieldName=address

  • 查询是通过反射fieldName进行去获取表结构userName、address 字段的。

  • 未转码请求分页地址: http://localhost:7011/user/page?conditionList[0].fieldName=userName&conditionList[0].operation=LIKE&conditionList[0].value=周

  • 已转码请求分页地址: http://localhost:7011/user/page?conditionList[0].fieldName=userName&conditionList[0].operation=LIKE&conditionList[0].value=%E5%91%A8

/*** @Author:liangjl* @Date:2020-08-16* @Description:用户控制层*/
@RestController
@RequestMapping("/user")
public class UserController {@Autowiredprivate UserMapper userMapper;@Autowiredprivate UserService userService;/*** 添加*/@RequestMapping("/add")public void add() {userMapper.insert(User.builder().userName("周伯通").passWord("123456").build());}/*** 修改* @param user*/@PutMapping("/updateById")public void updateById(@RequestBody User user) {userMapper.updateById(user);}/*** 删除通过多个主键Id进行删除* @param ids*/@DeleteMapping("/deleteByIds")public void deleteByIds(@RequestBody List<String> ids) {userMapper.deleteBatchIds(ids);}/*** 通过指定Id进行查询** @param userId*/@GetMapping("/getOne/{userId}")public void getOne(@PathVariable("userId") Long userId) {User user = userMapper.selectById(userId);System.out.println(JSON.toJSON(user));}/*** 用户分页,参数有多个使用下标索引进行处理.如果有两个参数(如用户名和地址):conditionList[0].fieldName=userName、 conditionList[0].fieldName=address* 未转码请求分页地址: http://localhost:7011/user/page?conditionList[0].fieldName=userName&conditionList[0].operation=LIKE&conditionList[0].value=周* 已转码请求分页地址: http://localhost:7011/user/page?conditionList[0].fieldName=userName&conditionList[0].operation=LIKE&conditionList[0].value=%E5%91%A8* @param page* @param conditions 条件* @return*/@GetMapping("/page")public IPage<User> page(Page page, Conditions conditions) {QueryWrapper<User> build = BuildConditionWrapper.build(conditions.getConditionList(), User.class);//通过lambda反射找到User实体类的createTime自动进行排序build.lambda().orderByDesc(User::getCreateTime);return userService.page(page, build);}}

16、WebCofig工具类统一处理配置

  • 消息转换器,中文乱码,Long的精度长度问题,时间格式等问题

  • cors 跨域支持 可以用@CrossOrigin在controller上单独设置

  • 统一处理请求URL拦截器

@Configuration
@ConditionalOnClass(WebMvcConfigurer.class)
@Order(Ordered.HIGHEST_PRECEDENCE)
public class WebConfig implements WebMvcConfigurer {@Beanpublic HttpMessageConverters customConverters() {//创建fastJson消息转换器FastJsonHttpMessageConverter fastJsonConverter = new FastJsonHttpMessageConverter();//创建配置类FastJsonConfig fastJsonConfig = new FastJsonConfig();//修改配置返回内容的过滤fastJsonConfig.setSerializerFeatures(// 格式化SerializerFeature.PrettyFormat,// 可解决long精度丢失 但会有带来相应的中文问题//SerializerFeature.BrowserCompatible,// 消除对同一对象循环引用的问题,默认为false(如果不配置有可能会进入死循环)SerializerFeature.DisableCircularReferenceDetect,// 是否输出值为null的字段,默认为falseSerializerFeature.WriteMapNullValue,// 字符类型字段如果为null,输出为"",而非nullSerializerFeature.WriteNullStringAsEmpty,// List字段如果为null,输出为[],而非nullSerializerFeature.WriteNullListAsEmpty);// 日期格式fastJsonConfig.setDateFormat("yyyy-MM-dd HH:mm:ss");// long精度问题SerializeConfig serializeConfig = SerializeConfig.globalInstance;serializeConfig.put(BigInteger.class, ToStringSerializer.instance);serializeConfig.put(Long.class, ToStringSerializer.instance);serializeConfig.put(Long.TYPE, ToStringSerializer.instance);fastJsonConfig.setSerializeConfig(serializeConfig);//处理中文乱码问题List<MediaType> fastMediaTypes = new ArrayList<>();fastMediaTypes.add(MediaType.APPLICATION_JSON_UTF8);fastJsonConverter.setSupportedMediaTypes(fastMediaTypes);fastJsonConverter.setFastJsonConfig(fastJsonConfig);//将fastjson添加到视图消息转换器列表内return new HttpMessageConverters(fastJsonConverter);}/*** 拦截器*/@Overridepublic void addInterceptors(InterceptorRegistry registry) {//registry.addInterceptor(logInterceptor).addPathPatterns("/**");//registry.addInterceptor(apiInterceptor).addPathPatterns("/**");}/*** cors 跨域支持 可以用@CrossOrigin在controller上单独设置*/@Overridepublic void addCorsMappings(CorsRegistry registry) {registry.addMapping("/**")//设置允许跨域请求的域名.allowedOrigins("*")//设置允许的方法.allowedMethods("*")//设置允许的头信息.allowedHeaders("*")//是否允许证书 不再默认开启.allowCredentials(Boolean.TRUE);}
}

17、运行结果

  • 添加 http://localhost:7011/user/add

  • 分页 http://localhost:7011/user/page?conditionList[0].fieldName=userName&conditionList[0].operation=LIKE&conditionList[0].value=%E5%91%A8

  • 默认当前current 为1当前第一页,size为10,当前页可以显示10条数据,也可以根据自己的情况进行自定义

  • http://localhost:7011/user/page?current=1&size=20&conditionList[0].fieldName=userName&conditionList[0].operation=LIKE&conditionList[0].value=%E5%91%A8

18、工程代码与说明

  • 1 、以上问题都是根据自己学习实际情况进行总结整理,除了技术问题查很多网上资料通过进行学习之后梳理。

  • 2、 在学习过程中也遇到很多困难和疑点,如有问题或误点,望各位老司机多多指出或者提出建议。本人会采纳各种好建议和正确方式不断完善现况,人在成长过程中的需要优质的养料。

  • 3、 导入代码的时候遇到最多的问题,我想应该是Maven较多,此时不懂maven的童鞋们可以通过自身情况,进行网上查资料学习。如通过网上找资料长时间解决不了,或者框架有不明白可以通过博客留言,在能力范围内会尽力帮助大家解决问题所在,希望在过程中一起进步,一起成长。

  • 工程代码在 base 分支 https://github.com/jilongliang/springboot/tree/base

热门内容:
  • 道友自诉:入职中软一个月(外包华为)就离职了!

  • 腾讯推出高性能 RPC 开发框架

  • 再见了SpringMVC,这个框架有点厉害,甚至干掉了Servlet!

  • 原来 Elasticsearch 还可以这么理解

  • 干掉Navicat:正版,MySQL官方客户端真香!

最近面试BAT,整理一份面试资料《Java面试BAT通关手册》,覆盖了Java核心技术、JVM、Java并发、SSM、微服务、数据库、数据结构等等。获取方式:点“在看”,关注公众号并回复 666 领取,更多内容陆续奉上。
明天见(。・ω・。)

Spring Boot+Gradle+ MyBatisPlus3.x搭建企业级的后台分离框架相关推荐

  1. gradle官方文档_Spring Boot+Gradle+MyBatisPlus3.x搭建企业级的后台分离框架

    你再主动一点点   我们就有故事了 原文:toutiao.com/i6861456496740270604 1.技术选型 解析器:FastJSON 开发工具:JDK1.8 .Gradle.IDEA 技 ...

  2. Spring boot Gradle项目搭建

    Spring boot Gradle项目搭建 使用IDEA创建Gradle工程     操作大致为:File->new->Project->Gradle(在左侧选项栏中)     创 ...

  3. spring boot / cloud (十七) 快速搭建注册中心和配置中心

    spring boot / cloud (十七) 快速搭建注册中心和配置中心 本文将使用spring cloud的eureka和config server来搭建. 然后搭建的模式,有很多种,本文主要聊 ...

  4. 从零搭建一个 Spring Boot 开发环境!Spring Boot+Mybatis+Swagger2 环境搭建

    从零搭建一个 Spring Boot 开发环境!Spring Boot+Mybatis+Swagger2 环境搭建 本文简介 为什么使用Spring Boot 搭建怎样一个环境 开发环境 导入快速启动 ...

  5. spring boot微服务项目搭建

    第一章 SpringBoot介绍 1 简介 Spring Boot是一个便捷搭建基于spring工程的脚手架:作用是帮助开发人员快速搭建大型的spring 项目.简化工程的配置和依赖管理:开发人员把时 ...

  6. Spring Boot Gradle 瘦身打包 thinJar,分离 lib jar 依赖

    原文地址:weiku.co/article/135/ ,欢迎转载 需求背景: srping boot 2.0+ 打包生产的 fat jar 虽然部署起来很方便,但将所有依赖都打包到一个 jar 包中使 ...

  7. 【Spring Cloud 基础设施搭建系列】Spring Cloud Demo项目 Spring Boot Test集成测试环境搭建

    文章目录 集成测试 @SpringBootTest的集成测试 Spring Boot Test集成测试环境搭建 参考 源代码 集成测试 集成测试(Integration Testing,缩写为INT) ...

  8. Spring Boot 学习(一) 快速搭建SpringBoot 项目

    快速搭建一个 Spring Boot 项目 部分参考于<深入实践Spring Boot>.<Spring实战 第四版>与程序猿DD的有关博客. 参考(嘟嘟独立博客):http: ...

  9. Spring Boot gradle 打包瘦身减少jar包体积 含demo

    Spring Boot 1.5.x 打包 demo项目地址 https://gitee.com/youngboyvip/package-example 解决问题 Spring Boot 项目包太大上传 ...

最新文章

  1. CSS之布局(文档流)
  2. android 6gb和8gb区别,手机6GB内存和8GB内存的差距到底有多大?你可能被忽悠了!...
  3. Android开发7——android.database.CursorIndexOutOfBoundsException:Index -1 requested
  4. 2021-03-07 英文写作中的“so that“和“such that“
  5. AG9 Service order创建好之后,要自动通过middleware传其他系统去 disable
  6. 1.原生js封装的获取某一天是当年的第几周方法
  7. 知识资产投资——《程序员修炼之道》的建议
  8. 【转】android实现退出整个工程
  9. Javascript: IE中命名函数直接量的Bug?
  10. mysql5.5java安装_配置非安装版的mysql 5.5
  11. 全向轮机器人应用平台
  12. Tomcat下使用 telnet命令连接
  13. 浅谈算法和数据结构: 六 符号表及其基本实现
  14. SVM多分类算法-一对一
  15. Arduino - 红外接收
  16. Google技巧:crack web sites
  17. 离散数学 第一章 部分课后习题
  18. 误删除vmdk文件恢复办法
  19. 2020计算机二级office大纲,2020计算机二级考试MS OFFICE 考试内容大纲.doc
  20. 前序遍历、中序遍历、后序遍历层序遍历详解附代码(数据结构C语言)

热门文章

  1. Java(三):序列化
  2. 题解 UVA11354 【Bond】
  3. html css 布局知识概况
  4. 使用PowerShell登陆多台Windows,测试DCAgent方法
  5. 关于UNION和UNION ALL的区别
  6. jquery总结和注意事项
  7. C#实现HttpPost提交文件
  8. 一晚上就能让你小腹变小的方法 - 健康程序员,至尚生活!
  9. 谢文睿:西瓜书 + 南瓜书 吃瓜系列 9. 集成学习(上)
  10. 参考答案:05 实对称矩阵与二次型