动手写个java快速开发框架-(2)集成mybatis plus

对于一个快速开发框架来说,离不开一个很重要的功能模块那就是数据库访问,目前在日常开发中用的最多的当然就是mybatis了,但是mybatis同样也会给我们带来很多重复的开发工作,例如一般的CRUD,也有很多开源框架在mybatis的基础上又封装了基础CRUD的基础类,但是这样的坏处也显而易见,和mybatis耦合很强,这里在我们的框架中,我们直接集成国内比较好的mybatis组件-mybatis plus,这个组件在github上的人气也很高,因为其底层原理很简单,所以大家也可以借助于该组件做一些深度二开,并且与mybatis没有强耦合,是两个独立的jar包。mybatis plus基于mybatis定义了很多Base范性基类,开发者只要将自己的Mapper和service继承自这些范性基类就可以直接继承基础的CRUD的方法,可以大幅减少代码量。

下面我们就拿上一篇提到的系统日志记录数据库的功能来举例子,让大家体验下在自己的框架中集成mybatis plus。

POM增加依赖

在之前框架的POM中新增以下依赖,因为我们框架是基于springboot开发所以这里我们直接使用mybatis plus为springboot开发的组件‘mybatis-plus-boot-starter’,可以更加方便和springboot集成,当然你也可以依赖mybatis plus基础库,但是要做些配置,具体可以参考官网文档,所以这里偷懒直接用了boot组件。

除了依赖mybatis plus的库,当然访问数据库还要依赖相关数据库的connector,只要是mybatis支持的数据库,当然plus也都可以支持,例子中我们用了大家日常用的最多的mysql,使用其他数据库的需要替换掉依赖的数据库connector,yml或property里的配置也需要进行调整。


    com.baomidou
    mybatis-plus-boot-starter
    ${mybatis-plus-boot-starter.version}


    mysql
    mysql-connector-java
    ${mysql.version}


mybatis plus相关资料可以查看github,里面的文档还是比较完善的:https://github.com/baomidou/mybatis-plus

配置

因为mybatis plus功能太完善,框架中不需要做任何二开,直接使用,我们直接拿上一篇提到的日志模块来举例,上一篇是写到文件中,这里我们将同样的数据写到数据库中。

首先我们在数据库中建立一张名叫sys_log的表,具体的建表sql可以参看sql目录下的建表语句,里面的字段和上一篇定义的SysLog实体类的字段一样,具体参看源码。

接下来在application-xxx.yml中配置datasource:

spring:
  datasource:
    url: jdbc:mysql://123.206.118.12:3306/mkframework?useUnicode=true&characterEncoding=utf-8
    username: root
    password: Dnn198411!
    driverClassName: com.mysql.jdbc.Driver

在application.yml中配置mybatis-plus相关信息,plus中有很多配置参数,这里只是配置了日常会用到的一些参数配置,还有其他的配置大家可以参考plus的github官方文档资料。

#mybatis
mybatis-plus:
  mapper-locations: classpath:/mapper/*Mapper.xml
  #实体扫描,多个package用逗号或者分号分隔
  typeAliasesPackage: com.monkey01.common.domain
#  typeEnumsPackage: com.baomidou.springboot.entity.enums
  global-config:
    # 数据库相关配置
    db-config:
      #主键类型  AUTO:"数据库ID自增", INPUT:"用户输入ID",ID_WORKER:"全局唯一ID (数字类型唯一ID)", UUID:"全局唯一ID UUID";
      id-type: id_worker
      #字段策略 IGNORED:"忽略判断",NOT_NULL:"非 NULL 判断"),NOT_EMPTY:"非空判断"
      field-strategy: not_empty
      #驼峰下划线转换
      column-underline: true
      #数据库大写下划线转换
      #capital-mode: true
      #逻辑删除配置
      logic-delete-value: 0
      logic-not-delete-value: 1
      db-type: h2
    #刷新mapper 调试神器
    refresh: true
  # 原生配置
  configuration:
    map-underscore-to-camel-case: true
    cache-enabled: false

定义DO、Mapper、Service类

数据库sys_log我们需要定义一个对应的DO和它进行ORM映射。

@TableName("sys_log")
public class SysLogDO implements Serializable {
    @TableId
    private Long id;
    //用户名
    private String username;
    //用户操作
    private String operation;
    //请求方法
    private String method;
    //请求URL
    private String url;
    //请求参数
    private String params;
    //执行时长(毫秒)
    private Long time;
    //IP地址
    private String ip;
    //创建时间
    private Date createDate;
    //...省略setter、getter
    }

大家一定注意到这里和其他的POJO的区别,那就是在类名前面和id字段定义前面都有注解,这里简单解释下。和mybatis一样,我们日常将一个DO类和数据库表关联起来有两种方法,一种是使用传统的mapper.xml将DO类和数据库表关联起来,字段名如果不一样的,也需要进行字段之间的映射关系定义,还有一定方法是在DO类中定义注解,来将原先定义在XML中的信息定义到注解里。当然plus会对这种传统的定义方法进行改良,我们只需要在DO类前面加上@TableName(“XXX”)在注解的value中写上数据库表名就可以将该DO类与对应的数据库表映射起来了。如果表中的字段和我们定义的DO类的字段名称完全一样或者数据库表字段只是用下划线替代了DO类中字段的驼峰结构,那么plus会自动进行映射字段,如果是将下划线转为驼峰定义需要在上面的配置中将转换设置为true,column-underline: true

还可以看到我们在id字段定义的前面加上了@TableID,该注解只可以定义在使用int或者Long定义的字段上用于自增id生成,在plus的配置中还可以配置生成id的算法,这里plus官方推荐的是使用开源sequence项目生成的id,只需要在yml中plus配置下配置id-type: id_worker就可以了。

定义好了DO后,还需要和mybatis一样,还需要定义mapper接口,下面我们看下我们要实现SysLog的增删改查需要怎样定义一个mapper接口。

@Mapper
public interface SysLogMapper extends BaseMapper {
}

就是这么简单,如果只是基本的增删改查就是这么简单,一个方法都不需要定义,只需要让mapper接口继承自BaseMapper这个范性基类,里面的范型定义为需要操作的DO类。我们看下BaseMapper源码就知道为什么这么简单就可以实现常用的增删改查功能了。

public interface BaseMapper {
    Integer insert(T var1);
    Integer deleteById(Serializable var1);
    Integer deleteByMap(@Param("cm") Map var1);
    Integer delete(@Param("ew") Wrapper var1);
    Integer deleteBatchIds(@Param("coll") Collection var1);
    Integer updateById(@Param("et") T var1);
    Integer update(@Param("et") T var1, @Param("ew") Wrapper var2);
    T selectById(Serializable var1);
    List selectBatchIds(@Param("coll") Collection var1);
    List selectByMap(@Param("cm") Map var1);
    T selectOne(@Param("ew") Wrapper var1);
    Integer selectCount(@Param("ew") Wrapper var1);
    List selectList(@Param("ew") Wrapper var1);
    List> selectMaps(@Param("ew") Wrapper var1);
    List selectObjs(@Param("ew") Wrapper var1);
    IPage selectPage(IPage var1, @Param("ew") Wrapper var2);
    IPage> selectMapsPage(IPage var1, @Param("ew") Wrapper var2);
}
 
 

是不是从这里就能发现,我们常用的一些数据库操作都包涵在里面了,包括分页也都在里面,是不是一下子效率提升了很多。

当然dao的mapper类定义好了以后就是定义service层的service类了。

@Service("sysLogService")
public class SysLogServiceImpl extends ServiceImpl implements SysLogService {
    private Logger logger = LoggerFactory.getLogger(getClass());
    @Override
    public void saveSysLog(SysLogDO sysLogDO) {
        this.saveSysLogFile(sysLogDO);
        this.saveSysLogDB(sysLogDO);
    }
    private void saveSysLogFile(SysLogDO sysLogDO){
        logger.info(sysLogDO.toString());
    }
    private boolean saveSysLogDB(SysLogDO sysLogDO) {
        return this.save(sysLogDO);
    }
}

从这里可以发现只需要让service实现类继承plus的ServiceImpl范型类就可以了,在范型类中需要定义上这个service对应的mapper类和实体DO类,然后在service实现类中就可以通过this调用上面我们看到的常用的数据库表操作方法了。

能解决大量重复代码的开发工作的核心就是这个ServiceImpl范型类和上面提到的BaseMapper接口,这里建议大家都可以看看ServiceImpl的源码,这里的设计方法其实可以用到很多我们常用的代码中。

自动代码生成

当然大家也会发现上面写的DO、Mapper、Service类也是一个重复的过程,我们可以通过plus为我们提供的自动代码生成方法来自动生成这些DO、Mapper、Service代码,这里我们可以很方便的实现这些重复的代码,具体可以参考test目录下的GeneratorServiceEntity类,在类里面需要配置数据库的相关信息,还有需要自动生成的类信息。都配置好厚直接执行这个Test方法就可以自动生成这些类了,减少了很多重复的工作。

总结

因为目前的mybatis和mybatis plus在orm这块已经做的非常完善了,真的没必要再自研一套,直接拿来用,对于mybatis的源码建议大家有空也可以读读,不难,但是里面涉及到很多好的框架设计方法,值得去学习。

本篇对应的代码tag是v0.2,大家以点击下载https://github.com/feiweiwei/MkFramework4java/releases/tag/v0.2,当然也可以通过git clone –b v0.2 https://github.com/feiweiwei/MkFramework4java.git下载。

你可能感兴趣的:(动手写个java快速开发框架-(2)集成mybatis plus)