using Autofac; using Autofac.Core; using Autofac.Features.ResolveAnything; using MAX.Core; using MAX.Core.Autofac; using MAX.Core.DependencyInjection; using MAX.Core.Helpers; using MAX.Core.Infrastructure; using MAX.Core.Reflections; using MAX.Framework.Interfaces; using MAX.Framework.Prism.Autofac; using Prism.Ioc; using Prism.Ioc.Internals; using System; using System.Collections.Generic; using System.Diagnostics; using System.Linq; using System.Reflection; namespace Prism.Autofac { public class AutofacContainerExtension : IContainerExtension, IContainerInfo { private AutofacScopedProvider _currentScope; public readonly ContainerBuilder Builder; public IContainer Instance { get; private set; } public IScopedProvider CurrentScope => _currentScope; public AutofacContainerExtension() { Builder = new ContainerBuilder(); string currentContainer = "CurrentContainer"; Builder.RegisterInstance(this).Named(currentContainer, typeof(AutofacContainerExtension)); Builder.RegisterInstance(this).As(); Builder.RegisterInstance(this).As(); //设置过滤AOP //IAspectConfiguration configuration = new AspectConfiguration(); //foreach (var item in AppTypeFinder.Assemblies) //{ // string _namespace = item.FullName; // if (!Regex.IsMatch(_namespace, "^MAX", RegexOptions.IgnoreCase | RegexOptions.Compiled)) // { // configuration.NonAspectPredicates.AddNamespace(_namespace); // } //} //Builder.RegisterDynamicProxy(configuration); } public AutofacContainerExtension(ContainerBuilder builder) { Builder = builder; string currentContainer = "CurrentContainer"; //Builder.RegisterDynamicProxy(); Builder.RegisterInstance(this).Named(currentContainer, typeof(AutofacContainerExtension)); Builder.RegisterInstance(this).As(); Builder.RegisterInstance(this).As(); } public IScopedProvider CreateScope() { return CreateScopeInternal(); } protected IScopedProvider CreateScopeInternal() { _currentScope = new AutofacScopedProvider(Instance); return _currentScope; } public void FinalizeExtension() { if (Instance != null) { return; } Assembly[] assemblies = AppTypeFinder.Assemblies.ToArray(); // Make sure any not specifically registered concrete type can resolve. IEnumerable startupList = ReflectionHelper.GetInstancesByInterface(assemblies); int index = 1; foreach (IStartup item in startupList.OrderByDescending(a => a.Priority)) { Debug.WriteLine($"Startup - {index++} : {item.GetType()}"); item.Initialize(); } // Make sure any not specifically registered concrete type can resolve. IEnumerable ListDependency = ReflectionHelper.GetInstancesByInterface(assemblies); foreach (IDependencyRegistrar item in ListDependency) { item.Register(Builder); } IEnumerable PreRegisterTypes = ReflectionHelper.GetInstancesByInterface(assemblies); foreach (IPreRegisterTypes item in PreRegisterTypes) { item.RegisterTypes(this); } Builder.RegisterSource(new AnyConcreteTypeNotAlreadyRegisteredSource()); Instance = Builder.Build(); IocManager.SetContainer(Instance); } public bool IsRegistered(Type type) { return Instance.IsRegistered(type); } public bool IsRegistered(Type type, string name) { return Instance.IsRegisteredWithName(name, type); } public IContainerRegistry Register(Type from, Type to) { Builder.RegisterType(to).As(from); return this; } public IContainerRegistry Register(Type from, Type to, string name) { Builder.RegisterType(to).Named(name, from); return this; } public IContainerRegistry RegisterInstance(Type type, object instance) { Builder.RegisterInstance(instance).As(type); return this; } public IContainerRegistry RegisterInstance(Type type, object instance, string name) { Builder.RegisterInstance(instance).Named(name, type); return this; } public IContainerRegistry RegisterSingleton(Type from, Type to) { Builder.RegisterType(to).As(from).SingleInstance(); return this; } public IContainerRegistry RegisterSingleton(Type from, Type to, string name) { Builder.RegisterType(to).Named(name, from).SingleInstance(); return this; } public IContainerRegistry RegisterSingleton(Type type, Func factoryMethod) { Debugger.Break(); throw new NotImplementedException(); } public IContainerRegistry RegisterSingleton(Type type, Func factoryMethod) { Debugger.Break(); throw new NotImplementedException(); } public object Resolve(Type type) { return Instance.Resolve(type); } public object Resolve(Type type, params (Type Type, object Instance)[] parameters) { List listps = new List(); foreach ((Type Type, object Instance) item in parameters) { TypedParameter ps = new TypedParameter(item.Type, item.Instance); listps.Add(ps); } return Instance.Resolve(type, listps); } public object Resolve(Type type, string name) { return Instance.ResolveNamed(name, type); } public object Resolve(Type type, string name, params (Type Type, object Instance)[] parameters) { List listps = new List(); foreach ((Type Type, object Instance) item in parameters) { TypedParameter ps = new TypedParameter(item.Type, item.Instance); listps.Add(ps); } return Instance.ResolveNamed(name, type, listps); } public IContainerRegistry Register(Type type, Func factoryMethod) { Debugger.Break(); throw new NotImplementedException(); } public IContainerRegistry Register(Type type, Func factoryMethod) { Debugger.Break(); throw new NotImplementedException(); } public IContainerRegistry RegisterMany(Type type, params Type[] serviceTypes) { Debugger.Break(); throw new NotImplementedException(); } public IContainerRegistry RegisterManySingleton(Type type, params Type[] serviceTypes) { Debugger.Break(); throw new NotImplementedException(); } public IContainerRegistry RegisterScoped(Type from, Type to) { Debugger.Break(); throw new NotImplementedException(); } public IContainerRegistry RegisterScoped(Type type, Func factoryMethod) { Debugger.Break(); throw new NotImplementedException(); } public IContainerRegistry RegisterScoped(Type type, Func factoryMethod) { Debugger.Break(); throw new NotImplementedException(); } public Type GetRegistrationType(string key) { Type retType = null; //First try friendly name registration. If not found, try type registration foreach (IComponentRegistration registration in Instance.ComponentRegistry.Registrations) { //System.Diagnostics.Debug.WriteLine(registration.ToString()); foreach (Service service in registration.Services) { //System.Diagnostics.Debug.WriteLine(service.ToString()); if (service is KeyedService ks) { if (key.Equals(ks.ServiceKey.ToString(), StringComparison.Ordinal)) { if (Instance.ComponentRegistry.TryGetServiceRegistration(service, out ServiceRegistration serviceRegistration)) { retType = serviceRegistration.Registration.Target.Activator.LimitType; } } } } } //Instance.TryResolveService //retType = Instance.ResolveNamed(key).GetType(); if (retType == null) { retType = Instance.ResolveNamed(key).GetType(); if (retType == null) { retType = typeof(System.Object); } } return retType; } public Type GetRegistrationType(Type serviceType) { Debugger.Break(); throw new NotImplementedException(); } private class AutofacScopedProvider : IScopedProvider { private readonly IContainer _container; public bool IsAttached { get; set; } public IScopedProvider CurrentScope => this; public IScopedProvider CreateScope() { return this; } public AutofacScopedProvider(IContainer container) { _container = container; } public void Dispose() { _container.Dispose(); } public object Resolve(Type type) { return _container.Resolve(type); } public object Resolve(Type type, params (Type Type, object Instance)[] parameters) { List listps = new List(); foreach ((Type Type, object Instance) item in parameters) { TypedParameter ps = new TypedParameter(item.Type, item.Instance); listps.Add(ps); } return _container.Resolve(type, listps); } public object Resolve(Type type, string name) { return _container.ResolveNamed(name, type); } public object Resolve(Type type, string name, params (Type Type, object Instance)[] parameters) { List list = new List(); foreach ((Type Type, object Instance) item in parameters) { TypedParameter ps = new TypedParameter(item.Type, item.Instance); list.Add(ps); } return _container.ResolveNamed(name, type, list); } } } }