2021-06-03 19:03:48 +00:00
package code
import (
. "../common"
"../db"
"errors"
2021-06-04 02:04:37 +00:00
"fmt"
2021-06-03 19:03:48 +00:00
"io/ioutil"
"net/http"
"os"
"path/filepath"
2021-06-04 02:04:37 +00:00
"strings"
2021-06-03 19:03:48 +00:00
)
type MakeCode struct {
2021-06-11 00:06:44 +00:00
IndexMenus Map
2021-06-03 19:03:48 +00:00
TableConfig Map
TableColumns map [ string ] map [ string ] Map
Config Map
Error
}
func ( that * MakeCode ) Db2JSON ( name string , path string , db db . HoTimeDB ) {
2021-06-04 18:18:56 +00:00
isMake := false
idSlice := Slice { }
2021-06-03 19:03:48 +00:00
if that . TableColumns == nil {
that . TableColumns = make ( map [ string ] map [ string ] Map )
}
//加载配置文件
btes , err := ioutil . ReadFile ( path )
2021-06-07 03:32:47 +00:00
Config [ "name" ] = name
2021-06-03 19:03:48 +00:00
that . Config = DeepCopyMap ( Config ) . ( Map )
if err == nil {
cmap := Map { }
//文件是否损坏
cmap . JsonToMap ( string ( btes ) , & that . Error )
for k , v := range cmap {
that . Config [ k ] = v //程序配置
Config [ k ] = v //系统配置
}
} else {
that . Error . SetError ( errors . New ( "配置文件不存在,或者配置出错,使用缺省默认配置" ) )
}
2021-06-11 00:06:44 +00:00
that . IndexMenus = Map { }
menusConfig := that . Config . GetSlice ( "menus" )
//将配置写入到内存中仅作为判断用
if menusConfig != nil {
for kmenu , _ := range menusConfig {
menu := menusConfig . GetMap ( kmenu )
if menu != nil {
mname := menu . GetString ( "table" )
if mname == "" { //如果为空则不是表格
mname = menu . GetString ( "name" )
}
that . IndexMenus [ mname ] = menu
childMenus := menu . GetSlice ( "menus" )
if childMenus != nil {
for ckmenu , _ := range childMenus {
cmenu := childMenus . GetMap ( ckmenu )
if cmenu != nil {
cname := cmenu . GetString ( "table" )
if cmenu . GetString ( "table" ) == "" {
continue
}
that . IndexMenus [ mname + "/" + cname ] = cmenu
}
}
}
}
}
}
2021-06-05 23:50:58 +00:00
that . TableConfig = that . Config . GetMap ( "tables" )
if that . TableConfig == nil {
that . TableConfig = Map { }
}
for tableName , _ := range that . TableConfig {
columns := that . TableConfig . GetMap ( tableName ) . GetSlice ( "columns" )
2021-06-03 19:03:48 +00:00
//初始化
if that . TableColumns [ tableName ] == nil {
that . TableColumns [ tableName ] = map [ string ] Map { }
}
//注入源数据
2021-06-05 23:50:58 +00:00
for index , _ := range columns {
columnsName := columns . GetMap ( index ) . GetString ( "name" )
that . TableColumns [ tableName ] [ columnsName ] = columns . GetMap ( index )
2021-06-03 19:03:48 +00:00
}
}
2021-06-04 02:04:37 +00:00
myInit := strings . Replace ( InitTpt , "{{name}}" , name , - 1 )
ctrList := ""
2021-06-04 18:18:56 +00:00
nowTables := make ( [ ] Map , 0 )
if db . Type == "mysql" {
nowTables = db . Select ( "INFORMATION_SCHEMA.TABLES" , "TABLE_NAME as name,TABLE_COMMENT as label" , Map { "TABLE_SCHEMA" : db . DBName } )
}
2021-06-03 19:03:48 +00:00
if db . Type == "sqlite" {
2021-06-04 18:18:56 +00:00
nowTables = db . Select ( "sqlite_sequence" , "name" )
}
//idSlice=append(idSlice,nowTables)
for _ , v := range nowTables {
if that . TableConfig . GetMap ( v . GetString ( "name" ) ) == nil {
if v . GetString ( "label" ) == "" {
2021-06-11 00:06:44 +00:00
v [ "label" ] = v . GetString ( "name" )
2021-06-04 18:18:56 +00:00
}
that . TableConfig [ v . GetString ( "name" ) ] = Map {
"label" : v . GetString ( "label" ) ,
"table" : v . GetString ( "name" ) ,
"auth" : [ ] string { "add" , "delete" , "edit" , "info" } ,
"columns" : [ ] Map { } ,
"search" : [ ] Map {
//{"type": "tree", "name": "oid", "label": "组织", "table": "organization", "showName": "label", "children": "children"},
{ "type" : "text" , "name" : "keyword" , "label" : "请输入关键词" , "value" : nil } ,
{ "type" : "date" , "name" : "date" , "label" : "时间段" , "value" : nil } ,
{ "type" : "select" , "name" : "state" , "label" : "状态" , "value" : nil ,
"option" : [ ] Map {
{ "name" : "正常" , "value" : 0 } ,
{ "name" : "异常" , "value" : 1 } ,
{ "name" : "全部" , "value" : nil } ,
2021-06-03 19:03:48 +00:00
} ,
} ,
2021-06-04 18:18:56 +00:00
} ,
2021-06-03 19:03:48 +00:00
}
2021-06-04 18:18:56 +00:00
}
2021-06-07 03:32:47 +00:00
//else {
// if !(that.TableConfig.GetMap(v.GetString("name")).GetString("label") != "备注" &&
// v.GetString("label") == "备注") {
// that.TableConfig.GetMap(v.GetString("name"))["label"] = v.GetString("label")
// }
//
//}
2021-06-04 18:18:56 +00:00
//初始化
if that . TableColumns [ v . GetString ( "name" ) ] == nil {
that . TableColumns [ v . GetString ( "name" ) ] = make ( map [ string ] Map )
}
2021-06-11 00:06:44 +00:00
2021-06-04 18:18:56 +00:00
tableInfo := make ( [ ] Map , 0 )
if db . Type == "mysql" {
tableInfo = db . Select ( "INFORMATION_SCHEMA.COLUMNS" , "COLUMN_NAME AS name,COLUMN_TYPE AS type,COLUMN_COMMENT AS label" , Map { "AND" : Map { "TABLE_SCHEMA" : db . DBName , "TABLE_NAME" : v . GetString ( "name" ) } } )
}
if db . Type == "sqlite" {
tableInfo = db . Query ( "pragma table_info([" + v . GetString ( "name" ) + "]);" )
}
2021-06-03 19:03:48 +00:00
2021-06-04 18:18:56 +00:00
idSlice = append ( idSlice , tableInfo )
for _ , info := range tableInfo {
if info . GetString ( "label" ) == "" {
2021-06-11 00:06:44 +00:00
info [ "label" ] = info . GetString ( "name" )
2021-06-03 19:03:48 +00:00
}
2021-06-05 23:50:58 +00:00
coloum := that . TableColumns [ v . GetString ( "name" ) ] [ info . GetString ( "name" ) ]
2021-06-04 18:18:56 +00:00
2021-06-05 23:50:58 +00:00
if coloum == nil {
2021-06-07 03:32:47 +00:00
//备注以空格隔开,空格后的是其他备注
indexNum := strings . Index ( info . GetString ( "label" ) , " " )
if indexNum >= 0 {
info [ "label" ] = info . GetString ( "label" ) [ : ]
}
//根据类型判断真实类型
for k , v := range ColumnDataType {
if strings . Contains ( info . GetString ( "type" ) , k ) {
info [ "type" ] = v
break
}
}
2021-06-05 23:50:58 +00:00
coloum = Map {
2021-06-04 18:18:56 +00:00
"name" : info . GetString ( "name" ) ,
"type" : info . GetString ( "type" ) ,
"label" : info . GetString ( "label" ) ,
//"add": false, "info": false, "edit": false, "list": true,
2021-06-07 03:32:47 +00:00
//"must": false,
2021-06-04 18:18:56 +00:00
}
2021-06-03 19:03:48 +00:00
2021-06-07 03:32:47 +00:00
for _ , v := range ColumnNameType {
if ( v . Strict && coloum . GetString ( "name" ) == v . Name ) || strings . Contains ( coloum . GetString ( "name" ) , v . Name ) {
//全部都不需要则不加入
if v . Edit == false && v . List == false && v . Info == false {
coloum [ "notUse" ] = true
break
}
if v . Info == false {
coloum [ "info" ] = v . Info
}
if v . Edit == false {
coloum [ "edit" ] = v . Edit
coloum [ "add" ] = v . Edit
}
if v . List == false {
coloum [ "list" ] = v . List
}
if v . Must == true {
coloum [ "must" ] = v . Must
}
if v . Type != "" {
coloum [ "type" ] = v . Type
}
break
}
}
if ! coloum . GetBool ( "notUse" ) {
that . TableConfig . GetMap ( v . GetString ( "name" ) ) [ "columns" ] = append ( that . TableConfig . GetMap ( v . GetString ( "name" ) ) . GetSlice ( "columns" ) , coloum )
2021-06-04 02:04:37 +00:00
}
2021-06-07 03:32:47 +00:00
}
//else {
//
// //if !(coloum.GetString("label") != "备注" && info.GetString("label") == "备注") {
// // coloum["label"] = info.GetString("label")
// //}
// //coloum["type"] = info.GetString("type")
//}
//暂时不关闭参数,保证表数据完全读取到
2021-06-05 23:50:58 +00:00
that . TableColumns [ v . GetString ( "name" ) ] [ info . GetString ( "name" ) ] = coloum
2021-06-04 02:04:37 +00:00
2021-06-03 19:03:48 +00:00
}
2021-06-04 02:04:37 +00:00
2021-06-04 18:18:56 +00:00
//创建模块文件
//判断文件是否存在
//_, err := os.OpenFile(name+"/"+v.GetString("name"), os.O_RDONLY, os.ModePerm)
_ , err := os . Stat ( name + "/" + v . GetString ( "name" ) + ".go" )
if err != nil { //文件不存在,则根据模板创建
myCtr := strings . Replace ( CtrTpt , "{{name}}" , name , - 1 )
myCtr = strings . Replace ( myCtr , "{{table}}" , v . GetString ( "name" ) , - 1 )
_ = os . MkdirAll ( name , os . ModeDir )
err = ioutil . WriteFile ( name + "/" + v . GetString ( "name" ) + ".go" , [ ] byte ( myCtr ) , os . ModePerm )
if err != nil {
that . Error . SetError ( err )
2021-06-03 19:03:48 +00:00
}
2021-06-04 18:18:56 +00:00
isMake = true
2021-06-03 19:03:48 +00:00
}
2021-06-04 02:04:37 +00:00
2021-06-04 18:18:56 +00:00
ctrList = ctrList + ` " ` + v . GetString ( "name" ) + ` ": ` + v . GetString ( "name" ) + "Ctr,\r\n "
}
2021-06-05 23:50:58 +00:00
that . Config [ "tables" ] = that . TableConfig
2021-06-04 18:18:56 +00:00
2021-06-07 03:32:47 +00:00
//生成id, 判断数据库是否有改变, 以保证数据库和配置文件匹配唯一
2021-06-04 18:18:56 +00:00
id := Md5 ( ObjToStr ( idSlice ) )
2021-06-04 02:04:37 +00:00
if id == that . Config . GetString ( "id" ) {
2021-06-04 18:18:56 +00:00
if isMake { //有生成包文件
fmt . Println ( "有新的业务代码生成,请重新运行" )
os . Exit ( - 1 )
}
2021-06-04 02:04:37 +00:00
return
}
2021-06-11 00:06:44 +00:00
//数据生成完后进一步解析
2021-06-07 03:32:47 +00:00
for fk , fv := range that . TableColumns {
2021-06-11 00:06:44 +00:00
//判断是否将表写入menu中
isMenusGet := false //判断是否被目录收录
for indexKey , _ := range that . IndexMenus {
indexCode := strings . Index ( indexKey , fk )
//如果相等或者表名在目录中已经设置(主要前一位是/并且他是最后一个字符串)
if indexKey == fk || ( indexCode != - 1 && indexKey [ indexCode - 1 ] == '/' && indexKey [ indexCode : ] == fk ) {
isMenusGet = true
break
}
}
//目录没有收录
if ! isMenusGet {
tablePrefixCode := strings . Index ( fk , "_" )
isNewPrefix := false //假定表名没有前缀
prefixName := ""
//并且代表有前缀,根据数据表分库设定使用
if tablePrefixCode != - 1 {
prefixName = fk [ : tablePrefixCode ]
}
if tablePrefixCode != - 1 {
for ck , _ := range that . TableColumns {
//判断不止一个前缀相同
if strings . Index ( ck , prefixName ) == 0 && ck != prefixName && ck != fk {
isNewPrefix = true
break
}
}
}
menuIns := Map { "label" : that . TableConfig . GetMap ( fk ) . GetString ( "label" ) , "table" : fk }
//多耗费一点内存
mMenu := Map { "menus" : Slice { menuIns } , "label" : that . TableConfig . GetMap ( fk ) . GetString ( "label" ) , "name" : prefixName , "icon" : "el-icon-setting" }
//表名有前缀
if ! isNewPrefix {
//是否已有对应前缀, 已经有对应的menu只需要push进去即可
prefixName = DefaultMenuParentName
mMenu = Map { "menus" : Slice { menuIns } , "label" : "系统管理" , "name" : prefixName , "icon" : "el-icon-setting" }
}
//没有新前缀
if that . IndexMenus [ prefixName ] != nil {
that . IndexMenus . GetMap ( prefixName ) [ "menus" ] = append ( that . IndexMenus . GetMap ( prefixName ) . GetSlice ( "menus" ) , menuIns )
that . IndexMenus [ prefixName + "/" + fk ] = menuIns
} else {
that . Config [ "menus" ] = append ( that . Config . GetSlice ( "menus" ) , mMenu ) //注入配置
//写入Index
that . IndexMenus [ prefixName ] = mMenu
that . IndexMenus [ prefixName + "/" + fk ] = menuIns
}
}
2021-06-07 03:32:47 +00:00
for k , v := range fv {
2021-06-11 01:41:23 +00:00
//虚招后缀是_id结尾的表字段 假设org_id
2021-06-07 03:32:47 +00:00
if len ( k ) <= 3 || strings . LastIndex ( k , "_id" ) != len ( k ) - 3 {
continue
}
2021-06-11 01:41:23 +00:00
//普通表匹配 org_id匹配为org
2021-06-07 03:32:47 +00:00
oldTableName := k [ : len ( k ) - 3 ]
//上级ID匹配
if oldTableName == "parent" {
oldTableName = fk
}
2021-06-11 01:41:23 +00:00
//如果依然找不到则查询system_org是否存在
if that . TableConfig [ DefaultMenuParentName + "_" + oldTableName ] != nil {
oldTableName = DefaultMenuParentName + "_" + oldTableName
}
2021-06-07 03:32:47 +00:00
//字段有动词前缀,自动进行解析
prefixColumn := strings . Index ( oldTableName , "_" )
2021-06-11 01:41:23 +00:00
//sys_org_id oldTableName即为sys此处判断为org表存在
2021-06-07 03:32:47 +00:00
if prefixColumn > - 1 && that . TableConfig [ oldTableName [ prefixColumn + 1 : ] ] != nil {
oldTableName = oldTableName [ prefixColumn + 1 : ]
}
2021-06-11 01:41:23 +00:00
//如果依然找不到则查询system_org是否存在
if prefixColumn > - 1 && that . TableConfig [ DefaultMenuParentName + "_" + oldTableName [ prefixColumn + 1 : ] ] != nil {
oldTableName = DefaultMenuParentName + "_" + oldTableName [ prefixColumn + 1 : ]
}
//普通方式查询不到,则转换为大型项目模块划分,暂时只支持一级模块划分,
//比如表sys_user 字段org_id, 查询不到sys_org表则查询org表, org表查询不到则查询默认前缀system_org表
2021-06-07 03:32:47 +00:00
//都查询不到则找不到,
prefix := strings . Index ( fk , "_" )
tableName := oldTableName
if prefix > 0 {
2021-06-11 01:41:23 +00:00
//表模块前缀sys_user sys即为前缀 sys_org
2021-06-07 03:32:47 +00:00
tableName = fk [ : prefix + 1 ] + oldTableName
if that . TableConfig [ tableName ] == nil {
2021-06-11 01:41:23 +00:00
//不存在则改为org
2021-06-07 03:32:47 +00:00
tableName = oldTableName
}
//表前缀+去除字段前缀
prefixColumn := strings . Index ( oldTableName , "_" )
if prefixColumn > - 1 {
tableName = fk [ : prefix + 1 ] + oldTableName [ prefixColumn + 1 : ]
if that . TableConfig [ tableName ] == nil {
tableName = oldTableName
}
}
}
2021-06-11 00:06:44 +00:00
//如果数据匹配则写入到配置中
2021-06-07 03:32:47 +00:00
if that . TableConfig [ tableName ] != nil {
v [ "link" ] = tableName
2021-06-11 01:41:23 +00:00
//一般查询name字段或者label字段, 如果没有name字段则默认第二个地段
2021-06-07 03:32:47 +00:00
if that . TableColumns [ tableName ] [ "name" ] != nil {
v [ "value" ] = tableName + "." + "name"
break
}
2021-06-11 01:41:23 +00:00
if that . TableColumns [ tableName ] [ "label" ] != nil {
v [ "value" ] = tableName + "." + "label"
break
}
2021-06-07 03:32:47 +00:00
if len ( that . TableConfig . GetMap ( tableName ) . GetSlice ( "columns" ) ) > 2 {
v [ "value" ] = tableName + "." + that . TableConfig . GetMap ( tableName ) . GetSlice ( "columns" ) . GetMap ( 1 ) . GetString ( "name" )
break
}
}
}
}
2021-06-04 18:18:56 +00:00
fmt . Println ( id , "---" , that . Config . GetString ( "id" ) )
2021-06-04 02:04:37 +00:00
that . Config [ "id" ] = id
//init文件初始化
myInit = strings . Replace ( myInit , "{{id}}" , id , - 1 )
myInit = strings . Replace ( myInit , "{{tablesCtr}}" , ctrList , - 1 )
_ = os . MkdirAll ( name , os . ModeDir )
2021-06-04 18:18:56 +00:00
err = ioutil . WriteFile ( name + "/init.go" , [ ] byte ( myInit ) , os . ModePerm )
2021-06-04 02:04:37 +00:00
if err != nil {
that . Error . SetError ( err )
2021-06-03 19:03:48 +00:00
}
//写入配置文件
2021-06-04 18:18:56 +00:00
//var configByte bytes.Buffer
2021-06-03 19:03:48 +00:00
2021-06-04 18:18:56 +00:00
//err = json.Indent(&configByte, []byte(that.Config.ToJsonString()), "", "\t")
2021-06-03 19:03:48 +00:00
_ = os . MkdirAll ( filepath . Dir ( path ) , os . ModeDir )
2021-06-04 18:18:56 +00:00
err = ioutil . WriteFile ( path , [ ] byte ( that . Config . ToJsonString ( ) ) , os . ModePerm )
2021-06-03 19:03:48 +00:00
if err != nil {
that . Error . SetError ( err )
}
2021-06-04 02:04:37 +00:00
fmt . Println ( "有新的代码生成,请重新运行" )
os . Exit ( - 1 )
2021-06-03 19:03:48 +00:00
}
2021-06-07 03:32:47 +00:00
2021-06-03 19:03:48 +00:00
func ( that * MakeCode ) Info ( table string ) string {
reStr := ""
for _ , v := range that . TableColumns [ table ] {
2021-06-07 03:32:47 +00:00
if v == nil {
continue
}
2021-06-03 19:03:48 +00:00
if v . Get ( "info" ) == nil || v . GetBool ( "info" ) {
reStr += v . GetString ( "name" ) + ","
}
}
if len ( reStr ) != 0 {
reStr = reStr [ : len ( reStr ) - 1 ]
}
return reStr
}
func ( that * MakeCode ) Add ( table string , req * http . Request ) Map {
data := Map { }
for _ , v := range that . TableColumns [ table ] {
2021-06-07 03:32:47 +00:00
//不可使用,未在前端展示,但在内存中保持有
if v . GetBool ( "notUse" ) {
continue
}
2021-06-03 19:03:48 +00:00
if v . Get ( "add" ) == nil || v . GetBool ( "add" ) {
reqValue := req . FormValue ( v . GetString ( "name" ) )
if reqValue == "" {
return nil
}
data [ v . GetString ( "name" ) ] = reqValue
}
}
if len ( data ) == 0 {
return nil
}
return data
}
func ( that * MakeCode ) Edit ( table string , req * http . Request ) Map {
data := Map { }
for _ , v := range that . TableColumns [ table ] {
2021-06-07 03:32:47 +00:00
//不可使用,未在前端展示,但在内存中保持有
if v . GetBool ( "notUse" ) {
continue
}
2021-06-03 19:03:48 +00:00
if v . Get ( "edit" ) == nil || v . GetBool ( "edit" ) {
reqValue := req . FormValue ( v . GetString ( "name" ) )
if reqValue == "" {
continue
}
data [ v . GetString ( "name" ) ] = reqValue
}
}
if len ( data ) == 0 {
return nil
}
return data
}
func ( that * MakeCode ) Search ( table string , req * http . Request ) ( string , Map ) {
reStr := ""
for _ , v := range that . TableColumns [ table ] {
2021-06-07 03:32:47 +00:00
//不可使用,未在前端展示,但在内存中保持有
if v . GetBool ( "notUse" ) {
continue
}
2021-06-03 19:03:48 +00:00
if v . Get ( "list" ) == nil || v . GetBool ( "list" ) {
reStr += v . GetString ( "name" ) + ","
}
}
if len ( reStr ) != 0 {
reStr = reStr [ : len ( reStr ) - 1 ]
}
data := Map { }
search := that . TableConfig . GetSlice ( "search" )
for k , _ := range search {
reqValue := req . FormValue ( search . GetMap ( k ) . GetString ( "name" ) )
if reqValue == "" {
continue
}
data [ search . GetMap ( k ) . GetString ( "name" ) ] = reqValue
}
return reStr , data
}