zoukankan      html  css  js  c++  java
  • C#"CodeSmith代码批量生成模板"制作经验分享

           最近忙的有些一头雾水,原本定的计划:每周写一篇技术文章,也被整的‘搁浅’了。今天感觉怎么着也得写一篇,要不这个计划可能又很难坚持下去了(ps: 写东西,不仅要时间,更重要的是心情——能静下心去写)。直接说正题,——代码生成器,应该是每个程序员必备的工具,无论你是做什么开发 或 使用的那种编程语言,它都能在很大程度上为你节省不少时间;而做C#开发的,可选的代码生成器,可能要更多 ——用的比较多、好用的 有: CodeSmith,动软代码生成器...。在这里,先简要的说下 我对这两种工具的使用感受:a. CodeSmith是我常用的,比较好用 ,可以很好的支持mysql,mssql,access等数据库的三层代码类 和数据库表的相关存储过程等,其模板(制作)语言比较简单易用,缺点:目前网上可用的 和其默认的模板,都不支持批量生成代码类,即每次只能生成一个表的对应模板类。b.动软代码生成器, 跟CodeSmith比,其优点在于:开源免费,可以批量生成,缺点(仅针对于我下载使用的,或者说是我个人的看法):对access数据库的支持不好(无法生成),其它的它们到底哪个更功能强大或好用,这里就不再讨论和深究。

          之前,在做配餐系统开发时,因一开始数据库中的表不多,就10个左右,用CodeSmith一个个去生成相关类,虽感觉有些麻烦,但也没想着找个能一次性搞定的方法,就有些‘麻木’的用着。而最近,需要在已做好的配餐系统中增加一个新的模块 ——此模块差不多要新建6个左右的数据库表。表增加了,那些可以用CodeSmith生成的类,自然需要一个个去生成,再加上数据库表并不是一下就能定好的,增改字段都是很正常的事,这样,就突然感觉,如果在do like this(如此操作),会浪费不少时间,也麻烦,于是,想偷懒,省事 ——(ps:呵呵...,不得不说很多工具正是因为人们想偷懒省事而创造出来。)就自然而然需要想办法实现‘代码批量’生成。 先上网找找看,一搜“CodeSmith代码批量生成模板”,却基本上没有此类信息,还好看到一个网友写的一篇“CodeSmith代码批量生成模板”测试类的文章,看后,有些收获,按其方法 将自己的模板修改后,批量生成模板搞定。现将模板 和 制作方法 贴出,希望对需要的朋友有些帮助!

        1. 批量生成模板:BatchCreate.cst

     

    <%--
    作者:know@more
    Blog:http:
    //www.cnblogs.com/know/
    --%>
    <%@ CodeTemplate Inherits="CodeTemplate" Language="C#" TargetLanguage="Text" Description="NetTiers main template." Debug="True" ResponseEncoding="UTF-8"%>

    <%-- 注册模板类start --%>
    <%-- 注册实体层Entity模板 --%>
    <%@ Register Name="EntityTemplate" Template="DBMad.Models.cst" MergeProperties="Flase" ExcludeProperties=""%>
    <%-- 注册业务逻辑层Business模板 --%>
    <%@ Register Name="BusinessTemplate" Template="DBMad.BLL.cst" MergeProperties="Flase" ExcludeProperties=""%>
    <%-- 注册模板类end --%>

    <%-- 模板属性start --%>
    <%-- 数据库 --%>
    <%@ Property Name="SourceDatabase" Type="SchemaExplorer.DatabaseSchema" DeepLoad="True" Optional="False" Category="01. Getting Started - Required" Description="Database that the tables views, and stored procedures should be based on. IMPORTANT!!! If SourceTables and SourceViews are left blank, the Entire Database will then be generated." %>
    <%-- 命名空间 --%>
    <%@ Property Name="MainNamespace" Default="MyPro" Type="System.String" Category="Context" Description="Your project name if you want use to Namespace!" %>
    <%@ Property Name="ModelNamespace" Default="Model" Type="System.String" Category="Context" Description="this layer Namespace Name" %>
    <%-- 模板属性end --%>

    <%
    if(this.OutputDirectory=="" || !System.IO.Directory.Exists(this.OutputDirectory))
    {
    Debug.WriteLine(
    "----------------------Error: 请核实OutputDirectory是否存在!----------------------");
    return;
    }

    //创建实体层Entity类
    this.GenerateEntityClasses();
    //this.GenerateBLLClasses(); //----可以根据需要选择生成
    //this.GenerateDALClasses();

    Debug.WriteLine(
    "Create Over!");
    %>

    <script runat="template">
    //生成实体Entity类
    private void GenerateEntityClasses()
    {
    Debug.WriteLine(
    "----------------------实体Entity类 生成Start----------------------");
    CodeTemplate Template
    = new EntityTemplate();
    foreach(TableSchema table in this.SourceDatabase.Tables)
    {
    string FileDirectory = this.GetFileDirectory("Model",table.Name,"");
    //生成模板---设置属性
    Template.SetProperty("TargetTable",table);
    Template.SetProperty(
    "ModelsNamespace",this.MainNamespace+this.ModelNamespace);
    //文件输出
    Template.RenderToFile(FileDirectory,true);
    Debug.WriteLine(FileDirectory
    +" 创建成功.");
    }
    Debug.WriteLine(
    "----------------------实体Entity类 生成End----------------------");
    }


    //将字符串首字母转换为大写
    private string MakeCamel(string value)
    {
    return value.Substring(0, 1).ToUpper() + value.Substring(1);
    }

    private string GetFileDirectory(string flolderName,string tabName,string surfix)
    {
    return string.Format("{0}\\{1}\\{2}{3}.cs",OutputDirectory,flolderName,MakeCamel(tabName),surfix);
    }
    </script>


    <script runat="template">
    //解决方案输出路径
    private string Directory = String.Empty;

    [Editor(
    typeof(System.Windows.Forms.Design.FolderNameEditor), typeof(System.Drawing.Design.UITypeEditor))]
    [Optional, NotChecked]
    [DefaultValue(
    "")]
    public string OutputDirectory
    {
    get
    {
    return Directory;
    }
    set
    {
    if (value.EndsWith("\\")) value = value.Substring(0, value.Length - 1);
    Directory
    = value;
    }
    }
    </script>

          此批量生成模板——生成的 模型层, 批量生成模板 和 实体类模板(DBMad.Models.cst)文件的,目录位置如下:

    ——此例中,是并列

      制作的关键点:1.BatchCreate.cst中注册 调用模板——类似于 .net中 注册自定义控件

     <%-- 注册实体层Entity模板 --%>
    <%@ Register Name="EntityTemplate" Template="DBMad.Models.cst" MergeProperties="Flase" ExcludeProperties=""%>

    2. BatchCreate.cst 的生成方法中,调用模板,并设置调用模板的属性

     CodeTemplate Template = new EntityTemplate();
            foreach(TableSchema table in this.SourceDatabase.Tables)
            {
       string FileDirectory = this.GetFileDirectory("Model",table.Name,"");
                //生成模板---设置属性
                Template.SetProperty("TargetTable",table);
       Template.SetProperty("ModelsNamespace",this.MainNamespace+this.ModelNamespace);
                //文件输出
                Template.RenderToFile(FileDirectory,true);
                Debug.WriteLine(FileDirectory +" 创建成功.");
            }

       ok, 大致方法如上,如有不清楚的朋友,可留言,再详细说明!

  • 相关阅读:
    后缀数组-另辟蹊径
    Project Euler 不定期更新
    Educational Codeforces Round 93 (Rated for Div. 2)
    Codeforces Round #664 (Div. 2)
    lower_bound和upper_bound的用法
    Codeforces Round #663 (Div. 2)
    Codeforces Round #661 (Div. 3)
    质数笔记
    C++运算符的优先级
    图的构建
  • 原文地址:https://www.cnblogs.com/know/p/2003876.html
Copyright © 2011-2022 走看看