Simple Injector 4.1:覆盖参数注入行为

Simple Injector 4.1: Overriding Parameter Injection Behavior

我是在 C# 中使用 DI 的新手,看过 Windsor、Ninject、Autofac、Unity 和 Simple Injector。我最初放弃了 Simple Injector,因为我需要值类型注入(fx.connection strings),但发现了一篇描述这个的博文:https://cuttingedge.it/blogs/steven/pivot/entry.php?id=94。不幸的是,该博文已过时,因为 IDependencyInjectionBehavior.BuildExpression 在 4.1 版中已弃用,取而代之的是引入了 IDependencyInjectionBehavior.GetInstanceProducer。 我不确定如何使用新的 InstanceProducer 执行博文中描述的操作。 InstanceProducer 有一个静态方法 FromExpression 但我不确定应该使用哪种类型等。

我目前做 Pure DI 并有以下设置:

// Settings
var conLocal = ConfigurationManager.ConnectionStrings["APIPortMan"].ConnectionString;
var con = ConfigurationManager.ConnectionStrings["PortMan"].ConnectionString;
var conAzure = ConfigurationManager.ConnectionStrings["Azure"].ConnectionString;
var conSitecore = ConfigurationManager.ConnectionStrings["Sitecore"].ConnectionString;
var azureStorageAccount = ConfigurationManager.AppSettings.Get("StorageConnection");
var reportUploadPath = ConfigurationManager.AppSettings.Get("ReportUploadPath");
var PfsmlPath = ConfigurationManager.AppSettings.Get("PfsmlPath");
var reloadCounter = int.Parse(ConfigurationManager.AppSettings.Get("transactionServiceReloadCounter"));
var systemStartDate = DateTime.Parse(ConfigurationManager.AppSettings.Get("holdingServiceStartDate"));
var semaphoreCount = int.Parse(ConfigurationManager.AppSettings.Get("semaphoreCount"));

然后我有一些存储库使用这些设置:

// Repositories
var _accountRepository = new AccountRepository(con, conAzure);
var _aggregatedPortfolioRelationshipRepository = new AggregatedPortfolioRelationshipRepository(conAzure);
var _aggregatedClientRelationshipRepository = new AggregatedClientRelationshipRepository(con, conAzure);
var _assetBondRepository = new AssetBondRepository(con, conAzure);
var _assetClassRepository = new AssetClassRepository(con, conAzure);
var _assetDerivativeRepository = new AssetDerivativeRepository(con, conAzure);
var _assetRepository = new AssetRepository(con, conAzure);
var _benchmarkRepository = new BenchmarkRepository(con, conAzure);
var _benchmarkWeightRepository = new BenchmarkWeightRepository(con, conAzure);
var _clientRepository = new ClientRepository(con, conAzure);
var _defaultPriceRepository = new DefaultPriceRepository(con, conAzure);
var _emailRepository = new UpdateEmailOutput(conAzure);
var _exchangeRateRepository = new ExchangeRateRepository(con, conAzure);
var _failedHoldingRepository = new FailedHoldingRepository(conLocal);
var _GICSRepository = new GICSRepository(con, conAzure);
var _holdingRepository = new HoldingRepository(conAzure);
var _limitLineRepository = new LimitLineRepository(con, conAzure);
var _PFSMLRepository = new PFSMLRepository(PfsmlPath);
var _portfolioRepository = new PortfolioRepository(con, conAzure);
var _sitecoreReportRepository = new SitecoreReportRepository(conSitecore, reportUploadPath);
var _systemInfoRepository = new SystemInfoRepository(conAzure);
var _transactionRepository = new TransactionRepository(con, conAzure);

后来一些服务使用存储库和一些设置。

因为大多数存储库共享一个公共接口 IRepository<T>(除了像 IAssetRepository 这样的扩展 IRepository 类型为 Asset 的单独接口)我希望能够使用批量创建/自动布线。此外,我想避免每次更改我的主代码时都更改 DI 设置(即新的构造函数参数、新的存储库 interface/class 等)。此外,我想避免在注册过程中使用 lambda、"new" 和 getInstance,因为这将需要在我更改构造函数时更改 DI 设置。

我已经在构造函数中采用了博文中提到的约定(使用AzureConnectionStringPortManConnectionString等)。我现在需要做的就是确保 Simple Injector 根据约定处理值类型参数:)

我在 Github 上发布了同样的问题(正如史蒂文指出的那样)。 https://github.com/simpleinjector/SimpleInjector/blob/v4.0.x/src/SimpleInjector.CodeSamples/ParameterConventionExtensions.cs 包含 convention-based 方法的更新版本,尽管 Steven/dotnetjunkie 说服我采用不同的方法(使用 settings-objects)。