【问题标题】:Code generation via sibling file in micro-service通过微服务中的兄弟文件生成代码
【发布时间】:2020-07-28 21:30:33
【问题描述】:

是否有一个 nuget 可以通过命令行(就像 EF Tools 使用 add-migration 一样)从我的实体(名称和属性)中包含的信息生成“兄弟”代码(又名样板文件)?

【问题讨论】:

    标签: c# templates microservices code-generation boilerplate


    【解决方案1】:

    最简单的方法可能是使用代码生成器来生成所有样板代码。 尽管许多代码生成器使用自己的模型来定义域实体,但它可能会很高效并节省大量工作量。

    带有 C# 模板 (https://github.com/telosys-templates-v3/csharp-web-mvc) 的 Telosys (https://www.telosys.org/) 等一些工具可用于 .Net 项目。

    在您的情况下,您只需在 DSL 模型中重新定义您的实体(参见 https://www.telosys.org/dsl-syntax.html,这很简单)

    另请参阅此回复: How to generate whole boiler plate code for CRUD operations like visual studio using code?

    【讨论】:

      【解决方案2】:

      我最终选择了 T4 文本模板,它基本上包括在每个文件夹中放置一个 .tt 文件。
      为了为每个实体创建相应的文件,我不得不使用一些反射(这部分很棘手)

      非常感谢最初创建 SaveOutput 方法的人。

      我在这里粘贴了一个工作模板。一个非常简单的,以便更好地理解。
      如果您使用 Resharper,我建议您安装 ForTea 插件。否则,处理模板变得非常困难。

      <#@ template debug="true" hostspecific="true" language="C#" #>
      <#@ assembly name="System.Core" #>
      <#@ assembly name="netstandard, Version=2.0.0.0, Culture=neutral, PublicKeyToken=cc7b13ffcd2ddd51" #>
      <#@ assembly name="$(TargetDir)MyProject.Shared.Domain.dll" #>
      <#@ assembly name="$(TargetDir)MyProject.Shared.Common.dll" #>
      <#@ assembly name="$(TargetDir)MyProject.Domain.dll" #>
      <#@ import namespace="System.IO" #>
      <#@ import namespace="System.Reflection" #>
      <#@ import namespace="MyProject.Shared.Common.Helpers" #>
      <#@ import namespace="MyProject.Shared.Common.Extensions" #>
      <#@ import namespace="MyProject.Shared.Domain.Entities" #>
      <#@ output extension=".txt" #>
      <#
      var types = FileHelper.GetTypes(typeof(IEntity),Assembly.LoadFrom(typeof(IEntity).Assembly.CodeBase.Replace("MyProject.Shared.Domain.dll","") +  "MyProject.Domain.dll"));
      foreach (var type in types) {
      
      if(new[]
      {
          //////// Exclude ////////
          "a"
          //, "b"
          //, "c"
          /////////////////////////
      }.Any(c => type.Name.Contains(c))) continue;
      
      ////////////////////////////////////////////// Your code //////////////////////////////////////////////
      #>
      namespace MyProject.Application.Messages
      {
          public static class <#=type.Name#>Message
          {
              public const string <#=type.Name#>NotFound = "The <#=type.Name.ToReadable()#> does not exist";
              public const string <#=type.Name#>AlreadyExists = "The <#=type.Name.ToReadable()#> already exists";
          }
      }
      <#
      ///////////////////////////////////////////////////////////////////////////////////////////////////////
      
      SaveOutput(type.Name + "Message.cs");
      }
      #>
      <#+
      private void SaveOutput(string outputFileName) {
      var templateDirectory = Path.GetDirectoryName(Host.TemplateFile);
      if (templateDirectory == null) return;
      var outputFilePath = Path.Combine(templateDirectory, outputFileName);
      if(!File.Exists(outputFilePath)) File.WriteAllText(outputFilePath, this.GenerationEnvironment.ToString()); 
      GenerationEnvironment.Remove(0, GenerationEnvironment.Length);
      }
      #>
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2018-10-26
        • 1970-01-01
        • 2019-05-06
        • 2018-10-08
        • 2021-05-12
        • 2016-05-15
        • 1970-01-01
        • 2011-09-04
        相关资源
        最近更新 更多