1

在我们以前的应用程序中,我们使用了StructureMap,我们可以编写很少的代码。asp.net核心内建依赖注入长代码

每次服务前,我们添加了依赖关系,如:

[SetterProperty] 
public IXService XService { get; set; } 

,并在构造函数中

ObjectFactory.BuildUp(this); 

然后在测试中,我们可以简单地通过

var service = new XService(); 

实例它现在,我们启动另一个应用程序并使用asp.net核心内置DI容器。 它看起来像我们应该写很多代码,而且很长的构造为每个测试:

private readonly ILogger<AccountsController> _logger; 
    private readonly IMapper _mapper; 
    private readonly IAccountBlService _accountBlService; 
    private readonly IValidationHelper _validationHelper; 
    private readonly IValidator<AccountDTO> _accountDTOValidator; 
    private readonly Example _example; 
    private readonly IConfiguration _configuration; 

    public AccountsController(BillingContext context, ILogger<AccountsController> logger, IMapper mapper, IAccountBlService accountBlService, 
     IValidationHelper validationHelper, IValidator<AccountDTO> accountDTOValidator, IOptions<Example> example, IConfiguration configuration) 
    { 
     _logger = logger; 
     _mapper = mapper; 
     _accountBlService = accountBlService; 
     _validationHelper = validationHelper; 
     _accountDTOValidator = accountDTOValidator; 
     _configuration = configuration; 
     _example = example.Value; 
    } 

有我们没有找到一个较短的方法吗?计划在不久的将来?我们应该使用StructureMap来代替内置的容器吗?或者这有什么缺点?谢谢!

回答

5
  • 有没有更短的方式,我们没有找到? 总之:没有,没有默认容器。但是我建议你阅读Mark Seemann在.NET中的依赖注入(如果你有,那么请忽略我这么说),因为你听说过“Composition Root”吗?恕我直言,你声明依赖的方式有相同数量的代码,只是分散在你的代码库中。虽然你应该把它放在一个可维护性的地方。
  • 是一个计划在不久的将来?不是我所知道的,但真的如果你看看它,它是相同数量的代码,只是集中。然而,我们使用NServiceBus的能力来调用BusConfiguration上的“RegisterComponents”,它使用反射来在一次调用中注册所有的依赖关系。你可以寻找可以做同样的容器。现在,如果你考虑你的测试,如果你使用XUnit,你可以通过de test类的构造函数来设置你的SUT。在工厂类重构它,所以你只需要写一次。通过这种方式,您还可以将模拟测试保持干净。
  • 我们应该用StructureMap,而不是内置容器? 如果你愿意。我们使用Autofac。
  • 还是有这个缺点? 不是我们迄今为止遇到的。有时你需要IServiceProvider来获得特殊的“技巧”,但总有一种方法。

注:如果您担心在你的控制器7只依赖(这是很多确实)有几个选项:

  • 看那依赖的范围。如果它在1种或2的操作方法仅用于你也可以把它声明[FromService]在操作方法的签名

  • 是您的控制器做得太多?小心上帝的课程。也许它需要重构。毕竟,控制器不过是动作方法的逻辑集合。

  • 可以依赖结合?有时似乎他们需要分离,但在大多数情况下,他们总是成对的。看起来有很高的凝聚力,你可以把它们组合成一个辅助班,以保持凝聚力。