作者:青玄道长,道号青玄

基于OSGI.NET的前端模块化设计与开发

基于OSGI.NET开发

导航

.net 插件内核之功能定义

 一.情况说明

 

   由于最近在忙其它事情,该系列也搁置了段时间,今天忙里偷闲,先把功能定义下来,后续在开发过程中进行不断的完善

 

二.功能定义

 

  1.插件内核的整个项目结构如下:

   

  其中:Minimal.Plugin.Contracts模块定义插件的相关契约,元数据以及相关的接口,不会在该模块进行功能实现

  Minimal.Plugin.Toolkit模块主要用于存放插件内核相关的工具类

  Minimal.Plugin.Runtime模块主要是对Minimal.Plugin.Contracts定义的契约的简易实现,至于IOC之类的功能将不会在插件内核引入,争取做到插件内核极简

2.对于插件内核启动则需要定义内核启动接口以及相关的初始化接口,具体接口定义如下:

 其中插件在初始化的时候需要扫描指定的目录或者下载服务器端的插件文件进行解析,因此需要定义插件扫描发现接口,具体接口如下:

至于具体的参数在后续进行调整,插件内核默认实现指定的插件目录组进行插件发现

3.当插件内核初始化完成之后,将会获取插件文件列表,即:Manifest.xml的一个地址列表,我们基于该列表对插件文件进行解析

4.插件文件解析接口定义:

其中:BundleData就是Manifest.xml插件描述文件的元数据信息,BundleData(后续会将整个插件内核代码进行上传,暂时这样看下吧)的定义如下:

插件内核拿到插件的元数据信息之后,将会根据插件元数据信息进行插件构建,因此需要定义插件相关接口

5.插件内核在启动的时候需要执行插件的初始化,启动,停止,加载并启动指定的插件,卸载指定的插件等功能,目前插件内核启动插件时暂时定义以下几个接口

6.目前插件内核初始化,插件搜索,元数据解析,插件列表启动等功能以定义,但是对于具体插件还未定义,之前已经说过插件包含了激活器,插件描述文件,插件上下文等信息,其中插件激活器定义如下:

插件上下文信息定义为:

说明:对于一个插件来说,该功能定义明显不够,如获取插件的依赖列表,当前插件的元数据信息,当前插件的状态等,功能的丰富后续会在实现时进行

7.对于插件解析完成之后,内核加载时如何将该插件对应的dll,自己私有的dll,依赖的插件加载进内存,因此还需要定义插件的加载接口

8.对于目前定义而言,基本的插件内核功能已明确,骨架已基本成型,后续在实现的时候会随时进行完善,下面我们具体看下插件描述信息的定义

a.BundleInfoData定义了插件的基本信息,可有可无,具体可以查看Manifest.xml插件描述文件的BundleInfo的节点

b.对于一个插件而言需要有插件的基本信息,其基本信息如下:

其中:Name为插件的中文名称

SymbolicName:插件的唯一标识,后续插件的加载,分析,解析都是该标识作为Key值进行处理

Version:插件的版本号,由于每个插件都可以独立启动,因此后续在插件发布,自动更新等时会已该版本号作为基准,如:插件在发布到插件仓库的时候默认都会对插件版本号进行+1处理,内核会根据版本号比对是否需要更新该插件

StartLevel:插件的启动级别,该启动级别决定插件何时进行解析和加载,如果处理不好如服务注册之后,其它插件使用该服务的时候如果启动级别高于该级别会出现空引用问题,这个也是插件使用过程中很容易出现的问题,因此在OGIS.NET定义的标准之上,对插件多定义了Initialize,Configure两个方法,旨在插件内核启动加载插件时进行处理,以淡化启动级别的作用

c.对于插件而言需要配置插件的激活器,也就是插件执行完成时执行的方法,目前插件激活器的描述如下:

<Activator Type="激活器,如:Axon.Login.BundleActivator"/>

说明:插件激活器不是必须的,当一个插件无激活器时,我认为系统只需要加载插件对应的dll到内存即可,如第三方的dll如果不去包装只需要该dll则可以进行这种处理:将dll和插件描述文件包装成一个插件格式,可以不配置激活器进行加载

