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

Как зарегистрировать общий интерфейс с помощью TinyIOC

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

В частности, у меня есть следующее (уменьшенное для простоты):

public interface IRepository<T> where T : TableEntity
{
    T GetById(string partitionKey, string rowKey);
    void Insert(T entity);
    void Update(T entity);
    void Update(string partitionKey, string rowKey, Action<T> updateAction);
    void Delete(T entity);
    IQueryable<T> Table { get; }
}


public class AzureRepository<T> : IRepository<T> where T : TableEntity
{
    ...
}

Нужно ли регистрировать все реализации один за другим, например:

container.Register<IRepository<Entity1>, AzureRepository<Entity1>>();
container.Register<IRepository<Entity2>, AzureRepository<Entity2>>();
container.Register<IRepository<Entity3>, AzureRepository<Entity3>>();
...

Или есть более короткий путь?

4b9b3361

Ответ 1

Как уже упоминалось в моем комментарии, TinyIoC имеет ошибку в разрешении Open Generics - он не сохраняет разделенные экземпляры с разными параметрами типа отдельно, и поскольку все регистрации неявно выполняются с .AsSingleton() по умолчанию, это всегда возвращает первый экземпляр типового типа, который был разрешен для всех последующих запросов на разрешение.

В связи с этим следующее не работает:

container.Register(typeof(IRepository<>), typeof(AzureRepository<>));

Однако существует обходное решение - сделать переходный период регистрации:

container.Register(typeof(IRepository<>), typeof(AzureRepository<>)).AsMultiInstance();

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

Edit

Подтверждено. В разрешении Open Generics используется SingletonFactory, который после создания экземпляра всегда будет возвращать это для последующих разрешений. Он не знает и не заботится о Generics. Чтобы это работало правильно, потребовался бы GenericSingletonFactory, который не только сохранил бы один экземпляр, но и словарь с ключом конкретного типа, который будет разрешен.

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