mirror of
https://github.com/AlexMacocian/Slim.git
synced 2026-07-15 15:19:59 +00:00
Slim Integration with Microsoft.Extensions.DependencyInjection (#20)
* Setup integration with Microsoft.Extensions.DependencyInjection * Setup Slim integration project with Microsoft.Extensions.DependencyInjection
This commit is contained in:
@@ -0,0 +1,85 @@
|
||||
using System;
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
|
||||
namespace Slim.Integration.ServiceCollection;
|
||||
public static class ServiceCollectionExtensions
|
||||
{
|
||||
public static System.IServiceProvider BuildSlimServiceProvider(this Microsoft.Extensions.DependencyInjection.ServiceCollection serviceCollection)
|
||||
{
|
||||
var serviceManager = new ServiceManager();
|
||||
foreach(var serviceDescriptor in serviceCollection)
|
||||
{
|
||||
switch (serviceDescriptor.Lifetime)
|
||||
{
|
||||
case ServiceLifetime.Singleton:
|
||||
RegisterSingleton(serviceManager, serviceDescriptor);
|
||||
break;
|
||||
case ServiceLifetime.Scoped:
|
||||
RegisterScoped(serviceManager, serviceDescriptor);
|
||||
break;
|
||||
case ServiceLifetime.Transient:
|
||||
RegisterTransient(serviceManager, serviceDescriptor);
|
||||
break;
|
||||
default:
|
||||
throw new InvalidOperationException($"Unexpected service lifetime {serviceDescriptor.Lifetime}.");
|
||||
}
|
||||
}
|
||||
|
||||
serviceManager.RegisterScoped<IServiceScopeFactory, ServiceScopeFactory>();
|
||||
return serviceManager;
|
||||
}
|
||||
|
||||
private static void RegisterSingleton(ServiceManager serviceManager, ServiceDescriptor serviceDescriptor)
|
||||
{
|
||||
if (serviceDescriptor.ImplementationInstance is null &&
|
||||
serviceDescriptor.ImplementationFactory is not null)
|
||||
{
|
||||
serviceManager.RegisterSingleton(serviceDescriptor.ServiceType, sp => serviceDescriptor.ImplementationFactory(sp));
|
||||
}
|
||||
else if (serviceDescriptor.ImplementationFactory is null &&
|
||||
serviceDescriptor.ImplementationInstance is not null)
|
||||
{
|
||||
serviceManager.RegisterSingleton(serviceDescriptor.ServiceType, sp => serviceDescriptor.ImplementationInstance);
|
||||
}
|
||||
else
|
||||
{
|
||||
serviceManager.RegisterSingleton(serviceDescriptor.ServiceType, serviceDescriptor.ImplementationType);
|
||||
}
|
||||
}
|
||||
|
||||
private static void RegisterScoped(ServiceManager serviceManager, ServiceDescriptor serviceDescriptor)
|
||||
{
|
||||
if (serviceDescriptor.ImplementationInstance is null &&
|
||||
serviceDescriptor.ImplementationFactory is not null)
|
||||
{
|
||||
serviceManager.RegisterScoped(serviceDescriptor.ServiceType, sp => serviceDescriptor.ImplementationFactory(sp));
|
||||
}
|
||||
else if (serviceDescriptor.ImplementationFactory is null &&
|
||||
serviceDescriptor.ImplementationInstance is not null)
|
||||
{
|
||||
serviceManager.RegisterScoped(serviceDescriptor.ServiceType, sp => serviceDescriptor.ImplementationInstance);
|
||||
}
|
||||
else
|
||||
{
|
||||
serviceManager.RegisterScoped(serviceDescriptor.ServiceType, serviceDescriptor.ImplementationType);
|
||||
}
|
||||
}
|
||||
|
||||
private static void RegisterTransient(ServiceManager serviceManager, ServiceDescriptor serviceDescriptor)
|
||||
{
|
||||
if (serviceDescriptor.ImplementationInstance is null &&
|
||||
serviceDescriptor.ImplementationFactory is not null)
|
||||
{
|
||||
serviceManager.RegisterTransient(serviceDescriptor.ServiceType, sp => serviceDescriptor.ImplementationFactory(sp));
|
||||
}
|
||||
else if (serviceDescriptor.ImplementationFactory is null &&
|
||||
serviceDescriptor.ImplementationInstance is not null)
|
||||
{
|
||||
serviceManager.RegisterTransient(serviceDescriptor.ServiceType, sp => serviceDescriptor.ImplementationInstance);
|
||||
}
|
||||
else
|
||||
{
|
||||
serviceManager.RegisterTransient(serviceDescriptor.ServiceType, serviceDescriptor.ImplementationType);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
using System;
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
|
||||
namespace Slim.Integration.ServiceCollection;
|
||||
|
||||
public sealed class ServiceScope : IServiceScope
|
||||
{
|
||||
public System.IServiceProvider ServiceProvider { get; set; }
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
if (this.ServiceProvider is IDisposable disposable)
|
||||
{
|
||||
disposable.Dispose();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
|
||||
namespace Slim.Integration.ServiceCollection;
|
||||
|
||||
public sealed class ServiceScopeFactory : IServiceScopeFactory
|
||||
{
|
||||
private readonly IServiceManager serviceManager;
|
||||
|
||||
public ServiceScopeFactory(
|
||||
IServiceManager serviceManager)
|
||||
{
|
||||
this.serviceManager = serviceManager;
|
||||
}
|
||||
|
||||
public IServiceScope CreateScope()
|
||||
{
|
||||
IServiceProvider scopedServiceManager = this.serviceManager.CreateScope();
|
||||
return new ServiceScope { ServiceProvider = scopedServiceManager };
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,76 @@
|
||||
using System;
|
||||
using System.ComponentModel.Design;
|
||||
|
||||
namespace Slim.Integration.ServiceContainer;
|
||||
|
||||
public class SlimServiceContainer : IServiceContainer
|
||||
{
|
||||
private readonly IServiceManager serviceManager;
|
||||
|
||||
public SlimServiceContainer()
|
||||
{
|
||||
this.serviceManager = new ServiceManager();
|
||||
}
|
||||
|
||||
public SlimServiceContainer(IServiceManager serviceManager)
|
||||
{
|
||||
this.serviceManager = serviceManager;
|
||||
}
|
||||
|
||||
public void AddService(Type serviceType, ServiceCreatorCallback callback)
|
||||
{
|
||||
this.serviceManager.RegisterSingleton(serviceType, sp => callback(this, serviceType));
|
||||
}
|
||||
|
||||
public void AddService(Type serviceType, ServiceCreatorCallback callback, bool promote)
|
||||
{
|
||||
var manager = this.serviceManager;
|
||||
if (promote is false)
|
||||
{
|
||||
this.AddService(serviceType, callback);
|
||||
return;
|
||||
}
|
||||
|
||||
while (manager is not null)
|
||||
{
|
||||
manager.RegisterSingleton(serviceType, sp => callback(this, serviceType));
|
||||
manager = manager.ParentServiceManager;
|
||||
}
|
||||
}
|
||||
|
||||
public void AddService(Type serviceType, object serviceInstance)
|
||||
{
|
||||
this.serviceManager.RegisterSingleton(serviceType, sp => serviceInstance);
|
||||
}
|
||||
|
||||
public void AddService(Type serviceType, object serviceInstance, bool promote)
|
||||
{
|
||||
var manager = this.serviceManager;
|
||||
if (promote is false)
|
||||
{
|
||||
this.AddService(serviceType, serviceInstance);
|
||||
return;
|
||||
}
|
||||
|
||||
while (manager is not null)
|
||||
{
|
||||
manager.RegisterSingleton(serviceType, sp => serviceInstance);
|
||||
manager = manager.ParentServiceManager;
|
||||
}
|
||||
}
|
||||
|
||||
public object GetService(Type serviceType)
|
||||
{
|
||||
return this.serviceManager.GetService(serviceType);
|
||||
}
|
||||
|
||||
public void RemoveService(Type serviceType)
|
||||
{
|
||||
throw new NotSupportedException("Removing one service is not currently supported");
|
||||
}
|
||||
|
||||
public void RemoveService(Type serviceType, bool promote)
|
||||
{
|
||||
throw new NotSupportedException("Removing one service is not currently supported");
|
||||
}
|
||||
}
|
||||
@@ -19,7 +19,15 @@
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.DependencyInjection.Abstractions" Version="6.0.0" />
|
||||
<PackageReference Include="Slim" Version="1.8.1" />
|
||||
<PackageReference Include="Slim" Version="1.9.1" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<None Include="..\LICENSE">
|
||||
<Pack>True</Pack>
|
||||
<PackagePath></PackagePath>
|
||||
</None>
|
||||
<None Include="..\README.md" Link="README.md" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
||||
Reference in New Issue
Block a user