2013-09-04 4 views
4

Я хотел бы решить следующие с Виндзорский замок:Виндзорский замок решительность массив с открытым общим и интерфейсом

IEnumerable<Definition<IEntity>> 

На данный момент я только получаю сообщение об IEnumerable с 1 объект, который соответствует первой реализации IEntity ,

Я хотел бы массив

{ Definition<Entity1>, Definition<Entity2>, ... } 

У меня требуется чувство суб распознаватель, но я понятия не имею, с чего начать.

Update

var container = new WindsorContainer(); 
container.Kernel.Resolver.AddSubResolver(
    new CollectionResolver(container.Kernel, true)); 

container.Register(Component.For(typeof (Definition<>))); 

var binDir = HostingEnvironment.MapPath("~/bin"); 
var assemblyFilter = new AssemblyFilter(binDir); 

container.Register(Types.FromAssemblyInDirectory(assemblyFilter) 
    .BasedOn<IEntity>() 
    .Unless(t => t.IsAbstract || t.IsInterface) 
    .WithServiceAllInterfaces() 
    .LifestyleTransient()); 

// This doesn't work! 
var items = container.Resolve(typeof(IEnumerable<Definition<IEntity>>)); 
+0

Не могли бы вы добавить свой регистрационный код? – Marwijn

+0

Местоположение - это ваши реализации для определения <>? –

ответ

1

Во-первых, я думаю, что вы должны улучшить свой дизайн немного. Я не знаю, фактический контекст, но я считаю, что ваша цель состоит в следующем:

public interface IEntity 
{ 
} 

public class Entity1 : IEntity 
{ 
} 

public class Entity2 : IEntity 
{ 
} 

public abstract class Definition<TEntity> 
    where TEntity : IEntity 
{ 
} 

public class Entity1Definition : Definition<Entity1> 
{ 
} 

public class Entity2Definition : Definition<Entity2> 
{ 
} 

При такой конструкции у вас есть проблема, что следующий код не является допустимым:

Definition<IEntity> definition = new Entity1Definition(); 

Для того, для этого вам нужно ввести ковариантный общий интерфейс для типа IEntity. Подробнее о ковариации и контрвариацию вы можете найти здесь: Covariance and Contravariance in Generics

Поэтому я предлагаю вам представить следующий интерфейс:

public interface IDefinition<out TEntity> 
    where TEntity : IEntity 
{ 
} 

Обратите внимание на из ключевых слов, помечает интерфейс как коварианта. А затем вывести свой Определение <TEntity> из этого раздела:

public abstract class Definition<TEntity> : IDefinition<TEntity> 
    where TEntity : IEntity 
{ 
} 

Теперь, когда мы поставили перед собой конструкцию таким образом, остальное легко. Мы можем зарегистрировать компоненты, как это:

WindsorContainer container = new WindsorContainer(); 
container.Kernel.Resolver.AddSubResolver(
     new CollectionResolver(container.Kernel, true)); 

container.Register(Types.FromThisAssembly() 
     .BasedOn(typeof(IDefinition<>)) 
     .Unless(t => t.IsAbstract || t.IsInterface) 
     .WithServices(typeof(IDefinition<IEntity>)) 
     .LifestyleTransient()); 

А потом решить их:

var items = container.ResolveAll(typeof(IDefinition<IEntity>)); 

Обратите внимание, что для решения всех экземпляров для зарегистрированной службы в Виндзоре, вы должны вызвать метод ResolveAll.

Смежные вопросы