在 PC 上或通过 TFS 构建间歇性 BadImageFormatException 构建 "plugin" DLL

Intermittent BadImageFormatException building "plugin" DLL on PC or via TFS build

我有一个应用程序,其中几个程序集是与主应用程序分开构建的。在 运行 时,它们位于主 BIN 文件夹之外的文件夹中,并由主应用程序使用 Assembly.LoadFrom 加载。在这些 "plugin" 程序集的 VS 项目中,引用了从主应用程序构建的物理程序集。

主应用程序和插件的构建均由 TFS 构建服务器构建。 "plugin" 程序集项目引用的程序集通常取自主应用程序的 TFS 构建,但有时它们取自我的 PC 上创建的构建。

我每天都在处理这个应用程序,99% 的插件构建工作正常。然后没有任何明显的解释,主应用程序将无法加载插件程序集,并出现以下错误:

System.BadImageFormatException: Could not load file or assembly 'file:///C:\Program Files\MyCompany\MainApp\Plugins\MyApp.Plugins.ABC.XYZ.dll' or one of its dependencies. The module was expected to contain an assembly manifest.
File name: 'file:///C:\Program Files\MyCompany\MainApp\Plugins\MyApp.Plugins.ABC.XYZ.dll'
   at System.Reflection.RuntimeAssembly._nLoad(AssemblyName fileName, String codeBase, Evidence assemblySecurity, RuntimeAssembly locationHint, StackCrawlMark& stackMark, IntPtr pPrivHostBinder, Boolean throwOnFileNotFound, Boolean forIntrospection, Boolean suppressSecurityChecks)
   at System.Reflection.RuntimeAssembly.nLoad(AssemblyName fileName, String codeBase, Evidence assemblySecurity, RuntimeAssembly locationHint, StackCrawlMark& stackMark, IntPtr pPrivHostBinder, Boolean throwOnFileNotFound, Boolean forIntrospection, Boolean suppressSecurityChecks)
   at System.Reflection.RuntimeAssembly.InternalLoadAssemblyName(AssemblyName assemblyRef, Evidence assemblySecurity, RuntimeAssembly reqAssembly, StackCrawlMark& stackMark, IntPtr pPrivHostBinder, Boolean throwOnFileNotFound, Boolean forIntrospection, Boolean suppressSecurityChecks)
   at System.Reflection.RuntimeAssembly.InternalLoadFrom(String assemblyFile, Evidence securityEvidence, Byte[] hashValue, AssemblyHashAlgorithm hashAlgorithm, Boolean forIntrospection, Boolean suppressSecurityChecks, StackCrawlMark& stackMark)
   at System.Reflection.Assembly.LoadFrom(String assemblyFile)

发生这种情况时,我会采取各种措施来尝试解决它,但我没有可靠的解决方案。我尝试了以下所有方法,最终问题消失了:

有时,当构建服务器构建的插件显示此问题时,在我的 PC 上构建的构建可以运行。其他时候两个构建都会显示问题。

到目前为止,主要应用程序和插件解决方案的构建配置都针对 "Any CPU"。今天(在看到很多 S/O 帖子将此异常与目标处理器架构相关联之后)我尝试将两者都切换到目标 x64,但这没有任何区别。

我不知道还要看什么...有什么想法吗?

我自己想出来了。它与构建本身或目标处理器架构无关。

程序集在安装过程中被损坏。我使用 MSBUILD Community Tasks 将插件程序集压缩到 ZIP 文件中以供分发。虽然任务成功完成,并且可以解压缩程序集,但手动检查包含无法加载的插件的 ZIP 文件显示它们有 CRC 错误。

解决方案是在 ZIP 任务中使用 ParallelCompression="false",例如

<Zip Files="@(PackageAssemblies);@(PackageAssemblyPDBs);@(PackageDocuments);@(PackageOtherFiles)" Flatten="True" WorkingDirectory="$(MSBuildProjectDirectory)" ZipFileName="$(PackageOutputFolder)$(PackageName)_$(Major).$(Minor).$(Revision)_Install.zip" ParallelCompression="false" />

在这里找到了线索:https://groups.google.com/forum/#!topic/msbuildtasks/txBNNAWNwYo