d.对于一个独立的插件极有可能会加载自己私有的dll,对于插件依赖的私有的dll目前描述如下:

e.插件化框架出现插件的相互依赖很常见,目前插件依赖的插件在描述文件里边定义如下:

说明:OSGI.NET将依赖的插件以及插件运行时依赖的dll定义于一个节点,目前我这边拆分出来分别进行定义,主要原因是自己的能力有限未必能解析出来,所以简化下

f.对于插件内核来说如何能做到高可扩展,有一个重要的思想或者说OSGI的规范很重要即:扩展点以及扩展数据的定义,目前在插件描述文件里边是这样体现的:

g.对于插件而言很有可能出现某个插件有自己的属性的定义,或者一些配置信息,在以前处理该问题时都是定义一个配置插件去管理插件的私有属性信息,但是在我分析SharpDevelop的Addin时发现可以在Addin.xml内配置插件的私有属性,因此参考该思想,在插件描述文件中也添加了私有属性的配置节点

h.就目前而言对于一个插件的描述文件的定义已经能满足大多数要求了,但是在定义复杂界面的时候可能会写很多的扩展点,为了避免该坑,在分析SharpDevelop的Addin插件树以及密码子等模型时发现它的插件描述定义很灵活,比如插件文件内新增了一个节点,只需要对该节点进行定义和解析即可,因此在我的插件内核中也引入了该概念,标签定义为TagExtends,具体如下:

对于TagExtends定义的标签将会在下一个节点Widgets内使用,也只能在该节点内使用,此处模仿了Addin,不过没有人家的高大上,其中Widgets如何使用的见下图:

说明:实在是对SharpDevelop的Addin插件树的思想所折服,因此在Minimal.Plugin插件内核中也定义了类似于插件树的概念,只不过由于个人能力有限,目前需要扩展标签TagExtends,微件Widgets(自己实在想不出一个响亮的名字,原谅我的自作主张)来实现插件树的概念,后续在解析的过程中不会具体的构造一个对应的插件树,而会根据path组装成一个扁平化的结构进行处理(实际上已经在这样做了,而且还实现了一个类似于VS的页面布局,这个都是后话,如果该插件内核完成之后,会基于该内核做一个UI界面框架)

 

三.感言

 

1.对于Minimal.Plugin插件内核目前已经实现了具体的概念和功能,目前之所以拿出来写博客是想记录下自己的设计过程,目前来说在写博客的过程中对其进行调整和优化并将一些优化过程中的想法写出来而已

2.对于插件内核的其它接口后续将不会再进行分析,在实现过程中会附带说明

3.该插件内核参考了OSGI.NET,SharpDevelop Addin以及Eclipse内核的部分设计和概念,因此在糅合的过程中需要不断的摸索,有时候看起来确实很突兀,希望大家理解

4.对于插件的具体结构在前一篇文章中有说明,后续不会在进行详细记录

5.对于OSGI规范中提到的插件片段概念(OSGI.NET有实现),目前对于我来说还未搞明白在哪种场景下可以使用,即使自己使用OSGI.NET 7-8年了也未发现使用场景,因此不会在该插件内核中实现

6.后续不会计划插件的热启动,因为该过程可能会非常复杂,我估计我可能,也许,应该搞不定,因此不会去考虑这些

7.最近一直在看Cola框架和Halo框架,如果合适的话后续可能会将业务扩展点的概念也会加入该插件内核,如果自己和自己讨论通过,将会按照自己的讨论结果执行

8.Minimal.Plugin.Runtime只是极简实现,不会引用一些高大上的第三方dll

9.咱们把目标定高点,比如我们的要求是造火箭,别到时候造出来一个窜天猴,要么飞不起来,要么拿手里还给炸了

 

四.下期预告

    1.后续将会围绕着Minimal.Plugin插件内核的开发过程,不定期的发布相关的文章

 

五.声明

    1.如果侵害您或者别人的权益请及时告知,本人将及时处理

    2.有好的建议与想法可以留言

 

posted on 2022-04-06 23:35  道号青玄  阅读(300)  评论(0编辑  收藏  举报