#dependency-injection #inversion-of-control #castle-windsor #ioc-container
#внедрение зависимостей #инверсия управления #замок-Виндзор #ioc-контейнер
Вопрос:
У меня есть много классов, которые принимают IMyService в качестве аргумента конструктора.
например
ClassA(IMyservice myservice)
// this should take a Concrete1 for IMyService
ClassB(IMyservice myservice)
// this should take a Concrete2 for IMyService
Как мне выполнить регистрацию, чтобы ClassB получал Concrete2, а ClassA — Concrete1?
Кроме того, есть ли способ сделать его стандартным и указать только экземпляры, которые отклоняются от значения по умолчанию? (Поскольку большинство примет Concrete1, и только небольшое число примет Concrete2.)
Я использую интерфейс fluent, А НЕ конфигурацию XML.
Ответ №1:
Используйте переопределения служб:
var container = new WindsorContainer();
container.Register(
Component.For<IMyService>().ImplementedBy<Concrete1>().Named("C1"),
Component.For<IMyService>().ImplementedBy<Concrete2>().Named("C2"),
Component.For<ClassA>().ServiceOverrides(ServiceOverride.ForKey("service").Eq("C1")),
Component.For<ClassB>().ServiceOverrides(ServiceOverride.ForKey("service").Eq("C2"))
);
Комментарии:
1. есть ли способ установить значение по умолчанию и просто переопределить исключения. В противном случае мне нужно было бы выполнить около 100 конкретных регистраций для concrete1 и около 3 для concrete2 — спасибо
2. Когда компоненту требуется «IMyService», я думаю, Windsor всегда вернет первый зарегистрированный. Таким образом, вы, вероятно, могли бы пропустить ServiceOverride для ClassA (и других 100 случаев) и просто использовать его в 3 дополнительных случаях.
3. что такое C1 и C2 в этом случае? являются ли они произвольными именами, присвоенными регистрациям, чтобы вы могли ссылаться на них в serviceOverrides? или они соответствуют фактическим классам в моем проекте? еще раз спасибо
4. Первое: просто произвольные имена, используемые для идентификации различных реализаций в переопределениях службы.