2015-09-25 51 views
1

我有一个需要间接使用三个不同版本的第三方库的项目。这些版本互不兼容,所以我不能使用绑定重定向 - 它必须是确切的.dll文件。 (该库是Spire.DocSpire.XLS & Spire.PDF;在Spire.PDF DLL由三个引用)引用同一个DLL的多个版本

我有三个组成部分分离成单个包装项目,并创建的类包装,其在图书馆的任何直接引用。但是,这并没有解决我的问题:'消费'项目仍然需要将所有库复制到bin文件夹才能运行。构建过程不知道要复制哪个版本,因此只复制最新版本。由于存在错误的DLL,这给我提供了运行时异常。

我已经考虑/尝试:

  • 添加一个绑定重定向到一个特定版本(运行时异常,因为库的确切版本未找到)
  • 使用生成后步骤合并包装器项目(同样是一个运行时异常,抱怨缺少库DLL)
  • 为应用程序的每个部分创建单独的控制台应用程序,然后单独调用它们 - 这是一个复杂的最后手段,我真的而不是做!

我读过extern alias可能会有所帮助 - 但据我所知,您只能区分名称不同的程序集。 Spire.PDF库在每个项目中具有相同的名称(以及相同的签名公共令牌)。

如何在同一解决方案中独立使用这三个独立版本的库?

编辑:

这个问题所建议的重复略有不同,因为我没有改变依赖库的任何代码的能力。 Spire.Doc依赖于不同版本的Spire.PDF Spire.XLS

+0

有趣的问题!我想你可能需要在运行时反思并加载dll。这有可能吗? – Muthu

+0

也许我并没有完全理解这个问题,但就我所见,问题在于Visual Studio将文件复制到另一个上。为什么不告诉它不要这样做呢? – Dialecticus

+0

此外,也许这个问题可以帮助:http://stackoverflow.com/q/5260404/395718 – Dialecticus

回答

2

在您的消费项目(项目A)中,创建一个通用界面(ISpiroPdfAlex),该界面包含外部程序集的3个版本提供的所有功能(和你使用)。您无法以任何方式从这些包装中引用任何东西中的项目A,否则您会创建依赖项,这是您要避免的依赖项。

将所有3个包装项目导入项目A并执行ISpiroPdfAlex。这将使您能够通过相同的API调用3个不同版本中的每一个。

在此之后,下项目A各自的版本(所以3子文件夹总数)的创建子文件夹 - 因为项目A没有引用任何外部组件,它本身不能加载它们 - 你当你需要正确的版本时,必须手动加载它们。由于外部DLL可能具有相同名称的依赖关系,因此它们不能全部位于同一文件夹中(如您所写),这就是为什么您需要子文件夹。

在当你需要使用这些版本之一,你可以调用Assembly.LoadFile从指定的文件夹中加载组件的特定版本,然后您可以使用Activator.CreateInstance或依赖注入来创建一个类的实例的运行时间实现你的界面。一旦你有了这个实例,你可以自由地调用任何函数,并且你会得到与版本相关的行为。

编辑:在注释中提到,这不是他的代码,对不同版本的PDF库,但他的代码依赖于其他第三方石塔库的依赖

OP。

在这种情况下,无法修改第三方代码以支持程序集的动态加载,并且它们已经具有二进制相关性。无法将不同版本的“相同”程序集加载到相同的进程中,特别是您提到这些版本甚至不能向后兼容。

在这种情况下,我能想到的唯一解决方案是将所有相关功能分解为单独的控制台应用程序(每个控制台应用程序一个),并通过命令行调用这些单独的.exe-s。

要传递信息,您可以直接在命令行或通过stdin传递数据。或者,您可以传递临时文件的名称,该文件具有进行某些处理所需的所有数据。要从控制台进程返回返回数据,您可以读取它的stdout或使用相同/不同的文件。

这样,你的主进程永不加载任何这些程序集,并且不依赖于它们 - 每个控制台应用程序只依赖于一个版本,所以没有冲突。

+0

这听起来像一个很好的计划 - 我现在会尝试 – AlexFoxGill

+0

我仍然有一个问题,图书馆有依赖关系之间 - 所以Spire.Doc试图加载Spire.PDF'3.4.108.54040',但Spire.XLS需要版本'3.4.183.55040' – AlexFoxGill

+0

@AlexFoxGill我更新了我的回答后,您的评论。 – xxbbcc

相关问题