Introduction
ASP.NET Core's built-in DI container handles basic registrations well, but manually registering dozens of services is tedious and error-prone. Scrutor adds assembly scanning to auto-register services by convention and a Decorate method to wrap existing registrations with cross-cutting behavior like caching, logging, or retry logic.
What Scrutor Does
- Scans assemblies to auto-discover and register services matching conventions
- Registers classes by their implemented interfaces, base types, or custom selectors
- Applies the decorator pattern to existing DI registrations without changing consuming code
- Supports filtering by namespace, attribute, or custom predicate
- Works with transient, scoped, and singleton lifetimes
Architecture Overview
Scrutor is a thin extension library over IServiceCollection. The scanning API builds a fluent pipeline: select assemblies, filter classes, choose registration strategy (as interface, as self, as matching interface), and set lifetime. Under the hood, it reflects over types once and calls the standard IServiceCollection.Add() methods. The Decorate<TInterface, TDecorator>() method replaces an existing registration by wrapping the original factory, so the container resolves the decorator with the original service injected.
Self-Hosting & Configuration
- Install via NuGet:
dotnet add package Scrutor - Call
services.Scan()in your DI setup (Program.cs or Startup.cs) - No configuration files or external dependencies
- Works with the built-in Microsoft DI container (no Autofac or StructureMap needed)
- Chain multiple scan operations for different assemblies or conventions
Key Features
- Convention-based registration: match interfaces by name, namespace, or attribute
- Decorator support without replacing the DI container
- Duplicate handling strategies: Skip, Replace, or Append
- Assembly source selection from entry assembly, calling assembly, or explicit types
- Composable filter pipeline with
AddClasses(predicate)for precise control
Comparison with Similar Tools
- Autofac — full-featured DI container with scanning; Scrutor adds scanning to the built-in container
- Manual registration — explicit control but does not scale; Scrutor automates the pattern
- Lamar (StructureMap) — alternative container with conventions; Scrutor avoids replacing the container
- Castle Windsor — mature DI with interceptors; heavier than Scrutor's focused feature set
- Simple Injector — convention registration available but requires replacing the default container
FAQ
Q: Does Scrutor replace the built-in DI container?
A: No. Scrutor extends IServiceCollection with scanning and decoration. It works with the default Microsoft container.
Q: Can I decorate a service multiple times?
A: Yes. Each Decorate<TInterface, TDecorator>() call wraps the previous registration, creating a chain of decorators.
Q: How do I exclude certain classes from scanning?
A: Use the AddClasses(c => c.Where(t => !t.Name.EndsWith("Helper"))) predicate to filter unwanted types.
Q: Does Scrutor support keyed or named services? A: Scrutor works with the standard DI abstractions. For keyed services in .NET 8+, combine Scrutor scanning with the built-in keyed service registration.