I get a strange behaviour in visual studio Vs executing msbuild in command line.
a solution (s1) contains 3 project (p1,p2,pB). p1 and p2 are "normal" VS project while pb is an xml msbuild file I wrote myself. The purpose of the task pB contains is modifying some part of the source code.
I did configure dependencies so that p1 and P2 depends on pB to be sure pB is the first project to execute.
When a do a compilation (pressing F6 key) in visual studio, the files are modified but it seems that p1 and p2 start before that modification so my result is not what I expended. Also, when I look in the build console everything seems ok.
And when A launch the compilation via "msBuild s1", everything is perfected !
How can I have the same behaviour between VS2010 and msbuild ?
Thx
Everytime you build a VS solution it creates a .sln.cache file wich is a quite a csproj file with every project you have in your solution.
Thus modifying the csproj files during the build will have no effect in your current build (which uses the .sln.cache file).
If you register pB project in BeforeBuild in both projects p1 and p2 like
<Target Name="BeforeBuild">
<MSBuild Projects="pB.proj" Properties="Configuration=$(Configuration)" />
</Target>
you can call MSBuild task and pass all needed parameters. This solution will works in both environments.
Related
I have a VS2017 csharp project and the .csproj file looks like the following:
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>netcoreapp2.0</TargetFramework>
</PropertyGroup>
<ItemGroup>
<MyItem Include="file.dat" />
</ItemGroup>
<PropertyGroup>
<PrepareResourcesDependsOn>
$(PrepareResourcesDependsOn);
MyCompileTarget
</PrepareResourcesDependsOn>
<CoreCompileDependsOn>
$(CoreCompileDependsOn);
MyCompileTarget
</CoreCompileDependsOn>
</PropertyGroup>
<Target Name="MyCompileTarget" Inputs="#(MyItem)" Outputs="#(MyItem->'%(FileName).out')">
...
</Target>
</Project>
Where MyCompileTarget is a target that generates the file.out from file.dat (in the actual code the incremental build target and properties are in a target file automatically included via a NuGet package).
The issue is that if I change file.dat and press on Build, no target is executed at all, (but MyTarget is correctly executed with Rebuild or when running with msbuild). I would expect the MyCompileTarget to be executed so that the file.out file is updated.
The same issue occurs if I use BeforeBuild or AfterBuild instead of PrepareResourcesDependsOn etc.
It seems that Visual Studio incremental build won't start unless some file in #(Compile) or #(EmbeddedResource) is changed. Indeed, if I add the following
<EmbeddedResource>file.dat</EmbeddedResource>
the incremental build works as expected (but clearly I do not want to embeed the file.dat into the generated assembly).
Is it possible to force Visual Studio to enable incremental build if file.dat is modified, and if the corresponding generated file is older than file.dat or it does not exist?
Note: the same issue occurs using VS2015, with .NET CORE or .NET FRAMEWORK.
Also, incremental build will be triggered if I change a csharp file, and it will therefore trigger MyTask, but only if file.dat is newer than the generated file (as expected).
Thanks in advance,
Fabio.
Is it possible to force Visual Studio to enable incremental build if file.dat is modified
You can set the property DisableFastUpToDateCheck to true in the project file to disable FastUpToDateCheck for Visual Studio build manager:
<PropertyGroup>
<DisableFastUpToDateCheck>True</DisableFastUpToDateCheck>
</PropertyGroup>
Check MSDN about DisableFastUpToDateCheck:
A boolean value that applies to Visual Studio only. The Visual Studio
build manager uses a process called FastUpToDateCheck to determine
whether a project must be rebuilt to be up to date. This process is
faster than using MSBuild to determine this. Setting the
DisableFastUpToDateCheck property to true lets you bypass the Visual
Studio build manager and force it to use MSBuild to determine whether
the project is up to date
Update:
Also, we can set the UpToDateCheckInput to the item:
<UpToDateCheckInput Include="file.dat" />
Disabling the VS fast up-to-date check will make your builds much slower. Don't do it!
Instead, make sure the up-to-date check knows about the items in your project and how they relate to build. There are two kinds of item you can add to your project for this:
UpToDateCheckInput for inputs
UpToDateCheckBuilt for outputs
In your case you need the second option as there is both an input and an output. You need to ensure that if you delete the output, it is rebuilt.
<PropertyGroup>
<UpToDateCheckBuilt Original="#(MyItem)" Include="#(MyItem->'%(FileName).out')">
</PropertyGroup>
For more information, see the documentation:
https://github.com/dotnet/project-system/blob/main/docs/up-to-date-check.md
We have a large non Visual Studio C++ project which is build via a batch file. I have integrated this up in Visual Studio as a makefile project with customised 'Build Command Line' in the project properties, this works well and has done for over a year.
I am now looking to introduce Team Foundation Server and configure automated builds.
If I build the project in Visual Studio then the project build as normal.
If I use the automated build sever to build the project the build fails every time
The option to view the log file in the build report is greyed out. The report given is
The command "Autobuild.cmd" exited with code 1.
Where autobuild is the cmd file specified in the solution's 'Build Command Line'.
Can anyone think of a reason why this might be the case, I assumed that the build sever would just run the Build command with the project specified in the 'Items to Build' box. If this is the case then I cannot see why it would fail.
There are loads of possible reasons; unfortunately you've not given enough information to answer that questions.
The first thing to try is changing your build definition logging level to Diagnostic. (you can also do this when you queue a new build).
What I also recommend is actually wrapping your makefile in an msbuild.proj file.
Something simple like:
<Project ToolsVersion="4.0" DefaultTargets="build"
xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Target Name="build">
<Exec Command="autobuild.cmd" />
</Target>
</Project>
The Exec task has loads of options to customize how the cmd is called and should help you diagnose your error.
In general if you want to take advantaged of TFS builds I'd recommend migrating as much of your autobuild.cmd to msbuild as possible. MSBuild is TFS's "makefile" language, so-to-speak.
In your build definition you have an option of logging, there you can change that to Verbose logging. Maybe you get some information in your log file then.
And for the issue of exited with code 1 I think you will need to add some extra informational lines to be printed in the cmd program and when your logging in TFS Build is active you maybe see more information on it.
I am using Visual Studio Express 2012. Where is the location of the log file? I have searched in the folder where my solution and projects are stored, but cannot find any .log file.
This is the configuration for logging:
Log file from Visual Studio is only supported for C++ projects. You just have to work with the output window for others.
See this similar thread: VS2010: minimal build log in output and detailed log in log file
And in case you happen to do this for a C++ project, the file is at:
... build log in the intermediate files directory
... The path and name of the build log is represented by the MSBuild macro
expression, $(IntDir)\$(MSBuildProjectName).log.
Use build output instead of logging to file. Instead of copy/paste, simply click somewhere in the output and press CTRL + S to save. Visual Studio will prompt you for a location (tested with Visual Studio 2017, but I'm assuming this works in earlier versions too).
The msdn documentation is pretty clear about this (And you ain't gonna like it!):
https://msdn.microsoft.com/en-us/library/jj651643.aspx
Where it says:
To create a build log file for a managed-code project On the menu bar,
choose Build, Build Solution.
In the Output window, highlight the
information from the build, and then copy it to the Clipboard.
Open a
text editor, such as Notepad, paste the information into the file, and
then save it.
While it's true that VS doesn't allow this directly, it is still possible to build with MSBuild "inside" VS2015 and get both the build window output and the log file, as follows: (Arguably this is a bit of a hack.)
In your VS Managed solution, add a new project (Let's call it 'Make').
a. The project type you want is Visual C++/NMake project.
Define the MSBuild commands you need on the command line (see below).
Change the solution configuration to build the NMake project instead of the normal managed projects.
This will create a project that has Build, Rebuild, and Clean command lines where you can execute MSBuild directly. For example:
Rebuild: MSBuild.exe /ds /v:diag /property:Configuration=Debug ..\BuildTest\BuildTest.csproj /t:Clean,Build
Build: MSBuild.exe /ds /v:diag /property:Configuration=Debug ..\BuildTest\BuildTest.csproj /t:Build
Clean: MSBuild.exe /ds /v:diag /property:Configuration=Debug ..\BuildTest\BuildTest.csproj /t:Clean
You can also specify multiple MSBuild.EXE command lines in order to build multiple projects. For the usual build-the-entire-solution outcome you can target only the final end assemblies and let the dependency graph generate the individual targets.
This will produce a .log file, where NAME is the name of the NMake project you used. In the example above, the log would be make.log.
A working example is available on GitHub:
https://github.com/bitblitz/VS_MsbuildExample
(Tested with VS2015)
Note that building individual projects directly will still build with the normal VS behavior, but you can build the full solution inside VS and get the build logs.
I have a custom MSBuild task which among other things adds embedded resources to other projects in the solution. After adding the resources I'd like to then build those projects, but found I can't get this working within Visual Studio.
To test, I stripped out the custom task entirely and redefined a simple AfterBuild target in the web project of a Silverlight solution. The target uses the MSBuild task to build the Silverlight application project in the solution, and looks like this:
<Target Name="AfterBuild">
<PropertyGroup>
<LinkedProject>..\SilverlightApplication1\SilverlightApplication1.csproj</LinkedProject>
</PropertyGroup>
<MSBuild Condition="'$(LinkedProject)' != '' "
Projects="$(LinkedProject)"
Targets="Build"
Properties="CustomFlag=true" >
</MSBuild>
</Target>
The odd thing is that this works perfectly when using MSBuild from the command line, yet does not work in Visual Studio when building the web project. I thought this might be some sort of Silverlight problem, and had the task build a .NET class library project instead, but the result was the same - it worked from the command line but not within VS. In VS there's no actual error - it's just that the Csc task does not compile the assembly and generates no output.
What do I need to do to get this working within Visual Studio?
Pass the 'UseHostCompilerIfAvailable=false' property to the MSBuild task.
It looks like Visual Studio breaks badly if csc is invoked from a MSBuild task as it reuses the initial project build settings for its in-process host compiler. In my case, I was building the same project twice - default build was using target framework v3.5, with a AfterBuild MSBuild task specifying v4.0. I ended up with the same issue - csc appeared to run but produced no output. I think what was happening was that with the UseHostCompilerIfAvailable property set to true, csc was calling the hosted compiler which reused my initial project settings, so even though the command line showed csc "building" my v4.0 assembly, the host compiler was simply overwriting the v3.5 one I had just built!
Change Visual Studio verbosity to detailed and check build log. I think that CoreBuild is not executed if your files have not changed, so you could try to use AfterCompile instead of AfterBuild.
I have a Visual Studio 2010 SharePoint project. If I choose 'Package' from the project menu, a .wsp file is generated. How can I invoke the same build from command line (i.e. what /target is required for MSBuild)?
I got it to work, finally. The tricky part is the fact that the SharePoint targets do not exist when MSBuild loads the .sln file, you have to load the individual .csproj files.
set msbuild="C:\WINDOWS\Microsoft.NET\Framework\v4.0.30319\MSBuild.exe"
set config=Debug
set outdir="C:\out\"
%msbuild% /p:Configuration=%config% /m ../My.SharePoint.Project/My.SharePoint.Projectcsproj /t:Package /p:BasePackagePath=%outdir%
This is also a useful document here: http://msdn.microsoft.com/en-us/ff622991.aspx
"To generate packages when building in
TFS 2010, set the parameter
/p:IsPackaging=True on MSBuild"
Also to package project with msbuild you can use target Package:
Define new target "BuildAndPackage"
<Target Name="BuildAndPackage">
<CallTarget Targets="Build"/>
<CallTarget Targets="Package"/>
</Target>
Use new target in build process:
<Project ToolsVersion="4.0" DefaultTargets="BuildAndPackage">
But this approach not recommended because it may cause errors in TFS Build process..
Set the MSBuild's verbosity to 'maximum' and you should see what is called from the build console.
In VS2010 of course :)