【问题标题】:An academic query about T4 templates关于 T4 模板的学术疑问
【发布时间】:2012-07-08 21:12:59
【问题描述】:

好的, 在我目前的项目中,我想得有点超前,所以我为这个问题的含糊程度深表歉意。是否有可能在解决方案的一个项目中拥有一个 T4 模板,该模板引用解决方案中的其他程序集之一并检查其他程序集的导出类型并使用它们的元数据来构建其他代码?我不需要引用该程序集目录中的类型,我只需要能够获取从特定基类派生的所有类型的列表以及有关它们的一些元数据。我正在考虑专门针对从公共基类构建并由 NHibernate 转储到数据库的某些对象执行此操作,作为一种从它们生成 DTO 类以便在 AJAX 调用期间向客户端抛出的简单方法。我不是在寻找一个绝对完美的解决方案,只是一个可以解决很多简单案例的解决方案。

同样,我真的没有具体的例子。几天后我就直接遇到了这个问题,但我突然想到这个选项可能涵盖了我可能遇到的很多情况。

想法?

【问题讨论】:

    标签: t4


    【解决方案1】:

    是的,这应该没问题 - 您可以使用 指令,也可以使用 $(SolutionDir) 和其他 VS 宏来获取导航到其他项目输出的起点。然后你就可以使用反射来读取你感兴趣的元数据了。

    【讨论】:

    • 当我尝试这个时,将<#@ assembly name="System.Reflection" #> 添加到模板中会产生Error 6 Compiling transformation: Metadata file 'System.Reflection' could not be found。任何想法如何解决这个问题?我需要 MethodInfo 类型的程序集。
    • 没关系...没有必要添加<#@ assembly name="System.Reflection" #>,立即使用<#@ import namespace="System.Reflection" #>
    【解决方案2】:

    我试图实现类似的东西,它工作正常。在下面的示例.tt 文件中,我所指的同一解决方案中我自己的程序集的名称是SomeLibrary。我所反映的类是一个名为SomeLibrary.SomeInterface 的接口。有一些方法可以使它更通用,但我不想让示例过于复杂。另外,请不要关注此模板的整体效果,这只是为了让您对它的工作方式有一个印象:

    <#@ template language="C#" #>
    <#@ output extension=".cs" #>
    <#@ assembly name="$(SolutionDir)$(SolutionName)\bin\$(ConfigurationName)\$(SolutionName).dll" #>
    <#@ import namespace="System.Reflection" #>
    <#
        Type someIType = typeof(SomeLibrary.SomeInterface);
    #>
    namespace SomeLibrary
    {
        class <#=someIType.Name#>Impl: <#=someIType.Name#>
        {
            <#=someIType.Name#> encapsulatedIntf;
            public <#=someIType.Name#>Impl(<#=someIType.Name#> anIntf)
            {
                encapsulatedIntf = anIntf;
            }
    
            // Methods to be implemented:
    <#
        MethodInfo[] methods = someIType.GetMethods();
        foreach (MethodInfo m in methods)
        {
    #>
            // <#=m#>;
    <#
        }
    #>
        }
    }
    

    就我而言,这会导致

    namespace SomeLibrary
    {
        class SomeInterfaceImpl: SomeInterface
        {
            SomeInterface encapsulatedIntf;
            public SomeInterfaceImpl(SomeInterface anIntf)
            {
                encapsulatedIntf = anIntf;
            }
    
            // Methods to be implemented:
            // Int32 someMethod(Int32);
            // System.String someOtherMethod();
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-05-24
      • 1970-01-01
      • 1970-01-01
      • 2011-04-07
      • 1970-01-01
      • 1970-01-01
      • 2021-02-09
      • 1970-01-01
      相关资源
      最近更新 更多