Wednesday, March 21, 2018

Have MSBuild only build targets that require building

Leave a Comment

So long story short, we've got a situation of having multiple solutions with assembly references between them. Used to be, we had to go and build these solutions in the correct order to have our dependencies built correctly.

I'm trying to make things easier by using MSBuild tasks to first restore nuget on the dependent solution, then build the dependencies for you, ie:

<Target Name="BeforeBuild" Condition="'$(Configuration)'=='Debug'">     <Message Importance="high" Text="Kicking off internal dependency build for $(MSBuildProjectName) in Configuration=$(Configuration), Platform=$(Platform), OutDir=$(OutDir)" />     <!--Build the dependencies-->     <Message Importance="high" Text="Restoring MyDependencyProject NuGet External Packages..." />     <Exec Command="..\..\bin\nuget.exe restore ..\MyProject\MyDependencyProject\MyDependencyProject.sln" />     <Message Importance="high" Text="Building MyDependencyProject dependency..." />     <MSBuild Projects="..\MyProject\MyDependencyProject\MyDependencyProject\MyDependencyProject.csproj" Targets="Build" Properties="Configuration=$(Configuration)" />     <Message Importance="high" Text="Building MyDependencyProject2 dependency..." />     <MSBuild Projects="..\MyProject\MyDependencyProject\MyDependencyProject\MyDependencyProject2.csproj" Targets="Build" Properties="Configuration=$(Configuration)" /> </Target> 

This works great! What used to be 7(!) separate solutions we had to open and build, is now condensed to 2 (we build our C++ COM libraries, then build our C# libraries).

One problem - while this is easier, it is very slow. I've been going over the diagnostic output from MSBuild, and it seems that the way I've set this up is forcing the dependencies to be rebuilt every single time. If I had set Targets="Rebuild" I would expect this, but I thought Targets="Build" would build ONLY IF a project was out of date (or had a file set to):

<CopyToOutputDirectory>Always</CopyToOutputDirectory>  

in the project file). I can not find any message in the diagnostic output to explain why the MSBuild target is rebuilding these dependencies, even if the dependencies have not been touched.

Why does MSBuild do a full rebuild of dependency projects that have not been altered with the above tasks?

Edit - More information

I see the following:

Target "IncrementalClean: (TargetId:324)" in file "C:\Program Files (x86)\MSBuild\14.0\bin\Microsoft.Common.CurrentVersion.targets" from project "c:\Source\MyProject\MyDependencyProject\MyDependencyProject\MyDependencyProject.csproj" (target "CoreBuild" depends on it): 

0 Answers

If You Enjoyed This, Take 5 Seconds To Share It

0 comments:

Post a Comment