NuGet自动包恢复不适用于MSBuild

时间:2014-03-10 12:39:24

标签: .net build msbuild nuget nuget-package-restore

我正在尝试使用MSBuild 12.0构建一个缺少packages内容的解决方案(内部除repositories.config除外)。我希望它能在构建之前自动恢复所有丢失的软件包但事实并非如此--MsBuild会报告大量错误:

  

“你错过了使用指令或汇编引用吗?”

NuGet Manager是2.7(我在Visual Studio 2013中看到这个关于框)。我甚至试图传递EnableNuGetPackageRestore=true参数 - 没有运气。我错过了什么?

12 个答案:

答案 0 :(得分:228)

如果您使用的是MSBuild 15附带的Visual Studio 2017,和.csproj文件位于new PackageReference format ,最简单的方法是use the new MSBuild Restore target


没有人真正回答了原来的问题,这是"在使用MSBuild从命令行构建时,如何让NuGet包自动恢复?"答案是:除非您使用"启用NuGet包恢复"选项(现已根据this reference弃用),您不能(但请参见下文)。如果你想做的话,例如在CI服务器上自动构建,这很糟糕。

然而,有一种稍微迂回的方式来获得所需的行为:

  1. https://dist.nuget.org/win-x86-commandline/latest/nuget.exe下载最新的NuGet可执行文件,并将其放在PATH中的某个位置。 (您可以将此作为预构建步骤。)
  2. 运行nuget restore,它会自动下载所有丢失的软件包。
  3. 运行msbuild以构建解决方案。
  4. 除此之外:虽然新的和推荐的自动包恢复方法涉及到版本控制中的混乱,但它也使得命令行包恢复变得不可能,除非您跳过额外的下载并运行nuget.exe。进度?

答案 1 :(得分:54)

Nuget的自动包恢复是Visual Studio的一项功能(从2013年开始),而不是MSBuild。如果要从命令行还原包,则必须运行 nuget.exe restore

您还可以使用“启用Nuget包还原”功能,但nuget人员不再推荐此功能,因为它会对项目文件进行侵入式更改,如果您在其他解决方案中构建这些项目,可能会导致问题。

答案 2 :(得分:34)

自v3.3.0起最新的官方NuGet文档更新

包恢复方法

  

NuGet提供了三种使用package restore的方法。


  

Automatic Package Restore 是NuGet团队在Visual Studio中推荐的Package Restore方法,它是在NuGet 2.7中引入的。   从NuGet 2.7开始,NuGet Visual Studio扩展集成到Visual Studio的构建事件中,并在构建开始时恢复缺少的包。默认情况下启用此功能,但开发人员可以根据需要选择退出。


  

以下是它的工作原理:

     
      
  1. 在项目或解决方案构建中,Visual Studio会引发一个事件:   构建正在解决方案中开始。
  2.   
  3. NuGet回应此事件   并检查解决方案中包含的packages.config文件。
  4.   
  5. 对于找到的每个packages.config文件,枚举其包   已检查是否存在于解决方案的packages文件夹中。
  6.   
  7. 从用户配置(和启用)的包源中下载任何缺少的包,并遵守包源的顺序。
  8.   
  9. 随着软件包的下载,它们将被解压缩到解决方案中   包文件夹。
  10.   

  

如果您安装了Nuget 2.7+;为>选择一种方法很重要。在Visual Studio中管理自动包还原。

     

有两种方法可供选择:

     
      
  1. (Nuget 2.7+):Visual Studio - >工具 - >包管理器 - >包   经理设置 - >启用自动包恢复
  2.   
  3. (Nuget 2.6及以下)右键单击解决方案并单击“启用包”   恢复此解决方案“。
  4.   


  从命令行构建解决方案时需要

Command-Line Package Restore ;它是在早期版本的NuGet中引入的,   但在NuGet 2.7中有所改进。

nuget.exe restore contoso.sln

  

<强> The MSBuild-integrated package restore   方法是原始的Package Restore实现,尽管如此   在许多情况下继续工作,它没有覆盖整套   其他两种方法解决了这些问题。

答案 3 :(得分:17)

花了一些时间来弄清楚整个画面,我想在这里分享一下。

Visual Studio有两种使用包还原的方法:自动包还原和MSBuild集成包还原。 “MSBuild-集成软件包还原”可在构建过程中恢复软件包,这些软件包可能会在某些情况下导致问题。 NuGet团队的“自动包恢复”为the recommended approach

