9

我正在尝试实现类似应用程序的插件。我知道已经有几种解决方案,但这只是概念的证明,仅此而已。这个想法是让应用程序主应用程序默认几乎没有功能,然后让插件相互了解,让它们实现所有需要的功能。

出现了几个问题:

  1. 我希望插件在运行时通过我的应用程序相互了解。这并不意味着在代码时他们不能引用其他插件的程序集,以便他们可以使用它的接口,只是插件功能初始化应该始终通过我的主应用程序进行。例如:如果我同时加载了插件 X 和 Y 并且 Y 想要使用 X 的功能,它应该通过我的应用程序“注册”它的兴趣以使用它的功能。我必须在我的应用程序中有一种“字典”,用于存储所有加载的插件。在注册对我的应用程序感兴趣后,插件 Y 将获得对 X 的引用,以便它可以使用它。这是一个好方法吗?
  2. 在编写使用 X 的插件 Y 时,我需要引用 X 的程序集,这样我就可以针对它的接口进行编程。那有版本控制的问题。如果我针对插件 X 的过时版本编写插件 Y 怎么办?我是否应该始终使用所有程序集所在的“中心”位置,始终保持最新版本的程序集?

是否有专门针对.NET 的此类设计的书籍?

谢谢

编辑:我认为人们正在远离我提出的 2 个问题。我可以查看 MEF 和#develop,但我想获得对我提出的问题的具体答案。

4

5 回答 5

6

我建议调查MEF。这是在 .NET 中做插件的一种新方法。例如,这是为 VS2010 做新插件的推荐方式。我自己没有使用过它,但是我对它的研究看起来很棒。将此添加为刺激他人的答案:)

于 2010-05-07T23:38:14.267 回答
3

查看System.AddIn命名空间。它比 MEF 略低一些,因此应该为您提供您正在寻找的“自己实现”体验。

于 2010-05-07T21:59:19.030 回答
2

有一本关于构建您正在寻找的东西的好书:剖析 C# 应用程序:在 SharpDevelop 中。这是一个链接: http: //www.icsharpcode.net/OpenSource/SD/InsideSharpDevelop.aspx

SharpDevelop 应用程序完全基于插件,本书讨论了他们如何构建它、他们面临的陷阱以及他们如何克服它。该书可从该网站免费获得,或者您也可以购买。

于 2010-05-07T22:39:29.037 回答
1

一旦我使用这个例子完成了它。我喜欢它,但那是几年前的事了,我认为现在可能有更好的解决方案。只要我记得基本思想是你的程序中有抽象类,你的插件继承该类并编译为 DLL ......或使用接口类似的东西。无论如何,这种方法对我很有用。后来我添加了一个文件系统观察器,这样它就可以在运行时加载那些 DLL 插件。

加载装配体

获取程序集公开的类型

于 2010-05-07T22:18:33.370 回答
0

关于您暴露的两个具体问题:

1)我不确定您要实现什么目标,但我的猜测是您希望延迟初始化功能,并且可能延迟加载加载项。如果这是目标,那么您提出的建议可能会奏效。所以它可以像这样工作:

  • Y 插件提供了它需要使用的功能列表(例如,可以通过特定的接口实现或通过 xml 清单来完成)。
  • X 插件实现了一个 API,该 API 允许使用Initialize(featureId)之类的方法来初始化功能。
  • 宿主应用程序获取 Y 所需的功能列表,加载/初始化 X 插件,并为每个功能调用Initialize
  • 宿主应用程序还提供了一个GetFeature()方法,Y 可以使用该方法来获取对“特征”对象的引用,该对象将在 X 中实现。

但是,如果插件 Y 可以直接访问 X API,我认为没有必要拥有所有用于注册功能的基础设施。Y 可以直接使用 X API 访问 X 功能,并且 Y 会在需要时负责延迟初始化每个功能。例如,Y 可以只调用 SomeXFeature.DoSomething(),并且该类的实现将在第一次使用该功能时对其进行初始化。

2) 如果程序集的 API 发生变化,任何依赖于它的程序集都可能会中断。插件只是依赖于其他程序集的程序集,因此它们也会中断。您可以采取以下措施来缓解此问题。

  • 为每个插件分配一个版本号。这可能只是汇编版本。
  • 加载插件时,请确保可以正确满足所有依赖项(即,它所依赖的所有插件都必须存在并具有所需的版本)。如果无法满足依赖关系,则拒绝加载插件。
  • 实现插件管理工具,用于所有插件安装/卸载操作。管理器可以在尝试安装依赖项不满足的插件时检查依赖项并报告错误,或者在尝试卸载其他插件所依赖的插件时。

Mono.Addins框架使用了类似的解决方案。在 Mono.Addins 中,每个插件都有一个版本号和它所依赖的插件/版本列表。加载加载项时,加载项引擎确保同时加载所有具有正确版本的依赖加载项。它还提供了一个 API 和一个命令行工具来管理插件的安装。

于 2010-08-06T17:58:46.337 回答