我试图使用Castle.Windsor(3.2.0.0)convention based registration,但似乎无法弄清楚如何注册实现特定接口的类仅在特定的命名空间中。
e.g。我真正想要写的是这样的:
container.Register(Classes.FromThisAssembly()
.InNamespace("MyApp.EventHandlers")
.BasedOn(typeof(IHandlesEvent<>))
.WithServiceAllInterfaces()
但是我得到一个警告,似乎暗示这将真正做的是在EventHandlers
命名空间中注册所有内容,然后在当前程序集中注册实现IHandlesEvent<>
的所有内容。
如果我运行应用程序,这似乎确实发生了什么。我不希望注册实现该接口的所有内容(例如,某些实现类是Sagas,需要手动跟踪)并且我并不真正希望该命名空间中的所有内容都已注册。 / p>
我真的不想单独注册事件处理程序,但我无法从Windsor文档中看到如何按惯例执行我需要的操作。有可能吗?
答案 0 :(得分:2)
我也很惊讶,但我可以观察到Castle 3.2上的行为。 BasedOn
发出警告说它会重新初始化注册:这是我的示例代码:
namespace WindsorTest
{
public interface IHandlesEvent {}
public interface IDontWantToBeRegistered {}
namespace Select
{
public class SelectClass : IHandlesEvent { }
public class DontRegisterMe : IDontWantToBeRegistered { }
}
namespace DontSelect
{
public class DontSelectClass: IHandlesEvent {}
}
internal class Program
{
private static void Main(string[] args)
{
var container = new WindsorContainer();
container.Register(Classes.FromThisAssembly()
.InNamespace("WindsorTest.Select")
.BasedOn<IHandlesEvent>()
.WithServiceAllInterfaces()
);
foreach (var handler in container.ResolveAll<IHandlesEvent>())
{
Console.WriteLine(handler.GetType().Name);
}
foreach (var handler in container.ResolveAll<IDontWantToBeRegistered>())
{
Console.WriteLine(handler.GetType().Name);
}
Console.ReadLine();
}
}
}
运行时输出DontSelectClass
。
但是我找到了一种方法,可以从注册的基类开始,然后使用命名空间对其进行优化。只需使用:
container.Register(Classes.FromThisAssembly()
.BasedOn<IHandlesEvent>()
.If(t => t.Namespace == "WindsorTest.Select")
.WithServiceAllInterfaces()
);