My .Net 7 application has the following issue:
Autofac.Core.DependencyResolutionException: An exception was thrown while activating MyApp.Modules.MyModule.Application.MyModule.UpdateCommand.UpdateCommandHandler.
---> Autofac.Core.DependencyResolutionException: None of the constructors found with 'MyApp.Modules.MyModule.Infrastructure.Configuration.AllConstructorFinder' on type 'MyApp.Modules.MyModule.Application.MyModule.UpdateCommand.UpdateCommandHandler' can be invoked with the available services and parameters:
Cannot resolve parameter 'MyApp.Modules.MyModule.Application.Contracts.IMyModule myModule' of constructor 'Void .ctor(Serilog.ILogger, MyApp.Modules.MyModule.Application.Contracts.IMyModule)'.
UpdateCommandHandler.cs (where the issue is occurring)
public class UpdateCommandHandler: ICommandHandler<UpdateCommand>
{
private readonly IMyModule _myModule;
private readonly ILogger _logger;
public UpdateCommandHandler(ILogger logger, IMyModule myModule)
{
_myModule = myModule;
_logger = logger;
}
public async Task<Unit> Handle(UpdateCommand request, CancellationToken cancellationToken)
{
var foo = await _myModule.ExecuteQueryAsync(new SampleQuery());
return Unit.Value;
}
}
Program.cs
...
var builder = WebApplication.CreateBuilder(args);
builder.Host.UseServiceProviderFactory(new AutofacServiceProviderFactory());
builder.Host.ConfigureContainer<ContainerBuilder>(b => b.RegisterModule(new AutofacModules()));
...
I looked at similar issues before posting, such as this, but I do believe I appropriately registered IMyModule in Autofac as MyModule in the following.
AutofacModules.cs
public class AutofacModules: Autofac.Module
{
protected override void Load(ContainerBuilder builder)
{
builder.RegisterType<MyModule>().As<IMyModule>().InstancePerLifetimeScope();
}
}
IMyModule.cs
public interface IMyModule
{
Task ExecuteCommandAsync(ICommand command);
Task<TResult> ExecuteQueryAsync<TResult>(IQuery<TResult> query);
}
MyModule.cs
public class MyModule: IMyModule
{
public async Task ExecuteCommandAsync(ICommand command)
{
await CommandsExecutor.Execute(command);
}
public Task<TResult> ExecuteQueryAsync<TResult>(IQuery<TResult> query)
{
var scope = MyCompositionRoot.BeginLifetimeScope();
var mediator = scope.Resolve<IMediator>();
return mediator.Send(query);
}
}
AllConstructorFinder.cs
internal class AllConstructorFinder : IConstructorFinder
{
private static readonly ConcurrentDictionary<Type, ConstructorInfo[]> Cache = new();
public ConstructorInfo[] FindConstructors(Type targetType)
{
var result = Cache.GetOrAdd(targetType, t => t.GetTypeInfo().DeclaredConstructors.ToArray());
return result.Length > 0 ? result : throw new NoConstructorsFoundException(targetType);
}
}