Заказное разрешение типов от Castle Windsor AllTypes - PullRequest
1 голос
/ 08 мая 2009

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

private static void ConfigureContainer()
{
    var container = new WindsorContainer();

    container.Register(AllTypes.Of<IStartupTask>()
             .FromAssembly(Assembly.GetExecutingAssembly()))
    ...

    var serviceLocator = container.Resolve<IServiceLocator>();
    ServiceLocator.SetLocatorProvider(() => serviceLocator);
}

Для того, чтобы получить задачи, я использую это, и оно работает как положено:

public static void Run()
{
    var tasks = ServiceLocator.Current.GetAllInstances<IStartupTask>();

    foreach (var task in tasks)
    {
       task.Execute();
    }
}

Вот моя проблема: у меня есть одно задание, которое зависит от того, какое другое запускается первым. Существует задача InitializeDatabase, которую нужно запустить перед задачей PopulateDatabse. Есть также куча других задач, которые выполняются, и я бы не стал разделять задачу InitializeDatabase, если есть некоторая конфигурация Castle, которая позволит мне упорядочить разрешение типов. Я не хочу указывать полный порядок разрешаемых типов, поскольку это противоречит цели автоматической регистрации, просто InitializeDatabase является первым или PopulateDatabase является последним.

Есть ли способ зарегистрировать, какие типы должны быть разрешены в первую очередь, без указания порядка всех типов?

Ответы [ 2 ]

2 голосов
/ 09 мая 2009

Вот один из способов сделать это, он может быть не очень красивым, но он работает:

[AttributeUsage(AttributeTargets.Class)]
public class FirstAttribute: Attribute {}
public interface IService {}
public class ThirdService : IService { }
[First]
public class FirstService : IService { }
public class SecondService: IService {}

[Test]
public void WindsorOrder() {
    var container = new WindsorContainer();

    container.Register(AllTypes.Of<IService>()
        .FromAssembly(Assembly.GetExecutingAssembly()));

    var intf = container.ResolveAll<IService>()
        .OrderByDescending(i => i.GetType().GetCustomAttributes(typeof(FirstAttribute), true).Length)
        .ToArray();
    Assert.IsInstanceOfType(typeof(FirstService), intf[0]);
}

Если вы удалите [First] из FirstService, первым будет ThirdService, и тест не пройдёт.

0 голосов
/ 11 мая 2009

Используйте HandlerSelector для этого

...