Net dll组件版本兼容问题

dll组件版本兼容问题,是生产开发中常常遇到的问题,常见组件兼容问题如:Newtonsoft.Json,log4net等html

为了节约你们时间,想直接看解决方法的,可直接点击目录三、4git

目录


1.版本兼容问题的缘由缓存

2.解决版本兼容前提markdown

3.指定特定版本bindingRedirect**工具

4.指定某文件夹中的特定版本codeBase**gitlab

 

版本兼容问题的缘由


首先让咱们简单了解下程序引用的原理:visual-studio

当运行库试图解析对另外一个程序集的引用时,就开始进行定位并绑定到程序集的进程。详细见:运行库如何定位程序集测试

步骤以下:spa

解决版本兼容前提


简单了解原理之后,常看法决兼容的方法.net

1. 首先了解你要用那个dll,具体版本是什么,查看版本方法:

1)文件夹里dll文件,右键->属性

2)解决方案里引用的dll,右键->属性

 

方法一、指定特定版本**


 利用config的bindingRedirect指向特定版本组件

.config添加节点

<configuration>
<runtime>
<assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
<dependentAssembly>
<assemblyIdentity name="Newtonsoft.Json" publicKeyToken="30ad4fe6b2a6aeed" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-10.0.0.0" newVersion="10.0.0.0" />
</dependentAssembly>
</assemblyBinding>
</runtime>
</configuration>

 解释:

项目中全部项目、类库引用0~10的Newtonsoft.Json版本,最终都指向到10这个版本

经验:

一、各版本之间是有代码变化的,若是一个类库用了某个组件10.0的A10方法,结果指向的8.0,8.0颇有可能尚未A10这个方法,天然项目中用到A10的地方会报错。调试和查错误比较麻烦,编译器会根据bin下面的dll版本与代码来匹配调用方法和属性提示错误,或者不提示错误。

二、代码可控的地方,尽量的将版本更新中的废弃方法改为高版本的替代方法。

三、通常高版本多数是兼容低版本的方法,指向高版本报错概率小些,固然也有特殊状况。

方法二、指定某文件夹中的特定版本


方法一能解决不少项目中出现的版本问题,可是有时候仍是会遇到比较奇怪的兼容问题。

例如:log4net和Memcached.ClientLibrary中的log4net冲突的问题,本文以解决这一版本冲突问题为例介绍此方法的使用方法。

若是想直接看结果,请点击解决方法

为啥会出现log4net版本兼容问题呢?

常见的组件是以name(名称)、version(版本)、publicKeyToken(公钥)三个组成,缘由主要是因为log4net version 1.2.11与1.2.10的publicKeyToken不一样所致。

可利用VS工具SN -T 组件文件名.dll查看公钥。

log4net (≥ 1.2.11) 公钥标记为 669e0ddf0bb1aa2a

log4net (= 1.2.10) 公钥标记为 1b44e1d426115821

看log4net在发展过程当中改过一次身份证,又有好多老版本的组件引用了log4net的低版本致使与高版本兼容问题

 log4net版本兼容问题的样例

一、建立项目,引用Memcached组件

WebApp为项目应用层,ClassLibrary为工具类库,WebApp引用ClassLibrary项目,ClassLibrary经过nuget引入Memcached.ClientLibrary 1.0组件。

ClassLibrary建立类Testing.cs代码以下:

    public class Testing
    {
        public static void Init()
        {
            MemcachedClient mc = new MemcachedClient();
        }
    }

 WebApp建立测试页面,测试代码以下:

Testing.Init();

二、应用层,引用高版本log4net

WebApp引用log4net 2.0.8

 最终项目状况是:

 三、运行结果

查看WebApp的bin文件夹下面的log4net版本是2.0.8,而Memcached.ClientLibrary组件用的log4net是1.2.10.0版本,因此报错了。

注意

若是单独编译WebApp,bin下面是版本是2.8.0,若是单独编译ClassLibrary类库,bin下面版本是1.2.10.0

 

处理log4net版本兼容问题

一、bin下面添加log4net1.2.10.0文件夹,并将log4net.dll版本为1.2.10.0放入到文件夹中,可重命名为log4net1.2.10.0.dll。

二、config添加

  <runtime>
    <assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
      <dependentAssembly>
        <assemblyIdentity name="log4net" publicKeyToken="1b44e1d426115821" />
        <codeBase version="1.2.10.0" href="bin/log4net1.2.10.0/log4net1.2.10.0.dll" />
      </dependentAssembly>
      <dependentAssembly>
        <assemblyIdentity name="log4net" publicKeyToken="669e0ddf0bb1aa2a" culture="neutral" />
        <bindingRedirect oldVersion="0.0.0.0-2.0.8.0" newVersion="2.0.8.0" />
      </dependentAssembly>
    </assemblyBinding>
  </runtime>

 三、结果以下

经验:

一、文件须要放在bin下面,并单独创建个文件夹,注意:若不创建文件夹,直接将重命名的log4net1.2.10.0.dll扔到bin下会报错,应该是探测方法是根据name寻找的。

二、ClassLibrary类库在单独编译的时候,会将高版本的替换成低版本,会有可能报错,能够在开发中将其生成的dll不复制到bin下,设置是在引用的dll下右键,复制本地设置为false,操做以下:

三、为了能把log4net1.2.10.0.dll上传到gitlab上面,能够在WebApp创建个相应文件夹,并设置复制到输出目录-始终复制,vs编译时会自动将log4net1.2.10.0/log4net1.2.10.0.dll复制到bin下面

总结


 但愿经过此文章,帮助更多的人解决NET组件的版本兼容问题。

参考文章


https://www.cnblogs.com/shijun/p/3713830.html

https://blog.csdn.net/zfrong/article/details/6183353

https://docs.microsoft.com/zh-cn/previous-versions/dotnet/netframework-3.5/6bs4szyc(v%3dvs.90)

https://docs.microsoft.com/zh-cn/previous-versions/visualstudio/visual-studio-2008/yx7xezcf(v=vs.90)


文章和观点,有可能由于知识和阅历的缘由,分析片面,请多谅解。

相关文章
相关标签/搜索