ABP之模塊


ABP的反射

為什么先講反射,因為ABP的模塊管理基本就是對所有程序集進行遍歷,再篩選出AbpModule的派生類,再按照以來關系順序加載。

ABP對反射的封裝着重於程序集(Assembly)與類(Type)。系統中分別定義了IAssemblyFinder與ITypeFinder兩個接口,從命名上就可以看出這兩個接口主要是用來進行程序集與類查找的。

IAssemblyFinder只提供了一個方法 GetAllAssemblies(),從IAssemblyFinder的實現類CurrentDomainAssemblyFinder可以看出這個方法的功能是獲取當前應用程序域下所有的程序集。

 

 

    public class CurrentDomainAssemblyFinder : IAssemblyFinder
    {
        /// <summary>
        /// Gets Singleton instance of <see cref="CurrentDomainAssemblyFinder"/>.
        /// </summary>
        public static CurrentDomainAssemblyFinder Instance { get { return SingletonInstance; } }
        private static readonly CurrentDomainAssemblyFinder SingletonInstance = new CurrentDomainAssemblyFinder();

        public List<Assembly> GetAllAssemblies()
        {
            return AppDomain.CurrentDomain.GetAssemblies().ToList();
        }
    }
View Code

 

 

 

ITypeFinder接口提供了兩個方法Find,FindAll,這兩個方法的查找范圍都是所有當前應用程序域下所有的程序集。ABP為ITypeFinder提供了默認的實現類ITypeFinder,這個類中有個private方法GetAllTypes與一IAssemblyFinder的字段AssemblyFinder。Find,FindAll方法都是都是對GetAllTypes返回結果進行再篩選。

 

 

        public Type[] Find(Func<Type, bool> predicate)
        {
            return GetAllTypes().Where(predicate).ToArray();
        }

        public Type[] FindAll()
        {
            return GetAllTypes().ToArray();
        }

        private List<Type> GetAllTypes()
        {
            var allTypes = new List<Type>();

            foreach (var assembly in AssemblyFinder.GetAllAssemblies().Distinct())
            {
                try
                {
                    Type[] typesInThisAssembly;

                    try
                    {
                        typesInThisAssembly = assembly.GetTypes();
                    }
                    catch (ReflectionTypeLoadException ex)
                    {
                        typesInThisAssembly = ex.Types;
                    }

                    if (typesInThisAssembly.IsNullOrEmpty())
                    {
                        continue;
                    }

                    allTypes.AddRange(typesInThisAssembly.Where(type => type != null));
                }
                catch (Exception ex)
                {
                    Logger.Warn(ex.ToString(), ex);
                }
            }

            return allTypes;
        }
View Code

 

 

 

 

主角AbpModule

AbpModule是一抽象類,所有的模塊都是他的派生類。AbpModule提供PreInitialize,Initialize,PostInitialize,Shutdown四個無參無返回值方法,從名字上就可以看出AbpModule的生命周期被划成四部分,其中初始化被分成了三部分。

兩屬性

protected internal IIocManager IocManager { get; internal set; }

protected internal IAbpStartupConfiguration Configuration { get; internal set; }

 

這兩個屬性的set方法都不是對程序集外公開的,所以可以判斷這兩個屬性都是ABP系統自身賦值的。再看IocManager,對於這一系統核心依賴注入容器管理者,應該只有一個,所以它應該就是對IoCManager.Instance的引用(這一部分后面會具體體現)。

對於Configuration屬性,因還沒具體看Configuration部分,所以暫時不細說。但從名字看,它應該是給AbpModule提供一些配置信息。

模塊依賴

當一模塊的初始化需要其他的模塊時,就需要指定它的依賴模塊。 在ABP中定義了DependsOnAttribute來出來模塊間的依賴關系。

 

 

    [AttributeUsage(AttributeTargets.Class, AllowMultiple = true)]
    public class DependsOnAttribute : Attribute
    {
        /// <summary>
        /// Types of depended modules.
        /// </summary>
        public Type[] DependedModuleTypes { get; private set; }

        /// <summary>
        /// Used to define dependencies of an ABP module to other modules.
        /// </summary>
        /// <param name="dependedModuleTypes">Types of depended modules</param>
        public DependsOnAttribute(params Type[] dependedModuleTypes)
        {
            DependedModuleTypes = dependedModuleTypes;
        }
    }
