MyBatis Generator 使用与原理(上)
Contents
这两天在看一个开源的小说管理平台的代码,发现它的项目使用了MyBatis Generator来生成代码操作数据库,花了两个早上的时间研究了一下,确实是很不错的工具,能在我们的开发过程中省掉不少的工作。
mybatis generator 的使用大致分成几步:
- 创建配置文件
- 保存配置文件到本地
- 执行 MyBatis Generator
我们以一个例子来说明如何使用 MyBaits Generator,项目的结构如下所示:
├── pom.xml
├── README.md
├── src
│ ├── main
│ │ ├── java
│ │ │ └── com
│ │ │ └── xueqiang
│ │ │ └── footmark
│ │ │ ├── controller
│ │ │ ├── FootmarkApplication.java
│ │ │ ├── model
│ │ │ ├── service
│ │ │ └── utils
│ │ └── resources
│ │ ├── application.properties
│ │ ├── log4j.properties
│ │ ├── mybatis
│ │ │ └── generator-configuration.xml
│ └── test
1. 配置文件
在 resources/mybatis/
目录下创建配置文件 generator-configuration.xml
,该文件的具体内容如下所示:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE generatorConfiguration
PUBLIC "-//mybatis.org//DTD MyBatis Generator Configuration 1.0//EN"
"http://mybatis.org/dtd/mybatis-generator-config_1_0.dtd">
<generatorConfiguration>
<!-- 全局配置文件,下面可以通过占位符的形式读取文件中的值 -->
<!-- <properties resource="db.properties"/>-->
<!-- 用来指定数据源驱动包(jar/zip)的绝对路径 -->
<classPathEntry location="D:\Users\xueqiang.chen\.m2\repository\mysql\mysql-connector-java\8.0.11\mysql-connector-java-8.0.11.jar"/>
<!-- 用于运行时的解析模式和具体的代码生成行为,对应org.mybatis.generator.config.Context类 -->
<!--
id:Context示例的唯一ID,用于输出错误信息时候作为唯一标记
targetRuntime:用于执行代码生成模式。可选值:
MyBatis3DynamicSql:动态SQL
MyBatis3Kotlin:基于Kotlin生成
MyBatis3:提供基本的基于动态SQL的CRUD方法和XXXByExample方法,会生成XML映射文件
MyBatis3Simple:提供基本的基于动态SQL的CRUD方法,会生成XML映射文件
MyBatis3DynamicSqlV1:已经过时,不推荐使用
defaultModeType:控制Domain类的生成行为。执行引擎为MyBatis3DynamicSql或者MyBatis3Kotlin时忽略此配置,可选值:
conditional:默认值,类似hierarchical,但是只有一个主键的时候会合并所有属性生成在同一个类。
flat:所有内容全部生成在一个对象中。
hierarchical:键生成一个XXKey对象,Blob等单独生成一个对象,其他简单属性在一个对象中
-->
<!--
context的内容需要按照顺序排列,否则会报错:
property->plugin->commentGenerator->connectionFactory|jdbcConnection->javaTypeResolver->javaModelGenerator->sqlMapGenerator->javaClientGenerator->table
-->
<context id="default" targetRuntime="MyBatis3DynamicSql">
<property name="javaFileEncoding" value="UTF-8"/>
<!-- <plugin type="org.mybatis.generator.plugins.SerializablePlugin"/>-->
<!--用于控制生成的实体的注释内容
suppressAllComments:是否生成注释
suppressDate:是否在注释中添加生成的时间戳
dateFormat:配合suppressDate使用,指定输出时间戳的格式
addRemarkComments:是否输出表和列的Comment信息-->
<commentGenerator>
<property name="suppressDate" value="true"/>
<property name="suppressAllComments" value="true"/>
</commentGenerator>
<!--用于指定数据源的连接信息,对应的类为org.mybatis.generator.config.JDBCConnectionConfiguration
driverClass:数据源驱动的全类名
connectionURL:JDBC的连接URL
userId:用户名
password:密码-->
<jdbcConnection driverClass="com.mysql.jdbc.Driver"
connectionURL="jdbc:mysql://127.0.0.1:3306/footmark"
userId="root"
password="mysql">
</jdbcConnection>
<!--用于解析和计算数据库列类型和Java类型的映射关系,该标签只包含一个type属性,用于指定org.mybatis.generator.api.JavaTypeResolver接口的实现类
forceBigDecimals:是否强制把所有的数字类型强制使用java.math.BigDecimal类型表示
useJSR310Types:是否支持JSR310,主要是JSR310的新日期类型
数据库JDBC类型 Java类型
DATE java.time.LocalDate
TIME java.time.LocalTime
TIMESTAMP java.time.LocalDateTime
TIME_WITH_TIMEZONE java.time.OffsetTime
TIMESTAMP_WITH_TIMEZONE java.time.OffsetDateTime-->
<javaTypeResolver>
<!-- 不强制把所有的数字类型转化为BigDecimal -->
<property name="forceBigDecimals" value="false" />
</javaTypeResolver>
<!--主要用于控制实体(Model)类的代码生成行为
targetPackage:生成的实体类的包名
targetProject:生成的实体类文件相对于项目(根目录)的位置
property:
constructorBased:是否生成一个带有所有字段属性的构造函数
enableSubPackages:是否允许通过Schema生成子包
exampleTargetPackage:生成的伴随实体类的Example类的包名
exampleTargetProject:生成的伴随实体类的Example类文件相对于项目(根目录)的位置
immutable:是否不可变
rootClass:为生成的实体类添加父类
trimStrings:Setter方法是否对字符串类型进行一次trim操作-->
<javaModelGenerator targetPackage="com.xueqiang.footmark.model.entity" targetProject="src/main/java">
<property name="enableSubPackages" value="true" />
<property name="trimStrings" value="true" />
</javaModelGenerator>
<!--主要用于控制XML映射文件的代码生成行为
targetPackage:生成的XML映射文件的包名
targetProject:生成的XML映射文件相对于项目(根目录)的位置,例如:src/main/resources
property:
enableSubPackages:是否允许通过Schema生成子包-->
<sqlMapGenerator targetPackage="mapper" targetProject="src/main/resources">
<property name="enableSubPackages" value="true" />
</sqlMapGenerator>
<!--主要用于控制Mapper接口的代码生成行为
type:Mapper接口生成策略.(<context>标签的targetRuntime属性为MyBatis3DynamicSql或者MyBatis3Kotlin时此属性配置忽略)
ANNOTATEDMAPPER:Mapper接口生成的时候依赖于注解和SqlProviders(也就是纯注解实现),不会生成XML映射文件。
XMLMAPPER:Mapper接口生成接口方法,对应的实现代码生成在XML映射文件中(也就是纯映射文件实现)
MIXEDMAPPER:Mapper接口生成的时候复杂的方法实现生成在XML映射文件中,而简单的实现通过注解和SqlProviders实现(也就是注解和映射文件混合实现)。
targetPackage:生成的Mapper接口的包名
targetProject:生成的Mapper接口文件相对于项目(根目录)的位置-->
<!--property属性:
enableSubPackages:是否允许通过Schema生成子包
useLegacyBuilder:是否通过SQL Builder生成动态SQL
rootInterface:为生成的Mapper接口添加父接口-->
<javaClientGenerator type="ANNOTATEDMAPPER" targetPackage="com.xueqiang.footmark.model.mapper" targetProject="src/main/java">
<property name="enableSubPackages" value="true" />
</javaClientGenerator>
<!--enableInsert 动态SQL提供类SqlProvider的类名称
enableSelectByPrimaryKey 是否允许生成selectByPrimaryKey方法
enableSelectByExample 是否允许生成selectByExample方法
enableUpdateByPrimaryKey 是否允许生成updateByPrimaryKey方法
enableDeleteByPrimaryKey 是否允许生成deleteByPrimaryKey方法
enableDeleteByExample 是否允许生成deleteByExample方法
enableCountByExample 是否允许生成countByExample方法
enableUpdateByExample 是否允许生成updateByExample方法
selectByPrimaryKeyQueryId value指定对应的主键列提供列表查询功能
selectByExampleQueryId value指定对应的查询ID提供列表查询功能-->
<table tableName="t_order"
enableCountByExample="false"
enableDeleteByExample="false"
enableSelectByExample="true"
enableUpdateByExample="false"
domainObjectName="Order"
mapperName="OrderMapper">
<generatedKey column="id" sqlStatement="MySql"/>
</table>
</context>
</generatorConfiguration>
上面的这个配置文件主要是按t_order
这个数据库表的属性生成整个 xml 配置文件的元素意义我们可以参考官方文档的介绍。