有几个步骤可以让“自动包恢复”工作:

  1. 在Visual Studio中,工具 - &gt;扩展和更新,如果有更新版本(版本2.7或更高版本),请升级NuGet

  2. 如果您使用TFS,请在解决方案的.nuget文件夹中删除NuGet.exe和NuGet.targes文件。然后编辑NuGet.Config以不检入NuGet包:

    <configuration>  
      <solution>  
        <add key="disableSourceControlIntegration" value="true" />  
      </solution>  
    </configuration> 
    

    如果您之前已将解决方案的packages文件夹签入TFS,请删除该文件夹并检查删除包文件夹删除。

    如果您不使用TFS,请删除.nuget文件夹。

  3. 在解决方案中的每个项目文件(.csproj或.vbproj)中,删除引用NuGet.targets文件的行。参考文献如下:

    <Import Project="$(SolutionDir)\.nuget\NuGet.targets" Condition="Exists('$(SolutionDir)\.nuget\NuGet.targets')" />
    

    在解决方案中的每个项目文件中删除此行。

  4. 在Visual Studio菜单中,通过

    工具 - &gt;选项 - &gt;包管理器 - &gt;一般或 工具 - &gt; NuGet包管理器 - &gt;包管理器设置

    请启用以下两个选项 1)'允许NuGet下载丢失的包' 2)'在Visual Studio中构建期间自动检查缺少的包'

  5. 按照以下步骤测试您的包恢复配置

    • 保存解决方案并关闭Visual Studio
    • 删除解决方案的包文件夹
    • 启动Visual Studio,打开解决方案并重建它。

答案 4 :(得分:5)

MSBuild 15有/t:restore option这样做。它附带Visual Studio 2017。

如果你想使用它,你还必须使用新的PackageReference,这意味着用这样的元素替换packages.config文件(在* .csproj中这样做):

<ItemGroup>
  <!-- ... -->
  <PackageReference Include="Contoso.Utility.UsefulStuff" Version="3.6.0" />
  <!-- ... -->
</ItemGroup>

如果您右键单击“引用”,则会自动迁移到此格式(如果您刚刚打开Visual Studio,重建或打开'管理NuGet包以获得解决方案'窗口,它可能不会显示,它将开始显示)。

答案 5 :(得分:4)

Ian Kemp有答案(有点点btw ..),这只是为他的一个步骤添加一些肉。

我最终在这里的原因是dev的机器正在构建良好,但构建服务器根本没有拉下所需的包(空包文件夹),因此构建失败。但是,登录到构建服务器并手动构建解决方案。

要完成第二个Ians 3点步骤(运行 nuget restore ),您可以创建一个运行exec命令的MSBuild目标来运行nuget restore命令,如下所示(在本例中为nuget。 exe位于.nuget文件夹中,而不是在路径上),然后可以在构建解决方案之前立即在TeamCity构建步骤(其他CI可用...)中运行

<Target Name="BeforeBuild">
  <Exec Command="..\.nuget\nuget restore ..\MySolution.sln"/>
</Target>

为了记录,我已经尝试了“nuget installer”的跑步者类型,但这一步是挂在Web项目上(适用于DLL和Windows项目)

答案 6 :(得分:3)

请注意,如果您使用 TeamCity 作为构建服务器,则可以使用“NuGet Installer”步骤在构建步骤之前恢复所有软件包。

答案 7 :(得分:2)

项目中有一个 packages.config 文件,其中包含软件包详细信息。

还有一个.nuget文件夹,其中包含 NuGet.exe和NuGet.targets 。如果缺少任何一个文件,它将无法恢复丢失的软件包并导致&#34;您是否缺少using指令或程序集引用?&#34;错误

答案 8 :(得分:2)

有时,如果您要在&#34; packages&#34;中找到要恢复的包的文件夹,就会发生这种情况。文件夹(即&#34; Packages / EntityFramework.6.0.0 /&#34; 但&#34; DLL&#34;不在里面(大多数版本控制系统会自动忽略&#34; .dll&#34;文件)。发生这种情况是因为在NuGet尝试恢复每个包之前它会检查文件夹是否已经存在,所以如果它存在,NuGet会假设&#34; dll&#34;在里面。因此,如果这是您的问题,只需删除NuGet将正确恢复它的文件夹。

答案 9 :(得分:0)

在Visual Studio 2017中 - 使用IDE编译时 - 它将下载所有缺少的nuget包并保存在“packages”文件夹中。

但是在构建机器上编译是使用msbuild.exe完成的。在那种情况下,我下载了nuget.exe并保存在路径中。

在执行msbuild.exe之前的每个构建过程中。它将执行 - &gt; nuget.exe恢复NAME_OF_SLN_File(如果只有一个.SLN文件,那么你可以忽略该参数)

答案 10 :(得分:0)

我遇到的问题是nuget包没有包含在使用devenv.exe构建sln文件的脚本化夜间版本中。

我关注advice from Microsoft,关键步骤是更新%AppData%/NuGet中的NuGet配置,使其包含:

<configuration>
    <packageRestore>
        <add key="automatic" value="True" />
    </packageRestore>
</configuration>

答案 11 :(得分:0)

您也可以使用

Update-Package -reinstall

在Visual Studio的程序包管理控制台上还原NuGet程序包。