View Code

 

 

 

 

DependsOnAttribute只提供了一Type數組屬性DependedModuleTypes,用來指定當前模塊的依賴AbpModule。依賴模塊也是AbpModule類型的,不知ABP為什么沒做類型判斷。

 

AbpModuleInfo與AbpModuleCollection

AbpModuleInfo就對模塊的抽象,而AbpModuleCollection是AbpModuleInfo的集合,存儲系統所有的模塊信息。其中AbpModuleCollection提供GetSortedModuleListByDependency方法,這個方法的主要作用就是獲取按依賴關系排序后的AbpModuleInfo集合。排序的具體實現間ListExtensions。

 

 

ModuleFinder

IModuleFinder及其實現類DefaultModuleFinder,主要是查賬應用程序域中所有的模塊類(即AbpModule的非抽象派生類)。

 

AbpModuleManager

AbpModuleManager的主要功能是查找應用程序域下所有AbpModule,再對模塊進行實例化,初始化,以及銷毀。

AbpModuleManager提供了InitializeModules與ShutdownModules來管理所有模塊的生命周期。

 

ABP對模塊的初始化的規范

對於這一部分我就直接引用陽銘的文章了。http://www.cnblogs.com/mienreal/p/4537522.html

 

ABP的入口

IoCManager與AbpModuleManager分別是依賴注入與系統模塊的管理者,那么是什么驅動這兩個系統核心。在翻看源代碼中,都把矛頭指向了AbpBootstrapper。

 

 

    public class AbpBootstrapper : IDisposable
    {
        /// <summary>
        /// Gets IIocManager object used by this class.
        /// </summary>
        public IIocManager IocManager { get; private set; }

        /// <summary>
        /// Is this object disposed before?
        /// </summary>
        protected bool IsDisposed;

        private IAbpModuleManager _moduleManager;

        /// <summary>
        /// Creates a new <see cref="AbpBootstrapper"/> instance.
        /// </summary>
        public AbpBootstrapper()
            : this(Dependency.IocManager.Instance)
        {

        }

        /// <summary>
        /// Creates a new <see cref="AbpBootstrapper"/> instance.
        /// </summary>
        /// <param name="iocManager">IIocManager that is used to bootstrap the ABP system</param>
        public AbpBootstrapper(IIocManager iocManager)
        {
            IocManager = iocManager;
        }

        /// <summary>
        /// Initializes the ABP system.
        /// </summary>
        public virtual void Initialize()
        {
            IocManager.IocContainer.Install(new AbpCoreInstaller());

            IocManager.Resolve<AbpStartupConfiguration>().Initialize();

            _moduleManager = IocManager.Resolve<IAbpModuleManager>();
            _moduleManager.InitializeModules();
        }

        /// <summary>
        /// Disposes the ABP system.
        /// </summary>
        public virtual void Dispose()
        {
            if (IsDisposed)
            {
                return;
            }

            IsDisposed = true;

            if (_moduleManager != null)
            {
                _moduleManager.ShutdownModules();
            }
        }
    }
View Code

 

 

 

 

因為AbpBootstrapper實現了IDisposable,所以AbpBootstrapper自身只提供吧 Initialize方法對系統進行初始化,再實現的Dispose方法下對系統進行關閉。

 

在ABP中提供了自己的HttpApplication派生類AbpWebApplication。其中有一AbpBootstrapper的屬性,再AbpWebApplication構造函數中直接實例化AbpWebApplication,在Application對AbpBootstrapper進行初始化,在Application_End對AbpBootstrapper進行Shutdown。

 

 protected AbpBootstrapper AbpBootstrapper { get; private set; }

        protected AbpWebApplication()
        {
            AbpBootstrapper = new AbpBootstrapper();
        }

        /// <summary>
        /// This method is called by ASP.NET system on web application's startup.
        /// </summary>
        protected virtual void Application_Start(object sender, EventArgs e)
        {
            AbpBootstrapper.IocManager.RegisterIfNot<IAssemblyFinder, WebAssemblyFinder>();
            AbpBootstrapper.Initialize();
        }

        protected virtual void Application_End(object sender, EventArgs e)
        {
            AbpBootstrapper.Dispose();
        }
View Code

 

 

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM