ViewModelLocator с дочерними контейнерами IOC?

Как реализовать шаблон ViewModelLocator при использовании дочерних контейнеров IOC? Типичная реализация локатора выглядит примерно так:

public IViewModel ViewModel
{
   get { return Services.ServiceLocator.GetInstance<IViewModel>(); }
}

где Services.ServiceLocator - статическое свойство только для чтения. Но это ломается, если вы используете дочерние контейнеры. Вот мое определение для Services.ServiceLocator с использованием дочерних контейнеров:

public static IServiceLocator ServiceLocator
{
    get { return RootContext.ServiceLocator; }
}

Ясно, что это не правильно: мои введенные зависимости будут исходить из корневого контейнера, а не из дочернего контейнера. (Дочерний контейнер создан и загрузка привязана чем-то отличным от моего текущего представления. Таким образом, мое текущее представление может автоматически связываться с дочерним контейнером.)

Итак, как получить правильный контейнер в сценарии с несколькими контейнерами? Стандартный ответ заключается в том, чтобы конструктор внедрил его, но это не представляется возможным с ViewModelLocator: он требует конструктор по умолчанию, поэтому он может быть построен из XAML.

Я также ищу решение, которое работает как в Silverlight 4, так и в WPF 4.0, так как я работаю над составным приложением PRISM (таким образом, без расширений разметки). Я использую Unity в качестве контейнера IOC. Да, и решение должно работать в Blend (то есть оно не должно препятствовать созданию новой модели представления времени разработки, которая обходит контейнер IoC).

1 ответ

Обычно дочерний контейнер определяет иерархию поиска. Однако ваш базовый контейнер должен будет создать ваш дочерний контейнер - передавая себя в качестве параметра.

Чтобы получить доступ к дочернему контейнеру, у вас может быть свойство, которое возвращает дочерний контейнер - либо единичный экземпляр, либо временный (т. Е. Новый) экземпляр. Однако если вы хотите смешиваемости, вам следует помнить, что дочерний контейнер должен быть в ваших ресурсах для привязки к нему во время разработки.

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

Изменить: для вашего особого случая это может быть полезно. Хотя у меня не было времени, чтобы посмотреть видео, Лоран сказал мне, что он демонстрирует способ динамической загрузки модели представления. Я надеюсь, что это поможет вам!

Другие вопросы по тегам