当前位置: 代码迷 >> MySQL >> 重写代码生成器支持模板(多层架构,MVC),多语言c#java;支持mysql跟sqlserver,动态编译
  详细解决方案

重写代码生成器支持模板(多层架构,MVC),多语言c#java;支持mysql跟sqlserver,动态编译

热度:112   发布时间:2016-05-05 16:51:26.0
重写代码生成器支持模板(多层架构,MVC),多语言c#,java;支持mysql和sqlserver,动态编译

多年前用过李天平前辈的,自己改过,后来李老师做动软了,不给源码,修改不是很方便。加上我目前需要转java方向,于是决定自己搞。到目前为止花了整整一个星期了,看看目前的成果。

QQ图片20150729212121

QQ截图20150729212205

QQ截图20150729213325

QQ截图20150729213412

QQ截图20150729213436

QQ截图20150729213529

最后是代码工程文件,用c#开发的,IDE是vs2010

QQ截图20150729214011

 

为了实现最大的模板自由,设计了专有的模板语法。基于C#,但是已经做到尽量简化,对有一点开发经验的同行应该是很好上手的。

目前c#的代码模板已经做了一些通用样例,接下来做java的开发代码模板。

总之,为了提高效率,并且规范项目团队成员的代码书写。

 

下面把核心的代码两个类文件贴出来,分别是动态编译和模板解析

  1 using System;  2 using System.Collections.Generic;  3 using System.Linq;  4 using System.Text;  5 using System.CodeDom.Compiler;  6 using System.Reflection;  7   8 namespace CodeMaker.Engine  9 { 10     public class Compiler 11     { 12         /// <summary> 13         /// 普通代码编译执行出字符串 14         /// </summary> 15         /// <param name="strCode"></param> 16         /// <returns></returns> 17         public static string DoCompile(string strCode) 18         { 19              20             StringBuilder strResults = new StringBuilder(); 21  22             CodeDomProvider provider = CodeDomProvider.CreateProvider("CSharp"); 23  24             //CompilerParameters 编译参数 25             CompilerParameters objCompilerParameters = new CompilerParameters(); 26             objCompilerParameters.ReferencedAssemblies.Add("System.dll"); 27             objCompilerParameters.ReferencedAssemblies.Add("System.Core.dll"); 28             objCompilerParameters.ReferencedAssemblies.Add("System.Data.dll"); 29             objCompilerParameters.ReferencedAssemblies.Add("CodeMaker.BLL.dll"); 30             objCompilerParameters.ReferencedAssemblies.Add("CodeMaker.DALFactory.dll"); 31             objCompilerParameters.ReferencedAssemblies.Add("CodeMaker.IDAL.dll"); 32             objCompilerParameters.ReferencedAssemblies.Add("CodeMaker.Model.dll"); 33             objCompilerParameters.ReferencedAssemblies.Add("CodeMaker.MySqlDAL.dll"); 34             objCompilerParameters.ReferencedAssemblies.Add("CodeMaker.SqlDAL.dll"); 35             objCompilerParameters.ReferencedAssemblies.Add("CodeMaker.Engine.dll"); 36             objCompilerParameters.GenerateExecutable = false; 37             objCompilerParameters.GenerateInMemory = true; 38              39             // CompilerResults 40             CompilerResults cr = provider.CompileAssemblyFromSource(objCompilerParameters, strCode); 41  42             if (cr.Errors.HasErrors) 43             { 44                 Console.WriteLine("编译错误:"); 45                 foreach (CompilerError err in cr.Errors) 46                 { 47                     strResults.Append(err.ErrorText); 48                     strResults.Append(Environment.NewLine); 49                     strResults.Append(err.Line); 50                     strResults.Append(Environment.NewLine); 51                     strResults.Append(err.ToString()); 52                     strResults.Append(Environment.NewLine); 53                  54                 } 55             } 56             else 57             { 58                 // 通过反射,调用OutPut的输出方法 59                 Assembly objAssembly = cr.CompiledAssembly; 60                 object objHelloWorld = objAssembly.CreateInstance("DynamicCodeGenerate.CodeGenerate"); 61                 MethodInfo objMI = objHelloWorld.GetType().GetMethod("OutPut"); 62  63                 strResults.Append(objMI.Invoke(objHelloWorld, null)); 64                 strResults.Append(Environment.NewLine); 65                66             } 67              68              69             return strResults.ToString(); 70         } 71  72         public static string DoCodeMakerCompile(string strDBType,string DALAssemblyPath, string strDataBase,string strTableName, string strEntityName,string strCode) 73         { 74              75              76             StringBuilder sb = new StringBuilder(); 77             //加上要编译部分代码的头部和尾部 78             //头部 79             sb.Append("using System;"); 80             sb.Append("using System.Data;"); 81             sb.Append("using System.Text;"); 82             sb.Append("using System.Linq;"); 83             sb.Append("using System.Globalization;"); 84             sb.Append("using System.Collections.Generic;"); 85             sb.Append("using CodeMaker.Model;"); 86             sb.Append("using CodeMaker.BLL;"); 87             sb.Append("using CodeMaker.Engine;"); 88             sb.Append("namespace DynamicCodeGenerate"); 89             sb.Append("{"); 90  91              92  93             sb.Append("   public class CodeGenerate"); 94             sb.Append("   {"); 95             sb.Append("        public string OutPut()"); 96             sb.Append("        {"); 97  98             //读取数据实体的属性的代码段 99             sb.Append(GetEntity(strDBType, DALAssemblyPath, strDataBase, strTableName, strEntityName));100 101             sb.Append(strCode);102 103             //返回值,字符串104             sb.Append("         return s.ToString(); ");105             sb.Append("        }");106             //fOutPut方法结束107             //首字母大写方法108             sb.Append("        public string ToTitleCase(string str)");109             sb.Append("        {");110             sb.Append("          return str.Substring(0,1).ToUpper()+str.Substring(1);");111             sb.Append("        }");112             //首字母小写方法113             sb.Append("        public string ToLowerCase(string str)");114             sb.Append("        {");115             sb.Append("          return str.Substring(0,1).ToLower()+str.Substring(1);");116             sb.Append("        }");117             118             sb.Append("   }");119             sb.Append("}");120 121             return DoCompile(sb.ToString());122         }123 124         private static string GetEntity(string strDBType, string DALAssemblyPath, string strDataBase, string strTableName, string strEntityName)125         {126             StringBuilder sb = new StringBuilder();127             sb.Append("CodeMaker.BLL.EntityBLL bll = new CodeMaker.BLL.EntityBLL(\"" + DALAssemblyPath + "\");");128             sb.Append("IList<CodeMaker.Model.Entity> es = bll.GetEntityList(\"" + strDataBase + "\", \"" + strTableName + "\");");129             sb.Append("string EntityName=\"" + strEntityName + "\";");//实体名,供模板中的代码段使用130             sb.Append("string TableName=\"" + strTableName + "\";");//表名,供模板中的代码段使用131             sb.Append("string DBType=\"" + strDBType + "\";");//数据库组件,判断数据库种类SQLSERVER,MYSQL,供模板中的代码段使用132             sb.Append("string TablePri=(es.Where(x=>x.IsPri==\"YES\").Count()>0)?es.Where(x=>x.IsPri==\"YES\").ToList()[0].ColumnName:\"\";");//表的主键列 名称133             sb.Append("string TablePriDataType=(es.Where(x=>x.IsPri==\"YES\").Count()>0)?CodeAnalysis.ToDataTypeFormat(es.Where(x=>x.IsPri==\"YES\").ToList()[0].DataType,DBType):\"\";");//表的主键列 数据类型134             return sb.ToString();135            136         }137 138         public static string GenerateCode()139         {140             return "";141         }142     }143 }

 

  1 using System;  2 using System.Collections.Generic;  3 using System.Linq;  4 using System.Text;  5 using System.Text.RegularExpressions;  6   7 namespace CodeMaker.Engine  8 {  9     public class CodeAnalysis 10     { 11         public static string Hello() 12         { 13             return "Hello"; 14         } 15  16         public static string ToCSharpCode(string strContent) 17         { 18             StringBuilder sb = new StringBuilder(); 19             //需要逐行解析 20             string[] ss = strContent.Split('\n'); 21             string strT=string.Empty; 22             if (ss.Length > 0) 23             { 24                 sb.Append("StringBuilder s = new StringBuilder();");//如果行数不为0,则需要声明字符串拼接 25                 sb.Append(System.Environment.NewLine); 26             } 27             for (int i = 0; i < ss.Length; i++) 28             { 29                 //处理字符串行 30                 sb.Append(DealCode(ss[i])); 31                 sb.Append(System.Environment.NewLine); 32                33  34             } 35  36             return sb.ToString(); 37         } 38  39         /// <summary> 40         /// 单行字符串处理 41         /// </summary> 42         /// <param name="strLine"></param> 43         /// <returns></returns> 44         private static string DealCode(string strLine) 45         { 46             //判断当该行是无特殊代码行。特殊代码(<-$、$->) 47  48             strLine = Regex.Replace(strLine, @"[\r\n]", "");  //替换掉常量中的换行符 49             50             51             if (strLine.Contains("<-$") && strLine.Contains("$->")) 52             { 53                 //有整行特殊代码段 54                 //strLine = strLine.Replace("\"", "\\\""); 55                 strLine = strLine.Replace("<-$", ""); 56                 strLine = strLine.Replace("$->", ""); 57  58                 //strLine += "s.Append(System.Environment.NewLine);"; 59             } 60             else if (strLine.Contains("<+$") && strLine.Contains("$+>")) 61             { 62                 //有变量取值代码段 63                 strLine = strLine.Replace("\"", "\\\""); 64                 strLine = "\""+strLine+"\\n\"";//前后先加引号,后面加个换行 65                 strLine = strLine.Replace("<+$", "\"+"); 66                 strLine = strLine.Replace("$+>", "+\""); 67                 68                  69                 strLine = "s.Append("+ strLine +");"; 70             } 71             else 72             {  73                 //不是特殊代码行 74                 //strLine = "s.Append(\"" + strLine + "\"); s.Append(System.Environment.NewLine);" ; 75                 strLine = strLine.Replace("\"", "\\\""); 76                 strLine = "s.Append(\"" + strLine + "\\n\");"; 77             } 78  79             return strLine; 80         } 81  82         #region 供动态编译的代码段中调用的静态方法 83  84         /// <summary> 85         /// 数据库字段数据类型 转为 java语言中的数据类型 86         /// </summary> 87         /// <param name="strDBColumnType">数据库字段数据类型</param> 88         /// <param name="strDBType">数据库MYSQL  SQLSERVER</param> 89         /// <returns></returns> 90         public static string ToJavaDataType(string strDBColumnType, string strDBType) 91         { 92             string strT = string.Empty; 93  94             //根据strDBType 判断数据库是什么,然后转换为程序语言中的数据类型 95             switch (strDBType) 96             { 97                 case "SQLSERVER": 98                     var stringwords = new string[]{"char","varchar","text","nchar","nvarchar","ntext"}; 99                     var intwords = new string[]{"int","smallint","tinyint"};100                     var boolwords = new string[] { "bit"};101                     var longwords = new string[] { "bigint"};102                     var decimalwords = new string[] { "numeric", "decimal", "money","smallmoney","float","real" };103                     var datewords = new string[] { "datetime", "smalldatetime" };104                     if (stringwords.Contains(strDBColumnType.ToLower()))105                     { 106                         strT="String";107                     }108                     else if (intwords.Contains(strDBColumnType.ToLower()))109                     {110                         strT = "int";111                     }112                     else if (longwords.Contains(strDBColumnType.ToLower()))113                     {114                         strT = "long";115                     }116                     else if (boolwords.Contains(strDBColumnType.ToLower()))117                     {118                         strT = "boolean";119                     }120                     else if (decimalwords.Contains(strDBColumnType.ToLower()))121                     {122                         strT = "decimal";123                     }124                     else if (datewords.Contains(strDBColumnType.ToLower()))125                     {126                         strT = "DateTime";127                     }128                     else129                     {130                         strT = "String";131                     }132 133 134                     break;135 136                 case "MYSQL":137                      var stringwords1 = new string[]{"char","varchar","text","tinytext","mediumtext","longtext"};138                     var intwords1 = new string[]{"smallint","tinyint","mediumint"};139                     var boolwords1 = new string[] { "bit"};140                     var longwords1 = new string[] { "int,bigint", "integer" };141                     var decimalwords1 = new string[] { "float", "decimal", "double" };142                     var datewords1 = new string[] { "datetime", "date" };143                     if (stringwords1.Contains(strDBColumnType.ToLower()))144                     {145                         strT = "String";146                     }147                     else if (intwords1.Contains(strDBColumnType.ToLower()))148                     {149                         strT = "int";150                     }151                     else if (longwords1.Contains(strDBColumnType.ToLower()))152                     {153                         strT = "long";154                     }155                     else if (boolwords1.Contains(strDBColumnType.ToLower()))156                     {157                         strT = "boolean";158                     }159                     else if (decimalwords1.Contains(strDBColumnType.ToLower()))160                     {161                         strT = "decimal";162                     }163                     else if (datewords1.Contains(strDBColumnType.ToLower()))164                     {165                         strT = "DateTime";166                     }167                     else168                     {169                         strT = "String";170                     }171 172 173                     break;174 175                 default:176                     break;177             }178 179             return strT;180         }181 182         /// <summary>183         /// 数据库字段数据类型 转为 c# 语言中的数据类型184         /// </summary>185         /// <param name="strDBColumnType">数据库字段数据类型</param>186         /// <param name="strDBType">数据库MYSQL  SQLSERVER</param>187         /// <returns></returns>188         public static string ToCSDataType(string strDBColumnType, string strDBType)189         {190             string strT = string.Empty;191 192             //根据strDBType 判断数据库是什么,然后转换为程序语言中的数据类型193             switch (strDBType)194             {195                 case "SQLSERVER":196                     var stringwords = new string[]{"char","varchar","text","nchar","nvarchar","ntext"};197                     var intwords = new string[]{"int","smallint","tinyint"};198                     var boolwords = new string[] { "bit"};199                     var longwords = new string[] { "bigint"};200                     var decimalwords = new string[] { "numeric", "decimal", "money","smallmoney","float","real" };201                     var datewords = new string[] { "datetime", "smalldatetime" };202                     if (stringwords.Contains(strDBColumnType.ToLower()))203                     { 204                         strT="string";205                     }206                     else if (intwords.Contains(strDBColumnType.ToLower()))207                     {208                         strT = "int";209                     }210                     else if (longwords.Contains(strDBColumnType.ToLower()))211                     {212                         strT = "long";213                     }214                     else if (boolwords.Contains(strDBColumnType.ToLower()))215                     {216                         strT = "bool";217                     }218                     else if (decimalwords.Contains(strDBColumnType.ToLower()))219                     {220                         strT = "decimal";221                     }222                     else if (datewords.Contains(strDBColumnType.ToLower()))223                     {224                         strT = "DateTime";225                     }226                     else227                     {228                         strT = "string";229                     }230 231 232                     break;233 234                 case "MYSQL":235                      var stringwords1 = new string[]{"char","varchar","text","tinytext","mediumtext","longtext"};236                     var intwords1 = new string[]{"smallint","tinyint","mediumint"};237                     var boolwords1 = new string[] { "bit"};238                     var longwords1 = new string[] { "int,bigint", "integer" };239                     var decimalwords1 = new string[] { "float", "decimal", "double" };240                     var datewords1 = new string[] { "datetime", "date" };241                     if (stringwords1.Contains(strDBColumnType.ToLower()))242                     { 243                         strT="string";244                     }245                     else if (intwords1.Contains(strDBColumnType.ToLower()))246                     {247                         strT = "int";248                     }249                     else if (longwords1.Contains(strDBColumnType.ToLower()))250                     {251                         strT = "long";252                     }253                     else if (boolwords1.Contains(strDBColumnType.ToLower()))254                     {255                         strT = "bool";256                     }257                     else if (decimalwords1.Contains(strDBColumnType.ToLower()))258                     {259                         strT = "decimal";260                     }261                     else if (datewords1.Contains(strDBColumnType.ToLower()))262                     {263                         strT = "DateTime";264                     }265                     else266                     {267                         strT = "string";268                     }269 270 271                     break;272 273                 default:274                     break;275             }276 277             return strT;278         }279 280         /// <summary>281         /// 把小写的sqlserver数据库中的数据类型转为sqlserver参数格式,例如 SqlDbType.VarChar282         /// </summary>283         /// <param name="strDataType"></param>284         /// <param name="strDBType">数据库MYSQL  SQLSERVER</param>285         /// <returns></returns>286         public static string ToDataTypeFormat(string strDataType,string strDBType)287         {288             string strT = string.Empty;289             switch (strDataType.ToLower())290             {291                 case "int":292                     strT = "Int";293                     break;294                 case "varchar":295                     strT = "VarChar";296                     break;297                 case "char":298                     strT = "Char";299                     break;300                 case "bigint":301                     strT = "BigInt";302                     break;303                 case "nvarchar":304                     strT = "NVarChar";305                     break;306                 case "datetime":307                     strT = "DateTime";308                     break;309                 case "smalldatetime":310                     strT = "SmallDateTime";311                     break;312                 case "bit":313                     strT = "Bit";314                     break;315                 case "text":316                     strT = "Text";317 318                     break;319                     case "decimal":320                     strT = "Decimal";321                     break;322                     case "ntext":323                     strT = "NText";324                     break;325                 default:326                     strT = "VarChar";327                     break;328             }329 330             return strT;331         }332 333         /// <summary>334         /// 获取数据类型或控件的简写,用于前缀命名335         /// </summary>336         /// <param name="strLongName"></param>337         /// <returns></returns>338         public static string ToNameFormat(string strLongName)339         {340             string strT = string.Empty;341             switch (strLongName.ToLower())342             {343                 case "int":344                     strT = "int";345                     break;346                 case "string":347                     strT = "str";348                     break;349                 case "char":350                     strT = "ch";351                     break;352                 case "long":353                     strT = "long";354                     break;355                 case "float":356                     strT = "float";357                     break;358                 case "datetime":359                     strT = "date";360                     break;361                 case "double":362                     strT = "double";363                     break;364                 case "bool":365                     strT = "Is";366                     break;367                 case "decimal":368                     strT = "dec";369                     break;370                 case "boolean":371                     strT = "Is";372                     break;373                 default:374                     strT = "x";375                     break;376             }377 378             return strT;379         }380         #endregion381     }382 }

 

4楼Sunday*
建议你用T4写模板,拼串太累了,而且不好修改。
Re: Supper_litt
@Sunday*,汗,我也写了一个代码生成器,不过就是用的拼接字符串。。。。
3楼游龙踏雪
等着开源
2楼Sunday*
不知道 楼主的项目工程是怎么用代码生成器创建的,是否能开源。
Re: 杨丹
@Sunday*,公司这边如果要立项的话可能就不好说,如果不立项,我会开源,不过不是简单的把代码提供下载,希望能搞个svn大家一起做下去。
1楼一个人De奋斗
坐上沙发了,感谢楼主,希望能提供下载
Re: 杨丹
@一个人De奋斗,等我这边测试一段时间后,会提供一个下载的版本。
  相关解决方案