This is supposed to be a quick checklist / cheatsheet to help debug DI failures.
These are easy issues that happened to me.
Having a quick check, sometimes, this is the most efficent way to catch a bug:
- Registered an interface, but try to inject a service; or vise versa.
- Forget to / missed register any dependency.
- Try to instantiate an abstraction class.
If that didn't help, examine the callstack? On top of the callstack, there usually shows the complains about what class/interface is missing from the DI container. For example:
Unhandled exception. System.ArgumentException: Cannot instantiate implementation type 'NetStackBeautifier.Services.BeautifierService' for service type 'NetStackBeautifier.Services.IBeautifierService'.
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.Populate()
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory..ctor(ICollection`1 descriptors)
at Microsoft.Extensions.DependencyInjection.ServiceProvider..ctor(ICollection`1 serviceDescriptors, ServiceProviderOptions options)
at Microsoft.Extensions.DependencyInjection.ServiceCollectionContainerBuilderExtensions.BuildServiceProvider(IServiceCollection services, ServiceProviderOptions options)
at Microsoft.Extensions.DependencyInjection.DefaultServiceProviderFactory.CreateServiceProvider(IServiceCollection containerBuilder)
at Microsoft.Extensions.Hosting.Internal.ServiceFactoryAdapter`1.CreateServiceProvider(Object containerBuilder)
at Microsoft.Extensions.Hosting.HostBuilder.CreateServiceProvider()
at Microsoft.Extensions.Hosting.HostBuilder.Build()
at Microsoft.AspNetCore.Builder.WebApplicationBuilder.Build()
at Program.<Main>$(String[] args) in D:\Repos\NetStackBeautifier\NetStackBeautifier.WebAPI\Program.cs:line 14The information that was given:
- It is trying to get an instance of
IBeautifierService; - The type the DI container trying to construct is:
BeautifierService;
Based on that, we want to understand why BeautifierService can't be constructed. The case I encountered - BeautifierService happen to be an abstract class and of course it couldn't be instantionated.
Another common calls stack looks like this:
Unhandled exception. System.AggregateException: Some services are not able to be constructed (Error while validating the service descriptor 'ServiceType: NetStackBeautifier.Services.IBeautifier Lifetime: Scoped ImplementationType: NetStackBeautifier.Services.SimpleExceptionStackBeautifier': Unable to resolve service for type 'NetStackBeautifier.Core.FrameClassNameFactory' while attempting to activate 'NetStackBeautifier.Services.SimpleExceptionStackBeautifier'.) (Error while validating the service descriptor 'ServiceType: NetStackBeautifier.Services.IBeautifierService Lifetime: Scoped ImplementationType: NetStackBeautifier.Services.BeautifierService': Unable to resolve service for type 'NetStackBeautifier.Core.FrameClassNameFactory' while attempting to activate 'NetStackBeautifier.Services.SimpleExceptionStackBeautifier'.)
---> System.InvalidOperationException: Error while validating the service descriptor 'ServiceType: NetStackBeautifier.Services.IBeautifier Lifetime: Scoped ImplementationType: NetStackBeautifier.Services.SimpleExceptionStackBeautifier': Unable to resolve service for type 'NetStackBeautifier.Core.FrameClassNameFactory' while attempting to activate 'NetStackBeautifier.Services.SimpleExceptionStackBeautifier'.
---> System.InvalidOperationException: Unable to resolve service for type 'NetStackBeautifier.Core.FrameClassNameFactory' while attempting to activate 'NetStackBeautifier.Services.SimpleExceptionStackBeautifier'.
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.CreateArgumentCallSites(Type implementationType, CallSiteChain callSiteChain, ParameterInfo[] parameters, Boolean throwIfCallSiteNotFound)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.CreateConstructorCallSite(ResultCache lifetime, Type serviceType, Type implementationType, CallSiteChain callSiteChain)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.TryCreateExact(ServiceDescriptor descriptor, Type serviceType, CallSiteChain callSiteChain, Int32 slot)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.GetCallSite(ServiceDescriptor serviceDescriptor, CallSiteChain callSiteChain)
at Microsoft.Extensions.DependencyInjection.ServiceProvider.ValidateService(ServiceDescriptor descriptor)
--- End of inner exception stack trace ---
at Microsoft.Extensions.DependencyInjection.ServiceProvider.ValidateService(ServiceDescriptor descriptor)
at Microsoft.Extensions.DependencyInjection.ServiceProvider..ctor(ICollection`1 serviceDescriptors, ServiceProviderOptions options)
--- End of inner exception stack trace ---
at Microsoft.Extensions.DependencyInjection.ServiceProvider..ctor(ICollection`1 serviceDescriptors, ServiceProviderOptions options)
at Microsoft.Extensions.DependencyInjection.ServiceCollectionContainerBuilderExtensions.BuildServiceProvider(IServiceCollection services, ServiceProviderOptions options)
at Microsoft.Extensions.DependencyInjection.DefaultServiceProviderFactory.CreateServiceProvider(IServiceCollection containerBuilder)
at Microsoft.Extensions.Hosting.Internal.ServiceFactoryAdapter`1.CreateServiceProvider(Object containerBuilder)
at Microsoft.Extensions.Hosting.HostBuilder.CreateServiceProvider()
at Microsoft.Extensions.Hosting.HostBuilder.Build()
at Microsoft.AspNetCore.Builder.WebApplicationBuilder.Build()
at Program.<Main>$(String[] args) in D:\Repos\NetStackBeautifier\NetStackBeautifier.WebAPI\Program.cs:line 21
---> (Inner Exception #1) System.InvalidOperationException: Error while validating the service descriptor 'ServiceType: NetStackBeautifier.Services.IBeautifierService Lifetime: Scoped ImplementationType: NetStackBeautifier.Services.BeautifierService': Unable to resolve service for type 'NetStackBeautifier.Core.FrameClassNameFactory' while attempting to activate 'NetStackBeautifier.Services.SimpleExceptionStackBeautifier'.
---> System.InvalidOperationException: Unable to resolve service for type 'NetStackBeautifier.Core.FrameClassNameFactory' while attempting to activate 'NetStackBeautifier.Services.SimpleExceptionStackBeautifier'.
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.CreateArgumentCallSites(Type implementationType, CallSiteChain callSiteChain, ParameterInfo[] parameters, Boolean throwIfCallSiteNotFound)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.CreateConstructorCallSite(ResultCache lifetime, Type serviceType, Type implementationType, CallSiteChain callSiteChain)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.TryCreateExact(ServiceDescriptor descriptor, Type serviceType, CallSiteChain callSiteChain, Int32 slot)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.TryCreateEnumerable(Type serviceType, CallSiteChain callSiteChain)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.CreateCallSite(Type serviceType, CallSiteChain callSiteChain)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.GetCallSite(Type serviceType, CallSiteChain callSiteChain)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.CreateArgumentCallSites(Type implementationType, CallSiteChain callSiteChain, ParameterInfo[] parameters, Boolean throwIfCallSiteNotFound)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.CreateConstructorCallSite(ResultCache lifetime, Type serviceType, Type implementationType, CallSiteChain callSiteChain)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.TryCreateExact(ServiceDescriptor descriptor, Type serviceType, CallSiteChain callSiteChain, Int32 slot)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.GetCallSite(ServiceDescriptor serviceDescriptor, CallSiteChain callSiteChain)
at Microsoft.Extensions.DependencyInjection.ServiceProvider.ValidateService(ServiceDescriptor descriptor)
--- End of inner exception stack trace ---
at Microsoft.Extensions.DependencyInjection.ServiceProvider.ValidateService(ServiceDescriptor descriptor)
at Microsoft.Extensions.DependencyInjection.ServiceProvider..ctor(ICollection`1 serviceDescriptors, ServiceProviderOptions options)<---For that, well, the key information is:
Unable to resolve service for type 'NetStackBeautifier.Core.FrameClassNameFactory'
And that is a dependency of SimpleExceptionStackBeautifier, that was not registered.
If what showed in the callstack still doesn't make sense, we need to check carefully about what is actually registered. This will also be useful when there is no exception but the service injected is not expected.
One quick way is to output all the service descriptors
#if DEBUG
foreach(ServiceDescriptor descriptor in builder.Services)
{
Console.WriteLine("{0}:{1}", descriptor.ServiceType.Name, descriptor.ImplementationType?.Name);
}
#endifA good place for that to run is after finish registering all services.
If you suspect to have a Captive Dependency, turn on validate scope is going to help validate it.
- For ASP.NET Core Application, ValidateScopes is true in
Developmentenvironment. - You can turn it on in prod environment too:
WebHost.CreateDefaultBuilder(args)
.UseDefaultServiceProvider((context, options) => {
options.ValidateScopes = true;
})