我想重构以下代码,如何注入通知处理程序?最小的原始代码更改和必要时的最佳重构.
public class TestEventHandlers
{
public TestEventHandlers() { }
public void OpenMarket(Page page)
{
var Id = page.Request["MarketId"];
var repository = new EntityRepository();
IEntity market = repository.GetById(Id);
if (market.State != "Open")
{
throw new Exception("The market is not open!");
}
else
{
market.Open();
repository.SaveChangesTo(market);
var smtpClient = new SmtpClient();
var message = new MailMessage();
message.Subject = "market open";
message.Body = market.ToString() + " was open.";
message.To.Add(new MailAddress("market@mail.com"));
smtpClient.Send(message);
}
}
public void CloseMarket(Page page)
{
var Id = page.Request["MarketId"];
var repository = new EntityRepository();
IEntity market = repository.GetById(Id);
if (market.State == "Close")
{
throw new Exception("The market is already close!");
}
else
{
market.Close();
repository.SaveChangesTo(market);
var smtpClient = new SmtpClient();
var message = new MailMessage();
message.Subject = "market closed";
message.Body = market.ToString() + " has been closed.";
message.To.Add(new MailAddress("market@mail.com"));
smtpClient.Send(message);
}
}
}
我已经像下面那样重构了它 –
public class TestEventHandlers
{
public TestEventHandlers() { }
public void OpenMarket(Page page)
{
var Id = page.Request["MarketId"];
if (id!=null)
{
var repository = new EntityRepository();
IEntity market = repository.GetById(Id);
if (market.State != "Open")
{
throw new Exception("The market is not open!");
}
else
{
market.Open();
repository.SaveChangesTo(market);
SendEmailNotification("market open", market.ToString() + " was open.", "market@mail.com");
}
}
else
{
throw new Exception("Id can not be null");
}
}
private static void SendEmailNotification(string subject,string body,string emailAddress)
{
var smtpClient = new SmtpClient();
var message = new MailMessage();
message.Subject = subject;
message.Body = body;
message.To.Add(new MailAddress(emailAddress));
smtpClient.Send(message);
}
public void CloseMarket(Page page)
{
var Id = page.Request["MarketId"];
if(id!=null)
{
var repository = new EntityRepository();
IEntity market = repository.GetById(Id);
if (market.State == "Close")
{
throw new Exception("The market is already close!");
}
else
{
market.Close();
repository.SaveChangesTo(market);
SendEmailNotification("market closed", market.ToString() + " has been closed.", "market@mail.com");
}
}
else
{
throw new Exception("Id can not be null");
}
}
}
最佳答案 我会用这样的东西:
public interface INotifier
{
void SendEmailNotification(string subject, string body, string emailAddress);
}
public class Notifier : INotifier
{
public void SendEmailNotification(string subject,string body,string emailAddress)
{
var smtpClient = new SmtpClient();
var message = new MailMessage();
message.Subject = subject;
message.Body = body;
message.To.Add(new MailAddress(emailAddress));
smtpClient.Send(message);
}
}
public class TestEventHandlers
{
public INotifier Notifier { get; set; }
public TestEventHandlers()
{
Notifier = new Notifier();
}
public void OpenMarket(Page page)
{
var Id = page.Request["MarketId"];
if (id!=null)
{
var repository = new EntityRepository();
IEntity market = repository.GetById(Id);
if (market.State != "Open")
{
throw new Exception("The market is not open!");
}
else
{
market.Open();
repository.SaveChangesTo(market);
Notifier.SendEmailNotification("market open", market.ToString() + " was open.", "market@mail.com");
}
}
else
{
throw new Exception("entityId can not be null");
}
}
public void CloseMarket(Page page)
{
var Id = page.Request["MarketId"];
if(id!=null)
{
var repository = new EntityRepository();
IEntity market = repository.GetById(Id);
if (market.State == "Close")
{
throw new Exception("The market is already close!");
}
else
{
market.Close();
repository.SaveChangesTo(market);
Notifier.SendEmailNotification("market closed", market.ToString() + " has been closed.", "market@mail.com");
}
}
else
{
throw new Exception("entityId can not be null");
}
}
}
在这种情况下,您的INotifier默认为构造函数的常规实现,但在需要时可以使用访问器覆盖.如果您希望在不进行测试时始终注入依赖项,则只需向构造函数添加参数即可.
希望这可以帮助.