مهارتهای تزریق وابستگیها در برنامههای NET Core. - قسمت هشتم - ساده سازی معرفی سرویسها توسط Scrutor
نویسنده: وحید نصیری
تاریخ: ۱۳۹۷/۱۰/۲۱ ۹:۲۵
آدرس: www.dntips.ir
| مطالب | ۳۶۹۴ |
| نویسندگان | ۲۷۶ |
| گروههای مطالب | ۱۰۲۴ |
| نقشههای راه | ۱۱۹ |
| دورهها | ۱۴ |
| اشتراکها | ۱۷۹۱۴ |
var container = new Container(x =>
{
x.Scan(scanner =>
{
scanner.AssemblyContainingType<IOrderHandler>();
// connects `IAccounting` to `Accounting` and `ISales` to `Sales` automatically.
scanner.WithDefaultConventions();
});
}); builder.RegisterAssemblyTypes(myAssembly) .Where(t => t.IsAssignableTo<IMyInterface>()) .AsImplementedInterfaces();
> Install-Package Scrutor > dotnet add package Scrutor
<Project Sdk="Microsoft.NET.Sdk.Web">
<ItemGroup>
<PackageReference Include="Scrutor" Version="3.0.2" />
</ItemGroup>
</Project> namespace CoreIocServices
{
public interface IFoo
{
void Run();
}
public class Foo : IFoo
{
public void Run()
{
throw new System.NotImplementedException();
}
}
public interface IBar
{
void Add();
}
public class Bar : IBar
{
public void Add()
{
throw new System.NotImplementedException();
}
}
public interface IBaz
{
void Stop();
}
public class Baz : IBaz
{
public void Stop()
{
throw new System.NotImplementedException();
}
}
} services.AddScoped<IFoo, Foo>(); services.AddScoped<IBar, Bar>(); services.AddScoped<IBaz, Baz>();
namespace CoreIocSample02
{
public class Startup
{
public void ConfigureServices(IServiceCollection services)
{
services.Scan(scan =>
//scan.FromCallingAssembly()
scan.FromAssemblyOf<IFoo>()
.AddClasses()
.AsMatchingInterface()
.WithScopedLifetime()); services.AddScoped<ITestService, TestService>(); services.AddScoped<IService, TestService>();
namespace CoreIocServices
{
public interface IService { }
public class Service1 : IService { }
public class Service2 : IService { }
public class Service : IService { }
} services.AddTransient<Service1>(); services.AddTransient<Service2>(); services.AddTransient<Service>();
namespace CoreIocSample02
{
public class Startup
{
public void ConfigureServices(IServiceCollection services)
{
services.Scan(scan =>
//scan.FromCallingAssembly()
scan.FromAssemblyOf<IService>()
.AddClasses()
.AsSelf()
.WithTransientLifetime()); services.Scan(scan =>
scan.AddTypes(new[] { typeof(Service1), typeof(Service2) })
.AsSelf()
.WithTransientLifetime()); services.AddSingleton<TestService>(); services.AddSingleton<ITestService>(x => x.GetRequiredService<TestService>()); services.AddSingleton<IService>(x => x.GetRequiredService<TestService>());
services.Scan(scan =>
//scan.FromCallingAssembly()
scan.FromAssemblyOf<IService>() public interface IImplementationTypeSelector : IAssemblySelector, IFluentInterface
{
IServiceTypeSelector AddClasses();
IServiceTypeSelector AddClasses(bool publicOnly);
IServiceTypeSelector AddClasses(Action<IImplementationTypeFilter> action);
IServiceTypeSelector AddClasses(Action<IImplementationTypeFilter> action, bool publicOnly);
} services.Scan(scan => scan
.FromAssemblyOf<IService>()
.AddClasses(classes => classes.AssignableTo<IService>())
// .AddClasses(classes => classes.InNamespaces("MyApp"))
// .AddClasses(classes => classes.Where(type => type.Name.EndsWith("Repository"))
.AsImplementedInterfaces()
.WithTransientLifetime()); services.AddTransient<ITransientService, TransientService>(); services.AddScoped<IScopedService, ScopedService>();
public class TransientService : IFooService {}
public class AnotherService : IScopedService {} services.Scan(scan =>
scan.FromAssemblyOf<IFoo>()
.AddClasses()
.UsingRegistrationStrategy(RegistrationStrategy.Skip)
.AsMatchingInterface()
.WithScopedLifetime()); namespace Scrutor
{
public abstract class RegistrationStrategy
{
public static readonly RegistrationStrategy Skip;
public static readonly RegistrationStrategy Append;
protected RegistrationStrategy();
public static RegistrationStrategy Replace();
public static RegistrationStrategy Replace(ReplacementBehavior behavior);
public abstract void Apply(IServiceCollection services, ServiceDescriptor descriptor);
}
} namespace Scrutor
{
[Flags]
public enum ReplacementBehavior
{
Default = 0,
ServiceType = 1,
ImplementationType = 2,
All = 3
}
} services.Scan(scan => scan
.FromAssemblyOf<CombinedService>()
.AddClasses(classes => classes.AssignableTo<ICombinedService>()) // Filter classes
.AsSelfWithInterfaces()
.WithSingletonLifetime()
.AddClasses(x=> x.AssignableTo(typeof(IOpenGeneric<>))) // Can close generic types
.AsMatchingInterface()
.AddClasses(x=> x.InNamespaceOf<MyClass>())
.UsingRegistrationStrategy(RegistrationStrategy.Replace()) // Defaults to ReplacementBehavior.ServiceType
.AsMatchingInterface()
.WithScopedLifetime()
.FromAssemblyOf<DatabaseContext>() // Can load from multiple assemblies within one Scan()
.AddClasses()
.AsImplementedInterfaces()
); .AddClasses(classes => classes.InNamespaces("SingletonServices")) public interface ITransientDependency
{
}
public interface IScopedDependency
{
}
public interface ISingletonDependency
{
} services.Scan(scan => scan
.FromAssemblyOf<IApplicationAssembly>()
.AddClasses(classes => classes.AssignableTo<ISingletonDependency>())
.AsMatchingInterface()
.WithSingletonLifetime()
.AddClasses(classes => classes.AssignableTo<IScopedDependency>())
.AsMatchingInterface()
.WithScopedLifetime()
.AddClasses(classes => classes.AssignableTo<ITransientDependency>())
.AsMatchingInterface()
.WithTransientLifetime()
.AddClasses(classes => classes.AssignableTo(typeof(IDomainEventHandler<>)))
.AsImplementedInterfaces()
.WithTransientLifetime());