【问题标题】:C# plugin system binary compatibility issuesC#插件系统二进制兼容性问题
【发布时间】:2011-08-23 09:07:49
【问题描述】:

我在 .NET 中实现了一个插件系统。基础库实现暴露给插件的基本类和接口,插件库链接基础库以使用暴露的类和接口。

我面临的问题是基础库的(简单)重新编译(有或没有修改)导致插件无法加载,并给出异常消息:

 "Could not load file or assembly 'BaseLibrary, Version=0.0.1.68, Culture=neutral, PublicKeyToken=7b445b12e635292c' or one of its dependencies. The located assembly's manifest definition does not match the assembly reference. (Exception from HRESULT: 0x80131040)"

这个问题是通过一次编译基础库和插件库来解决的,但是这在开发过程中不是很舒服,因为我在这个阶段经常修改基础库。

是否有任何方法可以“放松”二进制匹配?

是否有可能是基础库程序集信息(引用如下)可能是问题的原因?

 [assembly: AssemblyVersion("0.0.1.*")]

我忘了提到程序集已签名。


使用以下例程加载程序集

Assembly hLibrary = Assembly.LoadFile(pPath);
Type plugImageCodecFactoryType = hLibrary.GetType("Derm.ImageCodecPluginFactory", true, false);
object plugImageCodecFactory = Activator.CreateInstance(plugImageCodecFactoryType);
object plugInstance;

MethodInfo plugFactoryCreate = plugImageCodecFactoryType.GetMethod("CreatePlugin", BindingFlags.Instance|BindingFlags.Public);

plugInstance = plugFactoryCreate.Invoke(plugImageCodecFactory, null);

if (plugInstance is IImageCodecPlugin)
    RegisterPlugin((IImageCodecPlugin)plugInstance);

【问题讨论】:

    标签: c# plugins binary-compatibility


    【解决方案1】:

    阅读这些问题和答案,以更深入地讨论 AssemblyVersion 与 AssemblyFileVersion 的使用。

    Ignoring build numbers when referencing DLLs

    Differences between AssemblyVersion and AssemblyFileVersion

    简而言之,您应该仅在您对该程序集引入可能会导致依赖项采用新版本的潜在破坏性更改时更改 AssemblyVersion。

    对于较小的更改,您可以使用 AssemblyFileVersion 来标记差异。

    所以我会使用静态程序集版本进行开发,当您获得想要管理的稳定版本时增加它并手动管理未来的版本增量。

    【讨论】:

      【解决方案2】:

      假设您使用的是 Visual Studio,请查看其中一个插件项目中的引用。当您查看对基本库的引用的属性时,SpecificVersion 标志设置为什么?尝试将其设置为False,看看是否有区别。

      请注意,如果您的项目使用项目引用而不是直接引用已编译的 DLL,则此标志将不存在。在这种情况下,您需要像尝试过的那样在基本库上使用固定的修订号,或者您应该改用对 DLL 的直接引用,以便更改 SpecificVersion 属性。

      【讨论】:

      • 文件引用不会看到 Debug/Release/x86/x64 编译。但是 Juozas Kontvainis 在stackoverflow.com/questions/915712/… 的回答可以很好地解决这个问题。
      • @Luca 足够公平,尽管 OP 没有询问不同的编译,但有用的信息
      【解决方案3】:

      对我来说,这里与插件无关,因为编译器错误谈论的是基础库,并且考虑到您实现了插件基础架构,插件必须完全解耦并延迟加载。所以即使有插件加载问题,也会在运行时遇到而不是编译时。

      所以对我来说原因是你的程序集版本。

      问候。

      【讨论】:

      • 是的,将版本修订版修复为 68(而不是默认的 *),即使在基础库重新编译的情况下,插件也会被加载并正确运行。那么,如何忽略插件加载的修订?我想只用主要和次要版本标记二进制更改。
      • 留0,有什么问题?
      • 版本修订标识源/二进制版本。修订更改需要重新编译每个插件(以及部署)。
      • 好的,但同样,保留为 0 并增加您需要的那部分版本。我的意思是,如果您不想更改最后一个数字,请不要更改它,没有人也没有任何技术会强迫您这样做。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-10-11
      • 1970-01-01
      相关资源
      最近更新 更多