4
votes

I am trying to create a NuGet package using our TFS 2013 build. I basically followed THIS steps and locally everything works fine.
But our build does not use the default output directories and that seems to crash the nuget pack command.
On my local machine everything is builded into SOLUTION/PROJECT/bin/Release, but the TFS Build uses BUILD/Sources/SOLUTION/PROJECT for the sources and BUILD/Binaries/Release as its output directory. Running the build I get the following log/error:

BuildPackage:
"D:\BUILD\Sources\SOLUTION\.nuget\NuGet.exe" pack "D:\BUILD\Sources\SOLUTION\PROJECT\PROJECT.csproj" -Properties "Configuration=Release;Platform=AnyCPU" -NonInteractive -OutputDirectory "D:\BUILD\Binaries\Release" -symbols -NoPackageAnalysis -BasePath "D:\BUILD\Binaries\Release" Attempting to build package from 'PROJECT.csproj'.

D:\BUILD\Sources\SOLUTION\.nuget\NuGet.targets(133,5): error : Unable to find 'D:\BUILD\Sources\SOLUTION\PROJECT\bin\Release\PROJECT.dll'. Make sure the project has been built.

I then added the -BasePath "$(TargetDir)" to the BuildCommand in NuGet.targets, but still no change:

<BuildCommand>$(NuGetCommand) pack "$(ProjectPath)" -Properties "Configuration=$(Configuration);Platform=$(Platform)" $(NonInteractiveSwitch) -OutputDirectory "$(PackageOutputDir)" -symbols -NoPackageAnalysis -BasePath "$(TargetDir)"</BuildCommand>

How can I tell NuGet to load the correct files using TFS?

UPDATE:
I found a workaround: If I set the build output path of the project to the same "relative path" as used by our TFS build it works...
But that can't be the solution, right?

2

2 Answers

9
votes

I had the same exact problem as you in my own TFS builds. The problem is that when NuGet pack is invoked with a csproj file, it literally evaluates the csproj as a MSBUILD file and the default OutDir MSBUILD property is set to {ProjectDir}\bin\{ConfigurationName}.

But with TFS builds, the output directory is usually set to a staging location such as BUILD/Binaries/Release in your case.

What you are missing, is this OutDir property to NuGet pack, here is an example that should work for you:

<BuildCommand>$(NuGetCommand) pack "$(ProjectPath)" -Properties "Configuration=$(Configuration);Platform=$(Platform);OutDir=$(OutDir)" $(NonInteractiveSwitch) -OutputDirectory "$(PackageOutputDir)" -symbols -NoPackageAnalysis -BasePath "$(TargetDir)"</BuildCommand>

With this additional OutDir property, NuGet should be able to find your newly built binaries and add them to the package.

-1
votes

Setting OutDir or other path related parameters might not be enough. For example, it will not work for the case if your .nuspec is including files by relative path, it will fail to find them.

What worked for us is specifying the -Build option for nuget pack. From the docs:

Build : Determines if the project should be built before building the package.

It will try first to build the project (with default parameters + supplied properties) and will correctly find output files with all included files.