如何强制.NET使用GAC中的程序集的本地副本

时间:2008-11-06 05:06:16

标签: .net gac

我有一个.NET程序集(由于我无法控制的原因)必须在GAC中。但是,同一个程序集由另一个程序使用,该程序具有自己的同一程序集的旧版本的副本。它必须使用自己的副本,而不是GAC中的任何副本。在这种情况下,正确的版本控制可能比它的价值更麻烦,原因我不会进入。我的问题是:无论如何都要告诉.NET:只需使用此DLL,就在此目录中 - 忽略您在GAC或其他任何地方找到的内容

6 个答案:

答案 0 :(得分:44)

确保GAC程序集和本地程序集具有不同的版本号(至少可以通过在AssemblyInfo中对AssemblyVersion进行粗分析来自动增加构建号,这不是一个坏主意:[assembly:AssemblyVersion(“1.0.0) 。*“)])。然后,使用应用程序的配置重定向程序集绑定:

在您的情况下,您不需要assemblyBinding配置的“applyTo”属性。你只需要:

<runtime>
    <assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
        <dependentAssembly>
            <assemblyIdentity name="YourAssembly" publicKeyToken="AAAAAAAAAAAA" culture="neutral"/>
            <bindingRedirect oldVersion="0.0.0.0-5.2.1.0" newVersion="5.0.8.1"/>
        </dependentAssembly>
    </assemblyBinding>
</runtime>

答案 1 :(得分:27)

如果它们具有相同的版本号,则答案是您不能。如果您尝试加载具有与GAC程序集相同的完整程序集名称(名称,版本,密钥)的程序集,则CLR将每次都选择GAC程序集。

答案 2 :(得分:10)

您可以将DEVPATH设置为强制加载程序集,请参阅link text

这不能回答你的问题,因为它只适用于开发用途,即使之后也没有真正推荐,因为它不反映生产用法。不过,我想我会分享它,因为它很高兴知道。

答案 3 :(得分:1)

您是否尝试过Assembly.LoadFromFile()?这是一个手动操作,但应该在需要之前将程序集加载到内存中。然后,.NET将使用内存中的那个而不是寻找它。

另一种方法是如果本地程序集是无符号的,你可以用这种方式区分它。

罗布

答案 4 :(得分:1)

我有类似的问题。我使用ildasmilasm更改了目标dll的publicKeyToken以生成新的dll。然后我在项目引用中更新它以指向新的dll。我采取的步骤是here

这对我有用。

答案 5 :(得分:0)

绑定重定向不起作用的原因之一是因为Oracle.ManagedDataAccess提供程序对dll的搜索顺序与非托管提供程序不同。非托管提供程序从应用程序目录开始,然后在注册表中查找dllpath,然后在machine.config中查找dll路径,然后在web.config中查找dll路径。根据Oracle文档,托管提供者的搜索顺序如下:

  

托管驱动程序将通过以下搜索顺序引用这些程序集:

  1. 全局程序集缓存
  2. Web应用程序的bin目录或Windows应用程序的EXE目录
  3. 基于应用程序运行在32位还是64位.NET Framework中的x86或x64子目录。如果应用程序是使用AnyCPU构建的,则只要程序集可用,ODP.NET就会使用正确的DLL位。如果您的应用程序是AnyCPU,Oracle建议使用此方法查找相关程序集。

https://docs.oracle.com/en/database/oracle/oracle-database/12.2/odpnt/installODPmd.html#GUID-0E834EC7-21DF-4913-B712-2B0A07FD58FD

因此,解决此问题的方法是注销GAC程序集,或者如果无法卸载,则只需在bin和web.config中放入与GAC不同的Oracle.ManagedDataAccess版本。