using Mediator; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.DependencyInjection.Extensions; namespace Toolkit.Framework.Foundation; public static class IServiceCollectionExtensions { public static IServiceCollection AddHandler(this IServiceCollection services) where TRequestHandler : notnull { if (typeof(TRequestHandler).GetInterface(typeof(IRequestHandler<,>).Name) is { } contract) { if (contract.GetGenericArguments() is { Length: 2 } arguments) { Type requestType = arguments[0]; Type responseType = arguments[1]; Type wrapperType = typeof(RequestClassHandlerWrapper<,>).MakeGenericType(requestType, responseType); services.TryAdd(new ServiceDescriptor(typeof(TRequestHandler), typeof(TRequestHandler), ServiceLifetime.Transient)); services.Add(new ServiceDescriptor(wrapperType, sp => { return sp.GetService()?.Create(wrapperType, sp.GetRequiredService(), sp.GetServices(typeof(IPipelineBehavior<,>).MakeGenericType(requestType, responseType)))!; }, ServiceLifetime.Transient )); } } return services; } public static IServiceCollection AddFoundation(this IServiceCollection serviceCollection) { serviceCollection .AddSingleton() .AddHandler() .AddSingleton(provider => new ServiceFactory(provider.GetService, (instanceType, parameters) => ActivatorUtilities.CreateInstance(provider, instanceType, parameters!))) .AddHandler() .AddSingleton(provider => new Initialization(() => { return serviceCollection.Where(x => x.ServiceType.GetInterfaces() .Contains(typeof(IInitializable)) || x.ServiceType == typeof(IInitializable)) .GroupBy(x => x.ServiceType) .Select(x => x.First()) .SelectMany(x => provider.GetServices(x.ServiceType) .Select(x => (IInitializable?)x)).ToList(); })); return serviceCollection; } }