在app.manifest中指定精确的引用版本

时间:2012-05-02 16:28:00

标签: .net reference manifest gac publisher-policy

虽然在我们的应用程序中实现了ODP.Net的使用,但我遇到了版本的潜在问题,因此我敲了一个快速测试应用程序,看它是否会影响我们,它确实如此。

我们的客户在Oracle上拥有或想要我们的应用程序,但他们使用不同的版本,并且他们通常对其工作站上部署的Oracle客户端版本具有公司标准。我们的想法是使用我们的应用程序(在程序目录中)部署固定版本的ODP以及相应的即时客户端,因为Oracle保证客户端的任何给定版本的两个主要版本的兼容性,这意味着我们可以使用Oracle 10.1使用部署ODP和Client 11.1直到理论上的Oracle 12。

没关系,但是如果我们的客户端部署更高版本的Oracle客户端,在GAC中注册更新版本的ODP,以及发布者策略告诉应用程序使用新版本,则问题就出现了。我们正在使用EntlibContrib(ODP包装器)中的一个库的自定义实现,该库使用我们使用的特定版本的EL5和ODP构建,并且将新版本部署到GAC会导致此失败,正如测试应用程序所证明的那样。 / p>

为了测试这一点,我使用了安装了Win 7 x86的干净VM,然后添加了Oracle Client 10.2(在GAC中注册了ODP 10.2)并让我的测试应用程序使用ODP和Client 11.1。这很好用,所以我安装了客户端11.2,并在GAC中注册了ODP,这也添加了发布者策略,这证明了测试应用程序会失败。

为了解决这个问题,我在app.manifest中添加了一个依赖项,如下所示:

  <dependency>
    <dependentAssembly>
      <assemblyIdentity
          type="win32"
          name="Oracle.DataAccess"
          version="2.111.7.20"
          processorArchitecture="x86"
          publicKeyToken="89b483f429c47342"
       />
    </dependentAssembly>
  </dependency>

这与我们正在部署的ODP二进制文件的版本和公钥相匹配,因此我希望测试应用程序能够使用它。但是在启动应用程序时出现以下错误:

The application has failed to start because its side-by-side configuration is incorrect.

事件日志包含:

Activation context generation failed for "C:\Program Files\OPT\OPT\OraclePerformanceTester.exe". Dependent Assembly Oracle.DataAccess,processorArchitecture="x86",publicKeyToken="89b483f429c47342",type="win32",version="2.111.7.20" could not be found. Please use sxstrace.exe for detailed diagnosis.

使用sxstrace,我得到以下输出:

Begin Activation Context Generation.
Input Parameter:
    Flags = 0
    ProcessorArchitecture = x86
    CultureFallBacks = en-US;en
    ManifestPath = C:\Program Files\OPT\OPT\OraclePerformanceTester.exe
    AssemblyDirectory = C:\Program Files\OPT\OPT\
    Application Config File = C:\Program Files\OPT\OPT\OraclePerformanceTester.exe.Config

INFO: Parsing Application Config File C:\Program Files\OPT\OPT\OraclePerformanceTester.exe.Config.
INFO: Parsing Manifest File C:\Program Files\OPT\OPT\OraclePerformanceTester.exe.
INFO: Manifest Definition Identity is OraclePerformanceTester.exe,version="1.0.0.0".
INFO: Reference: Oracle.DataAccess,processorArchitecture="x86",publicKeyToken="89b483f429c47342",type="win32",version="2.111.7.20"
INFO: Resolving reference Oracle.DataAccess,processorArchitecture="x86",publicKeyToken="89b483f429c47342",type="win32",version="2.111.7.20".
INFO: Resolving reference for ProcessorArchitecture x86.
    INFO: Resolving reference for culture Neutral.
        INFO: Applying Binding Policy.
            INFO: No publisher policy found.
            INFO: No binding policy redirect found.
        INFO: Begin assembly probing.
            INFO: Did not find the assembly in WinSxS.
            INFO: Attempt to probe manifest at C:\Windows\assembly\GAC_32\Oracle.DataAccess\2.111.7.20__89b483f429c47342\Oracle.DataAccess.DLL.
            INFO: Attempt to probe manifest at C:\Program Files\OPT\OPT\Oracle.DataAccess.DLL.
            INFO: Attempt to probe manifest at C:\Program Files\OPT\OPT\Oracle.DataAccess.MANIFEST.
            INFO: Attempt to probe manifest at C:\Program Files\OPT\OPT\Oracle.DataAccess\Oracle.DataAccess.DLL.
            INFO: Attempt to probe manifest at C:\Program Files\OPT\OPT\Oracle.DataAccess\Oracle.DataAccess.MANIFEST.
            INFO: Did not find manifest for culture Neutral.
        INFO: End assembly probing.
ERROR: Cannot resolve reference Oracle.DataAccess,processorArchitecture="x86",publicKeyToken="89b483f429c47342",type="win32",version="2.111.7.20".
ERROR: Activation Context generation failed.

引用的文件(Oracle.DataAccess.dll)存在于可执行文件旁边的程序目录中,包含所有其他依赖项,但由于某种原因它只是不会提取它。我之前必须使用的唯一清单是UAC检查一个工作正常的exe,据我所知,我已经按照步骤指定了一个应该覆盖发布者策略的确切版本。我做错了什么?

干杯

1 个答案:

答案 0 :(得分:0)

我要补充一个答案,因为Hans Passant(他给了我答案)没有添加正式答案,而且我想扩展它,因为Hans的答案与我发现的其他答案相似,但不是过于清楚,因为他们只讲述部分故事。

在app.config中添加<publisherPolicy apply="no" />确实有效,但我发现几乎所有地方都说这不能解释app.config中应该去的 where 。您需要将此添加到<runtime>部分,如下所示:

<configuration>
    <!--Other Sections-->
    <runtime>
        <assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
            <dependentAssembly>
             <!--Ensures Oracle Publisher Policies don't override the version of ODP being used.-->
                <assemblyIdentity name="Oracle.DataAccess" publicKeyToken="89B483F429C47342"/>
                <publisherPolicy apply="no"/>
              </dependentAssembly>
        </assemblyBinding>
    </runtime>
    <!--Other Sections-->
</configuration>

您必须根据需要更改程序集名称和公钥。就是这样。我从一个通常可靠的来源获得了关于使用清单文件的duff信息,所以这里的教训是在最后花费一些时间之前仔细检查你的信息。时间尝试输出 - 这可能是浪费时间。