假设我在容器中注册了多个对象,所有对象都实现了相同的接口:
container.Register(
Component.For<ITask>().ImplementedBy<Task1>(),
Component.For<ITask>().ImplementedBy<Task2>(),
Component.For<ITask>().ImplementedBy<Task3>(),
Component.For<ITask>().ImplementedBy<Task4>(),
);
我希望解决ITask的所有实现:
var tasks = container.ResolveAll<ITask>();
有没有办法控制已解析实例的顺序?
注意:显然,我可以在ITask上实现Order
或Priority
属性,只需对任务列表进行排序,但我正在寻找更低级别的解决方案。
答案 0 :(得分:6)
我相信你所寻找的是一个处理程序过滤器,它基于稀少的文档和Windsor Castle 3中的重大变化;它提供组件的过滤和排序。这是他们的Wiki页面的摘录
接口类似于IHandlerSelector但允许您使用 filter.ResolveAll()方法
请求的过滤器/排序处理程序
所以基本上你需要实现IHandlerFilter
接口,然后在初始化Windsor容器时将此实现添加到内核中。从source code开始,此界面看起来与此类似......
public interface IHandlerFilter
{
bool HasOpinionAbout(Type service);
IHandler[] SelectHandlers(Type service, IHandler[] handlers);
}
将处理程序过滤器添加到内核中,如下所示......
var container = new WindsorContainer()
.Install(Configuration.FromXmlFile("components.config"));
container.Kernel.AddHandlersFilter(new YourHandlerFilterImplementation());
然后在使用ResolveAll
解析服务的所有组件时,将根据您自己的实现对订单进行排序(和过滤)
答案 1 :(得分:3)
我是第二个Leo的建议,即你所追求的是一个处理程序过滤器。
在我的博客上,我有this example on how a simple handlers filter can be made,恰好是通过ResolveAll<ITask>
(或IEnumerable<ITask>
注入时)导致有序任务实例的那个:< / p>
class TaskHandlersFilter : IHandlersFilter
{
readonly Dictionary<Type, int> sortOrder =
new Dictionary<Type, int>
{
{typeof (PrepareSomething), 1},
{typeof (CarryItOut), 2},
{typeof (FinishTheJob), 3},
};
public bool HasOpinionAbout(Type service)
{
return service == typeof(ITask);
}
public IHandler[] SelectHandlers(Type service, IHandler[] handlers)
{
// come up with some way of ordering implementations here
// (cool solution coming up in the next post... ;))
return handlers
.OrderBy(h => sortOrder[h.ComponentModel.Implementation])
.ToArray();
}
}
我还有more elaborate example用于指定排序的API - 在这种情况下,我允许类型指定相对于其他类型的位置,例如像
[ExecutesBefore(typeof(ExecutePayment))]
public class ValidateCreditCards : ITask { ... }
在您的具体情况中可能/可能没用:)