问题
Ok, I'm thinking a little ahead here in my current project, so I apologize for how vague this question is going to be. Is it possible in one project of a solution to have a T4 template that references one of the other assemblies in the solution and inspects the exported types of the other assembly and uses their metadata to build up other code? I don't need to reference the types in that assembly directory, I just need to be able to get a list of all of them that derive from a particular base class and some metadata about them. I'm thinking of doing this specifically for some objects that are built up from a common base class and dumped to the database by NHibernate as an easy way to generate DTO classes from them for throwing at the client during AJAX calls. I'm not looking for an absolutely perfect solution, just one that gets a lot of the easy cases out of the way.
Again, I don't really have a specific example. I'm a few days out from running into this problem head-on, but it occurred to me that this option might cover a lot of the cases I might run into.
Thoughts?
回答1:
Yep, this should be fine - you can use the <#@ assembly #> directive and also use $(SolutionDir) and other VS macros to get a starting point to navigate to your other project's output. Then you can use reflection to read the metadata you're interested in.
回答2:
I was trying to achieve something similar and it works fine. In the example .tt
file below, the name of my own assembly in the same solution that I am referring to is SomeLibrary
. The class I am reflecting on is an interface called SomeLibrary.SomeInterface
. There are ways to make this more generic, but I did not want to make the sample too complicated. Also, please do not pay attention to the overall result of this template, this is just to give you an impression on how it would work:
<#@ 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#>;
<#
}
#>
}
}
In my case, this results in
namespace SomeLibrary
{
class SomeInterfaceImpl: SomeInterface
{
SomeInterface encapsulatedIntf;
public SomeInterfaceImpl(SomeInterface anIntf)
{
encapsulatedIntf = anIntf;
}
// Methods to be implemented:
// Int32 someMethod(Int32);
// System.String someOtherMethod();
}
}
来源:https://stackoverflow.com/questions/11371641/an-academic-query-about-t4-templates