Asp.net mvc 如何为asp.net mvc设置电子邮件或通知服务
如何创建一个可以模拟和单元测试的电子邮件发送通知服务类 我的服务位于另一层,即类库。我试图不导入smtp客户端,但如果这是不可避免的,那么它就没有问题。这就是我现在拥有的:Asp.net mvc 如何为asp.net mvc设置电子邮件或通知服务,asp.net-mvc,design-patterns,asp.net-mvc-3,Asp.net Mvc,Design Patterns,Asp.net Mvc 3,如何创建一个可以模拟和单元测试的电子邮件发送通知服务类 我的服务位于另一层,即类库。我试图不导入smtp客户端,但如果这是不可避免的,那么它就没有问题。这就是我现在拥有的: public class EmailNotificationService : INotificationService { private readonly EmailNotification _emailNotification; public EmailNotificationService(Emai
public class EmailNotificationService : INotificationService
{
private readonly EmailNotification _emailNotification;
public EmailNotificationService(EmailNotification emailNotification)
{
_emailNotification = emailNotification;
}
public void Notify()
{
using (var mail = new MailMessage())
{
//If no replyto was passed in the notification, then make it null.
mail.ReplyTo = string.IsNullOrEmpty(_emailNotification.ReplyTo) ? null : new MailAddress(_emailNotification.ReplyTo);
mail.To.Add(_emailNotification.To);
mail.From = _emailNotification.From;
mail.Subject = _emailNotification.Subject;
mail.Body = _emailNotification.Body;
mail.IsBodyHtml = true;
//this doesn't seem right.
SmtpClient client = new SmtpClient();
client.Send(mail);
}
}
}
public class EmailNotification
{
public EmailNotification()
{
To = "";
ReplyTo = "";
Subject = "";
Body = "";
}
public string To { get; set; }
public string ReplyTo { get; set; }
public string Subject { get; set; }
public string Body { get; set; }
}
如果不想导入System.Net.Mail库,则必须使用接口。请注意,这对您的单元测试并没有多大帮助
public interface IEmailSender{
void Send(EmailNotification emailNotification);
}
然后在EmailNotificationService类中,您可以添加以下属性或在构造函数中传入IEmailSender
private IEmailSender emailSender;
public IEmailSender EmailSender
{
get{
if(this.emailSender == null){
//Initialize new EmailSender using either
// a factory pattern or inject using IOC
}
return this.emailSender
}
set{
this.emailSender = value;
}
}
您的通知方法将成为
public void Notify()
{
EmailSender.Send(_emailNotification);
}
然后,您将创建一个实现IEmailSender接口的具体类
public class MyEmailSender: IEmailSender
{
public void Send(EmailNotification emailNotification)
{
using (var mail = new MailMessage())
{
//If no replyto was passed in the notification, then make it null.
mail.ReplyTo =
string.IsNullOrEmpty(_emailNotification.ReplyTo) ? null :
new MailAddress(_emailNotification.ReplyTo);
mail.To.Add(emailNotification.To);
mail.From = emailNotification.From;
mail.Subject = emailNotification.Subject;
mail.Body = emailNotification.Body;
mail.IsBodyHtml = true;
SmtpClient client = new SmtpClient();
client.Send(mail);
}
}
}
发送电子邮件实际上比听起来和应该的要复杂得多。你想在这里测试什么?在这个类中,您几乎无法进行单元测试。测试它是否真的发送电子邮件是一项集成测试。您希望EmailNotificationService做什么??发送电子邮件当然。。。我认为你的设计过于复杂了。你面临的单元测试有没有一个特别的问题,这门课正在讨论?这个类看起来不错,我怀疑您的测试才是真正的问题所在。与其让IEmailSender接口的属性由私有字段支持,不如让它作为构造函数参数传递。但是不管怎样,除了getter返回适当的实例之外,您仍然没有任何需要测试的内容,而该实例不在原始代码中,因此OP在其原始实现中仍然没有任何可以进行单元测试的内容。。就像你说的,它要么发送邮件,要么不发送