我的解决方案被配置为“恢复包”,但它的一个项目无法构建:-
它可能是一个红鲱鱼,但上述错误出现在包恢复内容之前的日志中,即
接近有问题的项目的 .csproj 文件末尾是这个 <Target>
部分,它似乎产生了上述错误:-
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
<Import Project="$(SolutionDir)\.nuget\nuget.targets" />
<Import Project="..\packages\System.Data.SQLite.Core.1.0.97.0\build\net45\System.Data.SQLite.Core.targets" Condition="Exists('..\packages\System.Data.SQLite.Core.1.0.97.0\build\net45\System.Data.SQLite.Core.targets')" />
<Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
<PropertyGroup>
<ErrorText>This project references NuGet package(s) that are missing on this computer. Enable NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
</PropertyGroup>
<Error Condition="!Exists('..\packages\System.Data.SQLite.Core.1.0.97.0\build\net45\System.Data.SQLite.Core.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\System.Data.SQLite.Core.1.0.97.0\build\net45\System.Data.SQLite.Core.targets'))" />
</Target>
这是怎么回事?我是否正确地假设这个检查是在解决方案的包甚至被恢复之前发生的(因此它为什么失败)?我该如何解决?
解决方案中的其他项目(那些不引用 SQLite 核心包的项目)可以很好地恢复它们的包,并成功构建。
最佳答案
我发现这与您在构建期间用于恢复丢失的 NuGet 包的方法有关。我正在使用众所周知的“启用 NuGet 包还原”选项(通过右键单击解决方案)。问题是有问题的 NuGet 包(“System.Data.SQLite Core (x86/x64)”)添加了一个预构建步骤(较早的元素),该步骤检查此包是否安装了名为 System.Data 的构建目标文件.SQLite.Core.targets。
鸡和鸡蛋浮现在脑海中 - 包尚未恢复,但预构建步骤是检查包文件的存在!
用于恢复 NuGet 包的 recommended approach 现在似乎是较新的“自动包恢复”功能。我的理解是,这会在构建开始之前恢复 NuGet 包,从而避免了上述问题。不幸的是,TFS 2012 不支持此功能。有一种解决方法 ( detailed here ),它涉及在您的解决方案中创建一个 msbuild 项目文件,该文件负责在继续构建解决方案之前恢复 NuGet 包,但这开始变得困惑.
对于任何感兴趣(或熟悉 SQLite.Net)的人,这就是我为解决问题所做的:-
我删除了“System.Data.SQLite Core (x86/x64)”包并添加了“System.Data.SQLite Core MSIL”包。这仅包含托管的 ojit_code 程序集,并且不会对自定义构建目标做任何聪明的事情。
该程序集依赖于 native System.Data.SQLite.dll
,但出于某些奇怪的原因,它被设计为在 [bin]\x86 或 [bin]\x64 子文件夹(取决于体系结构)中查找。这些互操作 DLL 是我删除的原始包的一部分;它的构建目标(导致我的问题)负责将 DLL 复制到这些子文件夹。
为了解决这个问题,我将 x86 和 x64 互操作 DLL 添加到我的项目中,如下所示:-
FooProject
\x86
SQLite.Interop.dll
\x864
SQLite.Interop.dll
我确保他们的
SQLite.Interop.dll
是“内容”,然后将他们的 Build Action
设置更改为“始终复制”。将“内容”文件复制到输出文件夹时,项目文件夹结构会保留,因此这是创建 [bin]\x86 和 [bin]\x64 子文件夹及其各自 DLL 的便捷方式。关于nuget - 一个 NuGet 包(SQLite Core)导致 TFS 构建失败,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/30919328/