目录
切记!本博客只是提供一个思路,具体模板内容需要自己动手写,因为每个公司每个项目的框架可能稍有差异
切记!本博客只是提供一个思路,具体模板内容需要自己动手写,因为每个公司每个项目的框架可能稍有差异
写在前面
众所周知,MyBatis的xml配置以及domain实体类等等,重复的工作量非常大。很多小伙伴从网上找的自动生成代码的工具,生成的都跟自己实际项目中的不太一样,还要进行改造。
所以,我们可以手写一个适应项目中的增删改查一套模板,然后在此基础上进行开发,大大的减少了重复造轮子的时间。
生成原理
原理非常简单,将一些差异性的东西,使用占位符{xxxx}代替,然后读取模板文件,使用全局字符串替换即可。
例如domain模板文件
{copyright}
package com.cxf.domain.{packageName};
/**
* {tbChineseName}
*
* @author {user}
* @since {date}
*/
public class {upperBeanName} {
{domainFields}
{domainGetset}
}
生成的时候,只需要读取模板之后,使用String text = text.replace("{user}", user);即可将{user}里面的东西一键替换。
正常Controller、Service、Dao的生成
这几个很简单,基本就靠表名,替换一下类名就可以了。
模板实例
@RestController
@RequestMapping("/{beanParamName}s")
public class {controllerName} {
@Autowired
private {daoName} {daoParamName};
@PostMapping
@ApiOperation(value = "保存")
public {beanName} save(@RequestBody {beanName} {beanParamName}) {
{daoParamName}.save({beanParamName});
return {beanParamName};
}
@GetMapping("/{id}")
@ApiOperation(value = "根据id获取")
public {beanName} get(@PathVariable Long id) {
return {daoParamName}.getById(id);
}
@PutMapping
@ApiOperation(value = "修改")
public {beanName} update(@RequestBody {beanName} {beanParamName}) {
{daoParamName}.update({beanParamName});
return {beanParamName};
}
@GetMapping
@ApiOperation(value = "列表")
public PageTableResponse list(PageTableRequest request) {
return new PageTableHandler(new CountHandler() {
@Override
public int count(PageTableRequest request) {
return {daoParamName}.count(request.getParams());
}
}, new ListHandler() {
@Override
public List<{beanName}> list(PageTableRequest request) {
return {daoParamName}.list(request.getParams(), request.getOffset(), request.getLimit());
}
}).handle(request);
}
@DeleteMapping("/{id}")
@ApiOperation(value = "删除")
public void delete(@PathVariable Long id) {
{daoParamName}.delete(id);
}
}
@Mapper
public interface {daoName} {
@Select("select * from {table_name} t where t.id = #{id}")
{beanName} getById(Long id);
@Delete("delete from {table_name} where id = #{id}")
int delete(Long id);
int update({beanName} {beanParamName});
int save({beanName} {beanParamName});
int count(@Param("params") Map<String, Object> params);
List<{beanName}> list(@Param("params") Map<String, Object> params, @Param("offset") Integer offset, @Param("limit") Integer limit);
}
数据库表名转换成蛇形bean名称
String beanName = separated2Camel("t_user" , '_');
public static String separated2Camel(String name, char separator) {
if (StringUtils.isBlank(name)) {
return null;
}
name = StringUtils.lowerCase(name);
// 去掉开头的
while (StringUtils.startsWith(name, String.valueOf(separator))) {
name = StringUtils.substring(name, 1);
}
// 去掉最后的
while (StringUtils.endsWith(name, String.valueOf(separator))) {
name = StringUtils.substring(name, 0, name.length() - 1);
}
// 去掉中间的,后面首字母大写
StringBuilder sb = new StringBuilder();
for (int i = 0; i < name.length(); i++) {
char c = name.charAt(i);
if (c == separator) {
i++;
sb.append(Character.toUpperCase(name.charAt(i)));
continue;
}
sb.append(c);
}
return sb.toString();
}
bean名称首字母变大写
/**
* 首字母变大写
*/
public static String firstCharToUpper(String name){
if(StringUtils.isEmpty(name)){
return name;
}
StringBuilder sb = new StringBuilder();
sb.append(Character.toUpperCase(name.charAt(0)));
sb.append(name.substring(1));
return sb.toString();
}
读取txt文件
/**
* 读入文件
*/
public static String getText(String path)
{
String filecontent = "";
try {
File f = new File(path);
if (f.exists()) {
FileReader fr = new FileReader(path);
BufferedReader br = new BufferedReader(fr); //建立BufferedReader对象,并实例化为br
String line = br.readLine(); //从文件读取一行字符串
//判断读取到的字符串是否不为空
while (line != null) {
filecontent += line + "\n";
line = br.readLine(); //从文件中继续读取一行数据
}
br.close(); //关闭BufferedReader对象
fr.close(); //关闭文件
}
}
catch (IOException e) {
e.printStackTrace();
}
return filecontent;
}
写入文件
/**
* 将文本写入文件
*
* @param value
* @param path
*/
public static void saveTextFile(String value, String path) {
FileWriter writer = null;
try {
File file = new File(path);
if (!file.getParentFile().exists()) {
file.getParentFile().mkdirs();
}
writer = new FileWriter(file);
writer.write(value);
writer.flush();
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
if (writer != null) {
writer.close();
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
domain的生成
domain的模板
public class {upperBeanName} {
{domainFields}
{domainGetset}
}
获取表结构
public static List<Map<String, Object>> getTbInfo(Connection conn, String dBschema, String tbName) {
String sql = "SELECT " +
" C.TABLE_SCHEMA AS 'km', " + //库名
" T.TABLE_NAME AS 'bm', " + //表名
" T.TABLE_COMMENT AS 'bzs', " + //表注释
" C.COLUMN_NAME AS 'lm', " + //列名
" C.COLUMN_COMMENT AS 'lzs', " + //列注释
" C.ORDINAL_POSITION AS 'ldplsx', " + //列的排列顺序
" C.COLUMN_DEFAULT AS 'mrz', " + //默认值
" C.IS_NULLABLE AS 'sfwk', " + //是否为空
" C.DATA_TYPE AS 'sjlx', " + //数据类型
" C.CHARACTER_MAXIMUM_LENGTH AS 'zfzdcd', " + //字符最大长度
" C.NUMERIC_PRECISION AS 'szjd', " + //数值精度(最大位数)
" C.NUMERIC_SCALE AS 'xsjd', " + //小数精度
" C.COLUMN_TYPE AS 'llx', " + //列类型
" C.COLUMN_KEY 'key', " + //KEY
" C.EXTRA AS 'ewsm' " + //额外说明
" FROM " +
" information_schema.`TABLES` T " +
" LEFT JOIN information_schema.`COLUMNS` C ON T.TABLE_NAME = C.TABLE_NAME " +
" AND T.TABLE_SCHEMA = C.TABLE_SCHEMA " +
" WHERE " +
" T.TABLE_SCHEMA = ? AND " +
" T.TABLE_NAME = ?" +
" ORDER BY " +
" C.TABLE_NAME, " +
" C.ORDINAL_POSITION";
System.out.println("执行sql:" + sql);
List<Object> list = new ArrayList<Object>();
list.add(dBschema);
list.add(tbName);
try {
return executeQuery(conn, sql, list);
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
public static List<Map<String, Object>> executeQuery(Connection conn, String sql, List<Object> parameters)
throws SQLException {
List<Map<String, Object>> rows = new ArrayList<Map<String, Object>>();
PreparedStatement stmt = null;
ResultSet rs = null;
try {
stmt = conn.prepareStatement(sql);
setParameters(stmt, parameters);
rs = stmt.executeQuery();
ResultSetMetaData rsMeta = rs.getMetaData();
while (rs.next()) {
Map<String, Object> row = new LinkedHashMap<String, Object>();
for (int i = 0, size = rsMeta.getColumnCount(); i < size; ++i) {
String columName = rsMeta.getColumnLabel(i + 1);
Object value = rs.getObject(i + 1);
row.put(columName, value);
}
rows.add(row);
}
} finally {
JdbcUtils.close(rs);
JdbcUtils.close(stmt);
}
return rows;
}
拼接domain的字段和getSet方法
private static void getDomainVal() {
StringBuilder fieldsSb = new StringBuilder();
StringBuilder getsetSb = new StringBuilder();
for (Map<String, Object> fields : tbInfo) {
if(fields.get("lm").equals("create_by") || fields.get("lm").equals("create_at") || fields.get("lm").equals("update_by") || fields.get("lm").equals("update_at")){
continue;
}
String type = getFieldType(fields.get("sjlx").toString());
String name = separated2Camel(fields.get("lm").toString(), '_');
// 拼接字段
fieldsSb.append("\t// ").append(fields.get("lzs")).append("\n");
fieldsSb.append("\tprivate ").append(type).append(" ").append(name).append(";\n");
// 拼getset
getsetSb.append("\tpublic ").append(type).append(" get")
.append(firstCharToUpper(name))
.append("() {\n");
getsetSb.append("\t\treturn ").append(name).append(";\n");
getsetSb.append("\t}\n");
getsetSb.append("\tpublic void set")
.append(firstCharToUpper(name))
.append("(").append(type).append(" ").append(name).append(") {\n");
getsetSb.append("\t\tthis.").append(name).append(" = ").append(name).append(";\n");
getsetSb.append("\t}\n");
}
domainFields = fieldsSb.toString();
domainGetset = getsetSb.toString();
}
mapper.xml的生成
mapper.xml的模板
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.cxf.mapper.{packageName}.{upperBeanName}Mapper">
<resultMap id="{upperBeanName}Map" type="com.cxf.model.{packageName}.{upperBeanName}Model">
{resultMap}
</resultMap>
<sql id="sqlAllColumns">
{sqlAllColumns}
</sql>
<sql id="where">
<where>
{selectWhere}
</where>
</sql>
<select id="selectById" resultMap="{upperBeanName}Map">
SELECT
<include refid="sqlAllColumns"/>
FROM `{tbName}`
where `id`=#{id}
</select>
<select id="selectOne" resultMap="{upperBeanName}Map">
SELECT
{sqlAllColumnst}
FROM `{tbName}` t
LIMIT 1
</select>
<select id="selectAll" resultMap="{upperBeanName}Map">
SELECT
<include refid="sqlAllColumns"/>
FROM `{tbName}`
<where>
<if test="id != null and id != ''">
and id = #{id}
</if>
</where>
</select>
<insert id="insert">
insert into `{tbName}` ( <include refid="sqlAllColumns"/>)
values ({insertVal})
</insert>
<update id="update">
update `{tbName}`
set
{updateVal}
WHERE `id` = #{id}
</update>
<update id="patch">
update `{tbName}`
<set>
{updateSet}
</set>
where `id` = #{id}
</update>
<delete id="delete">
DELETE
FROM `{tbName}`
WHERE `id` = #{0}
</delete>
</mapper>
mapper.xml数据拼接
private static void getXmlVal() {
StringBuilder sqlAllColumnsSb = new StringBuilder(); sqlAllColumnsSb.append("\t");
StringBuilder resultMapSb = new StringBuilder();
StringBuilder sqlAllColumnstSb = new StringBuilder(); sqlAllColumnstSb.append("\t\t");
StringBuilder selectWhereSb = new StringBuilder();
StringBuilder insertValSb = new StringBuilder();
StringBuilder updateSetSb = new StringBuilder();
StringBuilder updateValSb = new StringBuilder();
for (int i = 0; i < tbInfo.size(); i++) {
Map<String, Object> fields = tbInfo.get(i);
String name = fields.get("lm").toString();
// 拼接sqlAllColumns
if(i != 0 && i%8 == 0){
sqlAllColumnsSb.append("\n\t");
}
sqlAllColumnsSb.append("`").append(name).append("`");
if(tbInfo.size() != i +1){
sqlAllColumnsSb.append(",");
}
// 拼接resultMapSb
resultMapSb.append("\t").append("<");
if(name.equals("id")){
resultMapSb.append("id ");
} else {
resultMapSb.append("result ");
}
resultMapSb.append("column=\"").append(name).append("\" property=\"").append(separated2Camel(name, '_')).append("\" />");
if(tbInfo.size() != i +1){
resultMapSb.append("\n");
}
// 拼接带别名的表字段
if(i != 0 && i%8 == 0){
sqlAllColumnstSb.append("\n\t\t");
}
sqlAllColumnstSb.append("t.`").append(name).append("`");
if(tbInfo.size() != i +1){
sqlAllColumnstSb.append(",");
}
// 拼接where条件
selectWhereSb.append("\t\t<if test=\"" + separated2Camel(name, '_') + " != null and " + separated2Camel(name, '_') + " != ''\">\n");
selectWhereSb.append("\t\t\tand `" + name).append("` = ").append("#{").append(separated2Camel(name, '_'))
.append("} \n");
selectWhereSb.append("\t\t</if>");
if(tbInfo.size() != i +1){
selectWhereSb.append("\n");
}
// 拼接insert字段
if(i != 0 && i%8 == 0){
insertValSb.append("\n\t\t");
}
insertValSb.append("#{").append(separated2Camel(name, '_')).append("}");
if(tbInfo.size() != i +1){
insertValSb.append(", ");
}
// 拼接update字段
if (!"id".equals(name)) {
updateSetSb.append("\t\t<if test=\"" + separated2Camel(name, '_') + " != null\">\n");
updateSetSb.append("\t\t\t`" + name).append("` = ").append("#{").append(separated2Camel(name, '_') )
.append("}, \n");
updateSetSb.append("\t\t</if>");
if(tbInfo.size() != i +1){
updateSetSb.append("\n");
}
}
// 拼接直接update字段
if (!"id".equals(name)) {
updateValSb.append("\t\t`" + name).append("` = ").append("#{").append(separated2Camel(name, '_') )
.append("}");
if(tbInfo.size() != i +1){
updateValSb.append(", \n");
}
}
}
sqlAllColumns = sqlAllColumnsSb.toString();
resultMap = resultMapSb.toString();
sqlAllColumnst = sqlAllColumnstSb.toString();
selectWhere = selectWhereSb.toString();
insertVal = insertValSb.toString();
updateSet = updateSetSb.toString();
updateVal = updateValSb.toString();
}