我使用依赖注入很长一段时间,我真的很喜欢这种技术,但我经常遇到一个问题,那就是应该注入太多的依赖关系4-5,这似乎很多。
但我找不到办法让它变得更简单。例如,我有一个具有发送消息的业务逻辑的类,它接受另外两个业务逻辑依赖项来执行所需的操作(一个用于将数据转换为已发送的消息,另一个用于转换已接收的消息)。
但除此之外,还需要一些“技术”依赖,如ILogger
,ITimerFactory
(因为它需要在里面创建计时器),IKeyGenerator
(生成唯一键)。
所以整个名单变得越来越大。有没有什么好的常用方法可以减少依赖项的数量?
答案 0 :(得分:4)
处理这些问题的一种方法是对Aggregates(或Facades)进行重构。 Mark Seemann写了一篇很好的文章,check it out(实际上我强烈推荐his book,只是说)。 所以说你有以下内容(摘自文章):
public OrderProcessor(IOrderValidator validator,
IOrderShipper shipper,
IAccountsReceivable receivable,
IRateExchange exchange,
IUserContext userContext)
您可以将其重构为:
public OrderProcessor(IOrderValidator validator,
IOrderShipper shipper,
IOrderCollector collector)
其中OrderCollector
是一个外观(它包含前三个依赖项):
public OrderCollector(IAccountsReceivable receivable,
IRateExchange exchange,
IUserContext userContext)
我希望这会有所帮助。
修改强>
就横切关注点(例如日志记录和缓存)以及处理它们的策略而言,这是一个建议(这就是我通常所做的),比如你有以下内容:
public interface IOrderService
{
void DoAwesome();
}
public class OrderService : IOrderService
{
public void DoAwesome()
{
// do your thing here ... no logging no nothing
}
}
在这里,我将使用装饰器模式创建一个启用了日志记录的OrderService:
public class OrderServiceWithLogging : IOrderService
{
private readonly IOrderService _orderService;
private readonly ILogger _logger;
public OrderServiceWithLogging(IOrderService orderService, ILogger logger)
{
_orderService = orderService;
_logger = logger;
}
public void DoAwesome()
{
_orderService.DoAwesome();
_logger.Log("Awesome is done!");
}
}
它可能看起来有点开销,但恕我直言,它干净且可测试。
另一种方法是进入面向方面编程并研究诸如拦截之类的概念,其中基本上你拦截某些方法调用并执行任务。许多DI框架(我想说全部?)支持拦截,所以这可能是你喜欢的东西。