Как добавить зависимость, которую можно использовать в качестве параметра типа TImpl для Castle Windsor?

Я получил это исключение во время выполнения с определенным URL:

" Отсутствует зависимость. Компонент NRBQ.Web.Controllers.DeliveryController имеет зависимость от SeaStore.Data.Legacy.Interfaces.INRBQDeliveryRepository, которая не может быть разрешена. Убедитесь, что зависимость правильно зарегистрирована в контейнере как служба или предоставлена ​​как встроенная аргумент ". ExceptionType: "Castle.MicroKernel.Resolvers.DependencyResolverException "

... поэтому я добавил этот код (на основе существующего кода, который работает) в класс IOC:

_container.Register
     (Component
    .For<INRBQDeliveryRepository>()
    .ImplementedBy<DeliveryController>()
    .LifeStyle.Transient);

В каком-то контексте:

private static Castle.Windsor.IWindsorContainer _container;

_container = new Castle.Windsor.WindsorContainer();
_container.AddFacility<Castle.Facilities.FactorySupport.FactorySupportFacility>();

. . .

_container.Register
  (Component
  .For<INRBQDeliveryRepository>()
  .ImplementedBy<DeliveryController>()
  .LifeStyle.Transient);

... но это даже не скомпилируется; Теперь я получаю:

Тип 'NRBQ.API.Controllers.DeliveryController' нельзя использовать в качестве параметра типа 'TImpl' в универсальном типе или методе 'Castle.MicroKernel.Registration.ComponentRegistration.ImplementedBy()'. Не существует неявного преобразования ссылок из NRBQ.API.Controllers.DeliveryController в SeaStore.Data.Legacy.Interfaces.INRBQDeliveryRepository.

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

ОБНОВИТЬ

В ответ на то, реализует ли DeliveryController INRBQDeliveryRepository: на самом деле, есть три вещи типа контроллера; пользовательский в NRBQ.Web:

public class DeliveryController : ApiController
{
    private readonly INRBQDeliveryRepository _deliveryRepository;

    public DeliveryController(INRBQDeliveryRepository deliveryRepository)
    {
        if (deliveryRepository == null)
        {
            throw new ArgumentNullException("DeliveriesController");
        }
        _deliveryRepository = deliveryRepository;
    }

    [Route("api/Deliveries/Count")] 
    public int GetCountOfDeliveryRecords()
    {
        return _deliveryRepository.GetCount();
    }
    . . .

... затем средний в NRBQ. Клиент:

namespace NRBQ.Client
{
    public class RESTNRBQDelivery : INRBQDelivery
    {
        INRBQClientSettings NRBQClientSettings;
        IRESTAPIClient RESTAPIClient;

        public RESTNRBQDelivery(IRESTAPIClient RESTAPIClient, INRBQClientSettings NRBQClientSettings)
        {
            this.NRBQClientSettings = NRBQClientSettings;
            this.RESTAPIClient = RESTAPIClient;
        }

        public RESTNRBQDelivery(IRESTAPIClient RESTAPIClient, INRBQClientSettings NRBQClientSettings, AuthenticationHeaderValue AuthHeader)
        {
            this.NRBQClientSettings = NRBQClientSettings;
            this.RESTAPIClient = RESTAPIClient;
            this.RESTAPIClient.AuthHeader = AuthHeader;
        }

        public int GetCount()
        {
            throw new NotImplementedException(); //TODO: Implement
        }

.... и, наконец, тот, который действительно делает тяжелую работу за кулисами, в NRBQ.API:

namespace NRBQ.API.Controllers
{
    public class DeliveryController : ApiController
    {
        ILogger Logger;
        INRBQService NRBQService;

        public DeliveryController(ILogger Logger, INRBQService NRBQService)
        {
            this.NRBQService = NRBQService;
            this.Logger = Logger;
        }

        [HttpGet]
        [Route("api/Deliveries/Count")] 
        public int GetCountOfDeliveryRecords()
        {
            //return _deliveryRepository.GetCount();
            return NRBQService.GetNRBQEntity();
        }

Последний звонок относится здесь:

public int GetNRBQEntity()
{
    return 17; // Bogus val for now
}

Это все моя лучшая попытка скопировать существующий тестовый / примерный код, но я признаю, что моя голова плавает, и я не очень понимаю, что происходит (как и почему).

ОБНОВЛЕНИЕ 2

Хотя я уверен, что это все еще не совсем хот-дог Натана (кажется, что он гонится за всем творением, вызывая сначала эту абстракцию, затем ту, потом другую, потом обратно к первому, потом другому, потом обратно ко второму и т. д. и т. д. до бесконечности и до тошноты (Advillium), добавив следующее:

container.Register
 (Component
 .For<INRBQDelivery>()
 .ImplementedBy<RESTNRBQDelivery>()
 .LifeStyle.Transient);

...в контексте:

public class NRBQClientInstaller : IWindsorInstaller
{
    public void Install(IWindsorContainer container, IConfigurationStore store)
    {
        container.Register
         (Component
         .For<SeaStore.Common.HTTP.IRESTAPIClient>()
         .ImplementedBy<SeaStore.Common.HTTP.WebAPIClient>()
         .LifeStyle.Transient);

        container.Register
         (Component
         .For<INRBQClient>()
         .ImplementedBy<RESTNRBQClient>()
         .LifeStyle.Transient);

        container.Register
         (Component
         .For<INRBQDelivery>()
         .ImplementedBy<RESTNRBQDelivery>()
         .LifeStyle.Transient);
    }
}

... избавился от сообщения об ошибке и вернул фальшивый результат, который я ожидал (или, скорее, надеялся, что не ожидал).

1 ответ

Решение

В вашем модуле IWindsorInstaller зарегистрируйте интерфейс и его реализатор:

container.Register
 (Component
 .For<INRBQDelivery>()
 .ImplementedBy<RESTNRBQDelivery>()
 .LifeStyle.Transient);