自定义 T4 预处理模板
本文关键字:预处理 T4 自定义 | 更新日期: 2023-09-27 18:35:09
我想做什么
我正在尝试使用 T4 创建邮件模板。
我正在使用一个预处理的模板,如果我理解正确,如果我想在运行时生成消息而不引入对Microsoft.VisualStudio.TextTemplating
程序集的依赖,这就是我必须做的。
由于我想将一些数据传递给我的模板,因此我向其添加了参数:
<#@ template language="C#" #>
<#@ parameter name="Param1" type="System.String" #>
<#@ parameter name="Param2" type="System.
Lorem <#= Param1 #> dolor <#= Param2 #>
然后我可以生成传递参数的消息,如下所示:
static void Main(string[] args) {
var template = new LoremIpsum();
template.Session = new Dictionary<string, object>() {
{"Param1", "ipsum"},
{"Param2", "sit amet"},
};
template.Initialize();
string text = template.TransformText();
}
问题出在哪里
由于我需要生成其中的几个类,我希望它们都有一个通用的方法来发送邮件,如下所示:
public void SendMail(string to, IDictionary<string, object> parameters)
或者,甚至更好:
public void SendMail(string to, string Param1, string Param2)
由于生成的类是分部的,因此可以向它们添加方法,添加另一个分部类声明,但这意味着我必须为所有生成的类重复(或多或少)相同的代码。
到目前为止我尝试过什么
我尝试创建一个基类,但如果我尝试这样做:
<#@ template language="C#" inherits="MailTemplateBase" #>
然后生成的代码中断,因为生成的类依赖于定义一些帮助程序方法的LoremIpsumBase
基类(我真的认为让每个生成的类从几乎相同但不同的基类继承没有意义)。
问题
- 如何为我的模板设置基类?
- 如何生成接受与模板中声明的参数相同的参数的方法?
我认为您需要创建一个空模板,复制创建的类并将其用作基类。然后,您可以使用所需的任何属性对其进行扩展。(复制代码后,无需保留空模板)
对于它的价值,我认为您正在尝试做的事情在VS 2010 RTM中开箱即用,但是VS2010 SP1改变了行为,因此您可以自己对模板进行子类。有关详细信息,请查看此连接问题。
编辑:
就将电子邮件方法放在底座上而言,我可能不会那样做。您可能需要考虑公开某种模板服务,该服务具有您需要的各种方法,例如:
public class TemplatingService : ITemplatingService
{
public string GenerateReminderMessage(string to, string name)
{
// Construct the template, passing in the parameters into the session as required
...
// Return the results of the template transformation
}
}
这样,您将从实际的 T4 实现中抽象出来,因此,如果某些内容确实在某个地方发生故障,您只需在一个类中修复它。
并公开使用模板服务生成邮件内容的邮件服务:
public class MailService : IMailService
{
public void SendReminderEmail(string to, string name)
{
var message = this.TemplatingService.GenerateReminderMessage(to, name);
this.MailerService.SendEmail(to, message);
}
}
请注意,MailerService 只是 .NET 邮件代码的简单包装器,但它允许您单独对 MailService 进行单元测试。
可能有更多的方法可以抽象出来,但这将是一个开始。
希望有帮助。
听起来你假设构造函数注入是将数据注入类的唯一方法。但是,我想在这种情况下,梅托德/属性注入是更好的选择。
我手头没有编译器,也无法确定验证它,但似乎它可以工作。