Подтвердить что ты не робот

Обнаружение причины круговой зависимости в Unity

Можно ли настроить Unity для обнаружения циклической ссылки или для перехвата распознавателя типа для отображения некоторой информации об отладке?

Пример

Вот пара интерфейсов и классов, которые зависят друг от друга

public interface IThing1 { }

public class Thing1 : IThing1
{
    private IThing2 _thing2;

    public Thing1(IThing2 thing2)
    {
        _thing2 = thing2;
    }

}

public interface IThing2 { }

public class Thing2 : IThing2
{
    private IThing1 _thing1;

    public Thing2(IThing1 thing1)
    {
        _thing1 = thing1;
    }
}

Замок Виндзор

Если эти два типа настроены в Castle Windsor, он выдаст исключение и предоставит некоторую отладочную информацию, чтобы найти круговую ссылку:

Castle.MicroKernel.CircularDependencyException: Dependency cycle has been detected when trying to resolve component 'CircularIoC.Thing1'.
The resolution tree that resulted in the cycle is the following:
Component 'CircularIoC.Thing1' resolved as dependency of
    component 'CircularIoC.Thing2' resolved as dependency of
    component 'CircularIoC.Thing1' which is the root component being resolved.

Unity

Если Unity настроен так, чтобы разрешать эти типы

    private static void ResolveWithUnity()
    {
        var container = new UnityContainer();

        container.RegisterType<IThing1, Thing1>();
        container.RegisterType<IThing2, Thing2>();

        var thing = container.Resolve<IThing1>();

        container.Dispose();
    }

Вызов container.Resolve < > приведет к исключению StackOverflowException.

Это документированное поведение, но было бы неплохо иметь более полезную информацию. Есть ли какая-либо настройка, которая предоставит больше информации о круговой ссылке?

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

Хотя я знаю, что переход на другой IoC решит проблему, это, к сожалению, не вариант.

4b9b3361

Ответ 1

Unity грустно не поддерживает эту (невероятно важную) особенность. Если вы готовы вставить обратно в нее, вы можете реализовать умный декоратор, используя некоторую консистентную смазку.

Вам понадобится переопределить все методы регистрации и построить и обновить структуру данных для зависимостей (график зависимостей). Затем напишите метод, который заставляет DFS обнаруживать циклическую зависимость, вы можете либо использовать его в качестве финализатора для процесса регистрации, разрешая, если возможны круговые зависимости, или используйте его для разрешения для запрашиваемого конкретного типа.

Как вы можете видеть, это много работы...

Другой вариант - просто обернуть с помощью декоратора методы устранения и уловить исключение StackOverflowException, проанализировать его, чтобы убедиться, что это было результатом процесса разрешения, и создать правильное исключение циклической зависимости.