我的问题:
我有一个已签名的程序集A.dll,它的版本为1.0.0.0 我有另一个引用A.dll的程序集(比如说B.dll)。
一旦两个组件都装配好,没有任何问题。 现在,如果A.dll的版本更改为1.0.0.1并重新编译,是否必须重新编译B.dll?
我问,因为我有这个确切的场景,在A.dll的版本发生变化后,我现在收到以下异常,试图加载B.dll:
Unhandled Exception: System.IO.FileLoadException:
Could not load file or assembly A, Version=1.0.0.0,
Culture=neutral, PublicKeyToken…
这让我觉得这个问题的答案总是肯定的。但是,我有另一个例子,我有两个具有上述确切方案的程序集,我在加载程序集时没有任何问题。
什么情况/条件导致此异常?如果有人能对此提供一些见解,将不胜感激。 感谢。
答案 0 :(得分:2)
当程序集强名称时,引用它的任何内容都将查找该特定版本。
您是正确的,Visual Studio中的“特定版本”不会以任何方式影响运行时。实际上,“特定版本”基本上意味着“当您运行构建时,如果MSBUILD无法找到引用的版本,构建是否会失败,或者只是使用可以在文件系统上找到的下一个版本?”
如果您重新编译A并将其部署为部分更新(而不是完全推出应用程序),那么如果应用程序中有任何引用旧版本的内容,您的应用程序可能会中断,除非您仍然拥有旧版本的A也可用(即你没有覆盖它)。
这是一些产品使用GAC的主要原因,因为它可以容纳相同DLL的多个版本而不会相互覆盖 - 如果您尝试将同一文件的不同版本部署到bin文件夹中(假设它们具有相同的文件名,他们通常会这样做,他们会互相覆盖,你只会得到你产品中的1个DLL!
您可以做的另一个技巧是将“重新版本化”的DLL放在二进制目录下的子文件夹中,然后编辑app.config以告知运行时在哪里找到它们。 http://support.microsoft.com/kb/837908
因此,总而言之,强名称程序集不仅使用简单名称来确定程序集的标识 - 更改其版本可以被视为完全更改其名称。
答案 1 :(得分:1)
装配件A是否签名并不一定重要。您是否在项目B的程序集引用中使用'Specific Version = true'进行编译?如果是这样,那么CLR将使用严格的规则来确定给定版本的A是否可接受。如果没有,则CLR将使用不太严格的规则,如果A增加其版本,则无需重新编译。
根据您的环境,您可能不会担心A会破坏未来版本的兼容性。如果您不关心它,那么您应该将程序集引用更改为“Specific Version = false”。 (在工作中,我们有两种情况:例如,当我们依赖第三方控制时,我们通常强制'特定版本=真',但是当我们使用内部共享组件时,我们将对其进行测试使用它的应用程序,我们将确保'Specific Version = false',因此我们不需要重新编译。)
您可以在MSDN上找到更多信息,包括当做必须针对特定版本进行编译但希望稍后重定向绑定时如何通过配置文件规避此问题:Redirecting Assembly Versions < / p>
希望有所帮助!