You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
96 lines
3.3 KiB
C#
96 lines
3.3 KiB
C#
using DS.Module.Core.Extensions;
|
|
using DS.Module.Core.Reflection;
|
|
using Microsoft.Extensions.DependencyInjection;
|
|
using Microsoft.Extensions.DependencyInjection.Extensions;
|
|
using System.Linq.Expressions;
|
|
|
|
namespace DS.Module.Core.Modules;
|
|
|
|
public class ModuleApplicationBase : IModuleApplication
|
|
{
|
|
public Type StartupModuleType { get; set; }
|
|
|
|
public IServiceCollection Services { get; set; }
|
|
|
|
public IServiceProvider ServiceProvider { get; set; }
|
|
|
|
/// <summary>
|
|
/// 模块接口容器
|
|
/// </summary>
|
|
public IReadOnlyList<IDSAppModule> Modules { get; set; }
|
|
|
|
public List<IDSAppModule> Source { get; protected set; }
|
|
|
|
public ModuleApplicationBase(Type startupModuleType, IServiceCollection services)
|
|
{
|
|
StartupModuleType = startupModuleType;
|
|
Services = services;
|
|
services.TryAddSingleton<IAssemblyFinder, AssemblyFinder>();
|
|
services.TryAddSingleton<ITypeFinder, TypeFinder>();
|
|
services.AddSingleton<IModuleApplication>(this);
|
|
services.TryAddObjectAccessor<IServiceProvider>();
|
|
Source = this.GetAllModule(services);
|
|
Modules = this.LoadModules();
|
|
}
|
|
|
|
protected virtual List<IDSAppModule> GetAllModule(IServiceCollection services)
|
|
{
|
|
var typeFinder = services.GetOrAddSingletonService<ITypeFinder, TypeFinder>();
|
|
var typs = typeFinder.Find(o => DSAppModule.IsAppModule(o));
|
|
var modules = typs.Select(o => CreateModule(services, o)).Distinct();
|
|
return modules.ToList();
|
|
}
|
|
|
|
protected virtual void SetServiceProvider(IServiceProvider serviceProvider)
|
|
{
|
|
ServiceProvider = serviceProvider;
|
|
ServiceProvider.GetRequiredService<ObjectAccessor<IServiceProvider>>().Value = ServiceProvider;
|
|
}
|
|
|
|
/// <summary>
|
|
/// 获取所有需要加载的模块
|
|
/// </summary>
|
|
/// <returns></returns>
|
|
protected virtual IReadOnlyList<IDSAppModule> LoadModules()
|
|
{
|
|
List<IDSAppModule> modules = new List<IDSAppModule>();
|
|
|
|
var module = Source.FirstOrDefault(o => o.GetType() == StartupModuleType);
|
|
//if (module == null)
|
|
//{
|
|
// throw new Exception($"类型为“{StartupModuleType.FullName}”的模块实例无法找到");
|
|
//}
|
|
Console.WriteLine("当前启动模块:", module);
|
|
modules.Add(module);
|
|
var dependeds = module.GetDependedTypes();
|
|
foreach (var dependType in dependeds.Where(o => DSAppModule.IsAppModule(o)))
|
|
{
|
|
var dependModule = Source.ToList().Find(m => m.GetType() == dependType);
|
|
if (dependModule == null)
|
|
{
|
|
throw new Exception($"加载模块{module.GetType().FullName}时无法找到依赖模块{dependType.FullName}");
|
|
}
|
|
|
|
modules.AddIfNotContains(dependModule);
|
|
}
|
|
|
|
return modules;
|
|
}
|
|
|
|
/// <summary>
|
|
/// 创建模块
|
|
/// </summary>
|
|
/// <param name="services"></param>
|
|
/// <param name="moduleType"></param>
|
|
/// <returns></returns>
|
|
private IDSAppModule CreateModule(IServiceCollection services, Type moduleType)
|
|
{
|
|
var module = (IDSAppModule)Expression.Lambda(Expression.New(moduleType)).Compile().DynamicInvoke();
|
|
services.AddSingleton(moduleType, module);
|
|
return module;
|
|
}
|
|
|
|
public virtual void Dispose()
|
|
{
|
|
}
|
|
} |