Search code examples
c#.net-coredependency-injectionautofacioc-container

Autofac WhenInjectInto like Grace/Ninject


i have this implementation with Grace (it's the same in Ninject) but i need use then in Autofac but autofac does not have a "WhenInjectInto" functionality. How can i migrate this code? Thx

public interface ILocationRepository
{
    Task<Location?> GetByIDAsync(int id);
}

public class LocationRepositoryProxyCache : BaseProxyCache, ILocationRepository
{
    private readonly ICacheProvider<Location> _cacheProvider;

    private readonly ILocationRepository _locationRepository;

    public LocationRepositoryProxyCache(ICacheProvider<Location> cacheProvider, ILocationRepository locationRepository)
    {
        _cacheProvider = cacheProvider;
        _locationRepository = locationRepository;
    }
    public Task<Location?> GetByIDAsync(int id)
    {
        return _cacheProvider.GetOrSetAsync("CACHE_KEY", () => _locationRepository.GetByIDAsync(id));
    }
}

public class LocationRepository : BaseRepository<Location>, ILocationRepository
{
    public LocationRepository(IMyInterface myAppDb) : base(myAppDb) { }

    public Task<Location?> GetByIDAsync(int id)
    {
        return ...;
    }
}

Grace code to migrate to Autofac

registrationBlock.Export<LocationRepository>().As<ILocationRepository>().When.InjectedInto<LocationRepositoryProxyCache>();
registrationBlock.Export<LocationRepositoryProxyCache>().As<ILocationRepository>();

Solution

  • Based on here , I made the sample code to register the Service by Keyed

            builder.RegisterType<LocationRepository>().Keyed<ILocationRepository>(SourceType.Fetching);
            builder.RegisterType<LocationRepositoryProxyCache>().Keyed<ILocationRepository>(SourceType.Caching);
             
            builder.RegisterType<Consumer>().As<IConsumer>().WithAttributeFiltering();
    

    Here is the LocationRepository and LocationRepositoryProxyCache

    public class Consumer : IConsumer
    {
        private ILocationRepository cacheRepo;
        private ILocationRepository fetchRepo;
        public Consumer([KeyFilter(SourceType.Fetching)] ILocationRepository fetchService ,
            [KeyFilter(SourceType.Caching)] ILocationRepository cacheService)
        {
            cacheRepo = cacheService;
            fetchRepo = fetchService;
        }
    
        public void Test()
        {
            cacheRepo.GetByIDAsync(1);
            fetchRepo.GetByIDAsync(2);
        }
    }
    public interface IConsumer {
        void Test();
    }
    

    I hope, it can help you.