背景:
写后台管理系统,涉及大量的增,删除,改,查;而且使用分层开发文件太多,就想到能不能把基本的代码,通过一个代码生成器来生成,从而节约开发时间;
(使用语言nodejs)
tpl 文件夹:
关于控制层与模型层的模板
controller.tpl 所需参数:
代码语言:javascript复制{{ funName }}:指函数名,通常指表名
{{ addParam }}: 添加的参数字段集合
{{ AddRequestParam }}: 添加接受参数
{{ updateParam }}: 更新的参数字段集合
{{ updateRequestParam }}: 更新接受参数
代码语言:javascript复制const {{ funName }}Model = require("../model/{{ funName }}model.js");
function getAll{{ funName }}(req, res) {
{{ funName }}Model.getAll{{ funName }}().then(function (data) {
res.send({code: 200, data: data});
}).catch(function (err) {
console.log(err);
res.send({code: 500});
});
}
function get{{ funName }}ById(req, res) {
let id = req.body.id;
{{ funName }}Model.get{{ funName }}ById(id).then(function (data) {
res.send({code: 200, data: data.length==0?[]:data[0]});
}).catch(function (err) {
console.log(err);
res.send({code: 500});
});
}
function delete{{ funName }}ById(req, res) {
let id = req.body.id;
{{ funName }}Model.delete{{ funName }}ById(id).then(function (data) {
res.send({code: 200, data: data});
}).catch(function (err) {
console.log(err);
res.send({code: 500});
});
}
function add{{ funName }}(req, res) {
{{ AddRequestParam }}
{{ funName }}Model.add{{ funName }}({{ addParam }}).then(function (data) {
res.send({code: 200, data: data});
}).catch(function (err) {
console.log(err);
res.send({code: 500});
});
}
function update{{ funName }}(req, res) {
{{ updateRequestParam }}
{{ funName }}Model.update{{ funName }}({{ updateParam }}).then(function (data) {
res.send({code: 200, data: data});
}).catch(function (err) {
console.log(err);
res.send({code: 500});
});
}
module.exports = {
getAll{{ funName }},
get{{ funName }}By{{ id }},
delete{{ funName }}By{{ id }},
add{{ funName }},
update{{ funName }}
}
model.tpl 所需参数 :
代码语言:javascript复制{{ funName }}:指函数名
{{ table }}: 数据库中的表名
{{ id }} : 对应表的自增id
{{ addParam }}: 添加的参数字段集合
{{ addSql }}: 添加的sql
{{ updateParam }}: 更新的参数字段集合
{{ updateSql }}: 更新的sql
代码语言:javascript复制const pool = require("../model/dbConfig.js");//连接池模块
// 1. 获取所有信息
function getAll{{ funName }}(){
return new Promise(function (resolve, reject) {
let sql = "select * from {{ table }}" ;
pool.query(sql,[]).then(function(data){
resolve(data);
}).catch(function(err){
reject(err);
});
});
}
// 2. 根据id获取数据
function get{{ funName }}ById(id){
return new Promise(function (resolve, reject) {
let sql = "select * from {{ table }} where {{ id }}=?" ;
pool.query(sql,[id]).then(function(data){
resolve(data);
}).catch(function(err){
reject(err);
});
});
}
// 3. 删除信息根据id
function delete{{ funName }}ById(id){
return new Promise(function (resolve, reject) {
let sql = "delete from {{ table }} where {{ id }} = ?" ;
pool.query(sql,[id]).then(function(data){
resolve(data.affectRows);
}).catch(function(err){
reject(err);
});
});
}
// 4. 添加员工信息
function add{{ funName }}({{ addParam }}){
"use strict";
return new Promise(function (resolve, reject) {
let sql = "{{ addSql }}" ;
pool.query(sql,[{{ addParam }}])
.then(function(data){
resolve(data);
}).catch(function(err){
reject(err);
});
});
}
代码语言:javascript复制
// 5. 修改信息
function update{{ funName }}({{ updateParam }}){
return new Promise(function (resolve, reject) {
let sql = "{{ updateSql }}";
pool.query(sql,[{{ updateParam }}])
.then(function(data){
resolve(data);
}).catch(function(err){
reject(err);
});
});
}
module.exports={
getAll{{ funName }},
get{{ funName }}By{{ id }},
delete{{ funName }}By{{ id }},
add{{ funName }},
update{{ funName }}
}
controller 文件夹
根据模板,生成 model 文件与 controller 文件
步骤如下:
- 获取用户提供的表名
- 根据表名,获取对应的列名
3. 根据对应列名,生成tpl文件需要的参数
4. 根据参数与模板, 生成对应的文件
- 获取用户提供的表名
let tables = req.body.tables; //用户传的表名,可多个
let tableArr = tables.split(','); // 逗号成数组
tableArr.forEach((t_name)=>{ //循环取出对应的表名
2. 根据表名,获取对应的列名
代码语言:javascript复制 getColumns(global.database,t_name).then(function (data) {
//此处的data就是获取的列名集合
}
getColumns 从模型层中引用,代码如下:
代码语言:javascript复制function getColumns(dbname,tablename){
return new Promise(function (resolve, reject) {
let sql = "SELECT column_name,data_type,extra FROM COLUMNS WHERE table_schema = ? AND table_name =?" ;
pool.query(sql,[dbname,tablename]).then(function(data){ //pool.query返回的是一个promise对象,所以可以使用then
//成功执行执行的方法
resolve(data);
}).catch(function(err){
reject(err);
});
});
}
3. 根据对应列名,生成tpl文件需要的参数
controller.tpl
所需参数:
{{ funName }}:指函数名,通常指表名
{{ addParam }}: 添加的参数字段集合
{{ AddRequestParam }}: 添加接受参数
{{ updateParam }}: 更新的参数字段集合
{{ updateRequestParam }}: 更新接受参数
参数funName:将表名的首字母转成大写,作为函数名
代码语言:javascript复制let funName = capitalizeFirstLetter(t_name)
capitalizeFirstLetter 方法,实现如下:
代码语言:javascript复制function capitalizeFirstLetter(str) {
if(str.length <= 1 ){
return str.toUpperCase();
}else{
return str.charAt(0).toUpperCase() str.slice(1);
}
}
参数addParam :将除自增字段的列名,首字母大写且用逗号连接
参数updateParam : 所有列名逗号连接
代码语言:javascript复制// 获取自增的列名
let idFiled = data.filter((item)=>{
return item.extra == "auto_increment";
});
// 自增的列名不存在,默认id为自增列
id = idFiled.length ==0 ? "id" : idFiled[0].column_name;
// 将列名放到一个数组中,且首字母大写
let ColumnArr = data.map(function (col_item) {
return capitalizeFirstLetter(col_item.column_name);
})
// 排除自增字段的列
let AddColumnArr = ColumnArr.filter(function (col_item) {
return col_item!=capitalizeFirstLetter(id);
});
addParam = AddColumnArr.join(",");
updateParam = [...AddColumnArr,id].join(",");
参数AddRequestParam: 除自增列以外的接收
参数updateRequestParam:所有列的接收
代码语言:javascript复制// 传不带自增列的数组
let AddRequestParam = bindRequestParam(AddColumnArr);
// 传所有列的数组
let updateRequestParam = bindRequestParam(ColumnArr);
function bindRequestParam(colArr){
let str=``;
for(var i=0;i<colArr.length;i ){
str =`let ${colArr[i]} = req.body.txt${colArr[i]};
`
;
}
return str;
}
4. 根据参数与模板, 生成对应的文件
代码语言:javascript复制bindController({funName,addParam,
updateParam,AddRequestParam,updateRequestParam});
function bindController(contentObj) {
return bindNodeCode(contentObj,"controller.tpl","Controller");
}
function bindNodeCode(contentObj,tplFile,type) {
var tpl = fs.readFileSync(path.resolve(__dirname,"../tpl/" tplFile), 'utf8');
var fileContent = configReplace(tpl,contentObj);
var outPath =path.resolve(__dirname,`../output/${contentObj.funName}${type}.js`);
let result = OutputFile(outPath,fileContent);
return result;
}
model.tpl
参数:
代码语言:javascript复制{{ funName }}:指函数名
{{ table }}: 数据库中的表名
{{ id }} : 对应表的自增id
{{ addParam }}: 添加的参数字段集合
{{ addSql }}: 添加的sql
{{ updateParam }}: 更新的参数字段集合
{{ updateSql }}: 更新的sql
与controller.tpl 模板的参数类似,多了addSql与updateSql 参数
addSql参数
代码语言:javascript复制addSql=bindInsertSql(t_name,AddColumnArr);
// 生成添加的sql语句
function bindInsertSql(tname,colArr) {
let addSql = `insert into ${tname} values(null,`;
addSql =insertColumnSql(colArr) ")";
return addSql;
}
function insertColumnSql(colArr) {
let sql=[];
colArr.forEach((item)=>{
sql.push("?");
})
return sql.join(",");
}
updateSql 参数
代码语言:javascript复制updateSql=bindUpdateSql(t_name,AddColumnArr,id);
function updateColumnSql(colArr) {
let sql=[];
colArr.forEach((item)=>{
sql.push(`${item.toLowerCase()}=?`);
})
return sql.join(",");
}
// 生成更新的sql语句
// tname:表名, colArr:更新的列, idFiled:where的条件
function bindUpdateSql(tname,colArr,idFiled) {
let updateSql =`update ${tname} set `
updateSql =updateColumnSql(colArr) ` where ${idFiled} = ?`;
return updateSql;
}
Nodejs生成的三层架构,就分享结束!!^_^