Новое в StructureMap - Ошибка получения экземпляра по умолчанию 202 - PullRequest
0 голосов
/ 20 мая 2010

Я очень новичок в StructureMap и получаю следующую ошибку:

Код исключения StructureMap: 202 Нет Экземпляр по умолчанию, определенный для PluginFamily Company.ProjectCore.Core.IUserSession, Company.ProjectCore, версия = 1.0.0.0, Культура = нейтральная, PublicKeyToken = ноль

Кажется, что это первый экземпляр интерфейса при компиляции а затем выдает ошибку выше:

private readonly IUserSession _userSession;

public SiteMaster()
{
  _userSession = ObjectFactory.GetInstance<IUserSession>(); // ERROR THROWN HERE
  ...
}

Для чего это стоит, у меня есть ссылка на PluginFamily над всеми интерфейсами:

[PluginFamily("Default")]
public interface IUserSession

Ниже весь мой StructureMap.config

<StructureMap>
  <Assembly Name="Company.ProjectWeb" />
  <Assembly Name="Company.ProjectCore" />
  <!--
  Use DefaultKey="Default" for standard cache 
  or DefaultKey="MemCached" for memcached cache.
  -->
  <PluginFamily
      Assembly="Company.ProjectCore"
      Type="Company.ProjectCore.Core.ICache"
      DefaultKey="MemCached" />
  <!--
  Use DefaultKey="Default" for sending the email
  in real time through the configured mail server 
  or use DefaultKey="MailQueue" to send the mail
  in batches through another process
  -->
  <PluginFamily
      Assembly="Company.ProjectCore"
      Type="Company.ProjectCore.Core.IEmailService"
      DefaultKey="MailQueue" />
  <!--
  Use DefaultKey="Default" for standard cache 
  or DefaultKey="UserSession" for memcached cache.
  -->
  <PluginFamily
      Assembly="Company.ProjectCore"
      Type="Company.ProjectCore.Core.IUserSession"
      DefaultKey="UserSession" />
  <!--
  Use DefaultKey="Default" for standard cache 
  or DefaultKey="Redirector" for memcached cache.
  -->
  <PluginFamily
      Assembly="Company.ProjectCore"
      Type="Company.ProjectCore.Core.IRedirector"
      DefaultKey="Redirector" />
  <!--
  Use DefaultKey="Default" for standard cache 
  or DefaultKey="Navigation" for memcached cache.
  -->
  <PluginFamily
      Assembly="Company.ProjectCore"
      Type="Company.ProjectCore.Core.INavigation"
      DefaultKey="Navigation" />

Есть предложения? Благодаря.

Ответы [ 2 ]

2 голосов
/ 20 мая 2010

Конфиг мне кажется правильным на первый взгляд. Вы вызываете ObjectFactory.Initialize до запуска кода, который вы опубликовали?

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

Кроме того, есть ли причина, по которой вы хотите использовать атрибуты и / или XML в первую очередь? Вы можете сконфигурировать свои экземпляры с помощью кода с помощью StructureMap через свободный интерфейс, и IMHO, это лучший способ сделать это (если вам не нужно поменять местами реализации, но даже тогда есть другие варианты).

Смотрите также: http://structuremap.github.com/structuremap/ConfiguringStructureMap.htm

Обновление после комментариев

Хорошо, я загрузил приложение, но не могу его запустить и не могу найти время для устранения неполадок. Прошу прощения, если не могу больше помочь.

Однако я очень кратко изучил код, и могу сказать вам окончательно, что часть кода, который я видел для использования IOC / DI, очень мешает. Если только это не начальный код, который книга покажет вам, как выполнить рефакторинг, я бы не рекомендовал это в качестве источника для изучения шаблона IOC или StructureMap.

Вот пример плохого кода:

public AccountService()
{
    _accountRepository = ObjectFactory.GetInstance<IAccountRepository>();
    _permissionRepository = ObjectFactory.GetInstance<IPermissionRepository>();
    _userSession = ObjectFactory.GetInstance<IUserSession>();
    _redirector = ObjectFactory.GetInstance<IRedirector>();
    _email = ObjectFactory.GetInstance<IEmail>();
    _profileService = ObjectFactory.GetInstance<IProfileService>();
    _webContext = ObjectFactory.GetInstance<IWebContext>();
    _friendService = ObjectFactory.GetInstance<IFriendService>();
}

Для меня это явный анти-паттерн Global Service Locator. Даже если это исключить, оно нарушает один из основных принципов МОК, а именно то, что зависимости должны быть явными.

Ваше приложение должно иметь несколько (или даже один, если возможно) вызов ObjectFactory.GetInstance (), и с этого момента все зависимости должны обрабатываться через каркас в качестве аргументов конструктора.

Таким образом, конструктор для Account Service будет выглядеть примерно так:

public AccountService(IAccountRepository accountRepository) 
    {
        //all arguments (not just account repo) would be passed into the ctor
        //you also want to check for null for all arguments
        _accountRepository = accountRepository;
    }

(также обратите внимание, что 8 аргументов, похоже, знак того, что у этого класса слишком много обязанностей)

Это действительно слишком много, чтобы разобраться в одном посте, но я бы порекомендовал найти лучший источник для изучения шаблона и инструмента.

0 голосов
/ 20 мая 2010

Автор StructureMap не одобряет использование декларации XML. Почему бы не объявить это с помощью кода, например:

ObjectFactory.Initialize(x => 
    {
        x.For<ICache>().Use<MemCached>();
        x.For<IEmailService>().Use<MailQueue>();
        x.For<IUserSession>().Use<UserSession>();
        x.For<IRedirector>().Use<Redirector>();
        x.For<INavigation>().Use<Navigation>();
    });

Таким образом, вам не придется угадывать, правильно ли все устроено. Это также намного проще в обслуживании и меньше кода.

...