I just started with the TeamCity CI server. I have 2 builds
API-Tests
UI-Tests
Both these builds run in parallel whereas both the builds will have a dropdown config parameter with choices(Regression, Sanity)
I have a build name Release with a similar dropdown config parameter with choices(Regression, Sanity) and this build depends on both API-Tests and UI-Tests. The build Release will have to trigger manually by choosing the dropdown parameter(Regression, Sanity).
I want to pass the option chosen in the Release build to both API-Tests and UI-Tests builds. I can't use %dep.*%, since Release build depends on API-Tests and UI-Tests builds.
I have attached the build chain for reference. Please guide me to fix the requirement or suggest at least a workaround.
Sample Build Chain
It seems like you're looking for the reverse.dep.* pattern, which is best described in the official documentation.
Quoting the docs:
It is possible to redefine build parameters in the snapshot-dependency builds when the current build starts. For example, build configuration A depends on B and B depends on C; on triggering, A can change any parameter used in B or C.
It looks like this is your case:
To change a parameter in all dependencies at once, use a wildcard:
reverse.dep.*.<property_name>
Anyway, I would encourage you to read the whole article to get thorough understanding of the subject and choose the most suitable option.
Related
Suppose we have sequential build, i.e. a single node. msbuild parses the solution file, examines all the project dependencies and decides to build the projects in a certain order.
Is it possible to instruct msbuild just to output this order without actually building anything?
P.S.
I realize I can implement this logic myself using MSBuild API. I can read the solution file and all the projects and build the dependency graph myself. I am specifically curious if msbuild can do it, since it does this logic anyway already.
There are various diagnostic features in MSBuild but currently there isn't a feature that is like reporting a SQL execution plan or like PowerShell's -WhatIf parameter.
You could submit a feature request at dotnet/msbuild.
If you do submit a feature request, provide the link here.
Is there any way to make CMake "forget" about a file in the dependency tree? My original problem (to avoid the XY situation) is the following: I want to timestamp the build of a set of tools which have complicated dependencies among them and to other tools. Right now, I want to use a pure timestamp, but later I might want add some info from the repository (SVN). Whatever system I end up implementing needs to have the following characteristics (my "X"):
No unnecessary rebuilding: the executables should not be rebuilt on every make if the only change would be the timestamp.
Update on any change: if any tool is going to be rebuilt or relinked, either by changes to its code or to one of its dependencies, the timestamp needs to be updated.
My current solution goes along the lines of creating a custom command+target that invokes CMake at make time (so the command calls CMake itself with -P script.cmake) to generate a timestamp.h file. The main files of my tools would include that file, and the projects would depend on the target so that it gets rebuilt first.
However, this has its drawbacks: if I do update the timestamp file on every call to make, then CMake's dependency scanner would know about that file even if I do not list it as an explicit dependency of my tools. Thus, every make would trigger at least a recompilation of the respective "main" files and the corresponding relink. With tens of tools, this means slowing down the build when I may be working on just two or three of them at once.
So, I was thinking that my solution would be to somehow make CMake forget about that file when building its dependency tree for the "main" file of each tool. I would keep the dependency on the custom target that does depend on the file, so that it would be regenerated first on each call to make. However, the build tool would not consider that file as relevant to determine whether it is necessary to actually rebuild each individual tool. Thus, tools only with other changes would be rebuilt (satisfying my first criterion), and any change that causes a rebuild of a tool would obviously use the version just generated (fulfilling the second criterion).
To my chagrin, I have not found a way to make the dependency scanner forget about this file, so my solution cannot be put to use. How would I go about doing such a thing? Is it even possible, or is it completely the wrong way to go about this? I am using CMake 3.4, and my code is currently C++, but I would like a solution that did not rely on C/C++ specifics, since I have a different project (written in Fortran) in which I would also like to have build timestamping.
I've had almost the same problem than you are. Simply solved by pushing the timestamp header file into standalone target containing only this header generator command. After that you have several choices:
1.. Exclude that project from the build by the IDE you are using. For example, for the Visual Studio you can do it by several ways:
1.1. Project->Project Dependencies...->uncheck project with that header (not always works: Error while removing project dependency in VS2010)
1.2. Build->Configuration Manager...->uncheck project with that header
2.. Create an environment variable and use the condition with that variable around the add_dependencies command in the CMakeLists.txt file.
3.. Generate 2 standalone solutions through the cmake generator with included and with excluded add_dependencies in the CMakeLists.txt file.
I've used particulary [1.2]. When i need build and debug, then i uncheck the dependecy. By default, dependecy always checked, so there is no problem to miss timestamp build for a build server.
Note:
The timestamp header will be included in all projects you want to include that header (for example, through the add_library and add_executable) and you still can observe it in the IDE under a project item menu even if a project depends on the timestamp project indirectly. This is useful if you don't want to search for the timestamp project with the header to open it from there and want to open it from any project which has included that header.
So, in case of removing the timestamp header from the add_library or add_executable you won't have that opportunity.
I am trying to configure Bamboo builds. Bamboo provides ${bamboo.buildNumber} as a special variable. However this variable is just simple auto increment integer. When I am using this in build, I have to use it as 1.0.${bamboo.buildNumber}. It would generate builds with numbers 1.0.1, 1.0.2 etc.
However, I would like to generate build with format 1.0.0.$(Date:yyMMdd)$(Date:HHmm) similar to TFS build definitions. It should generate builds with numbers like 1.0.0.170210.0510 or 2.10.0.160210.0510.
I can very well write batch file or Powershell to do this, however, if there is already an option available, I would like to use it.
use bamboo.buildTimeStamp variable
My goal is to create build definitions within Visual Studio Team Services for both test and production environments. I need to update 2 variables in my code which determine which database and which blob storage the environment uses. Up till now, I've juggled this value in a Resource variable, and pulled that value in code from My.Resources.DB for a library, and Microsoft.Azure.CloudConfigurationManager.GetSetting("DatabaseConnectionString") for an Azure worker role. However, changing 4 variables every time I do a release is getting tiring.
I see a lot of posts that get close to what I want, but they're geared towards C#. For reasons beyond my influence, this project is written in VB.NET. It seems I have 2 options. First, I could call the MSBuild process with a couple of defined properties, passing them to the .metaproj build file, but I don't know how to get them to be used in VB code. That's preferable, but, at this point, I'm starting to doubt that this is possible.
I've been able to set some pre-processor constants, to be recognized in #If-#Else directives.
#If DEBUG = True Then
BarStaticItemVersion.Caption = String.Format("Version: {0}", "1.18.0.xxx")
#Else
BarStaticItemVersion.Caption = String.Format("Version: {0}", "1.18.0.133")
#End If
msbuild CalbertNG.sln.metaproj /t:Rebuild /p:DefineConstants="DEBUG=False"
This seems to work, though I need to Rebuild to change the value of that constant. Should I have to? Should Build be enough? Is this normal, or an indication that I don't have something set quite right?
I've seen other posts that talk about pre-processing the source files with some other builder, like Ant, but that seems like overkill. It feels like I'm close here. But I want to zoom out and ask, from a clean sheet of paper, if you're given 2 variables which need to change per environment, you're using VB.NET, and you want to incorporate those variable values in an automated VS Team Services build process upon code check-in, what's the best way to do it? (I want to define the variables in the VSTS panel, but this just passes them to my builder, so I have to know how to parse the call to MSBuild to make these useful.)
I can control picking between 2 static strings, now, via compiler directives, but I'd really like to reference the Build.BuildNumber that comes out of the MSBuild process to display to the user, and, if I can do that, I can just feed the variables for database and blob container via the same mechanism, and skip the pre-processor.
You've already found the way you can pass data from the MsBuild Arguments directly into the code. An alternative is to use the Condition Attribute in your project files to make certain property groups optional, it allows you to even include specific files conditionally. You can control conditions by passing in /p:ConditionalProperty=value on the MsBuild command. This at least ensures people use a set of values that make sense together.
The problem is that when MsBuild is running in Incremental mode it is likely to not process your changes (as you've noticed), the reason for this, is that the input files remain unchanged since the last build and are all older than the last generated output files.
To by-pass this behavior you'd normally create a separate solution configuration and override the output location for all projects to be unique for that configuration. Combined with setting the Compiler constants for that specific configuration you're ensured that when building that Configuration/Platform combination, incremental builds work as intended.
I do want to echo some of the comments from JerryM and Daniel Mann. Some items are better stored in else where or updated before you actually start the compile phase.
Possible solutions:
Store your configuration data in config files and use Configuration Transformation to generate the right config file base don the selected solution configuration. The process is explained on MSDN. To enable configuration transformation on all project types, you can use SlowCheetah.
Store your ocnfiguration data in the config files and use MsDeploy and specify a Parameters.xml file that matches the deploy package. It will perform the transformation on deploy time and will actually allow your solution to contain a standard config file you use at runtime, plus a publish profile which will post-process your configuration. You can use a SetParameters.xml file to override the variables at deploy time.
Create an installer project (such as through Wix) and merge the final configuration at install time (similar to the MsDeploy). You could even provide a UI which prompts for specific values (and can supply default values).
Use a CI server, like the new TFS/VSTS 2015 task based build engine and combine it with a task that can search&replace tokens, like the Replace Tokens task, Tokenization Task, Colin's ALM Corner Build and Release Tasks. And a whole bunch that specifically deal with versioning. Handling these things in the CI server also allows you to do a quick build locally at all times and do these relatively expensive steps on the build server (patching source code breaks incremental build in MsBuild, because there are always newer input files.
When talking specifically about versioning, there are a number of ways to set the AssemblyVersion and AssemblyFileVersion just before compile time, usually it involves overriding the AssemblyInfo.cs file before compilation. Your code could then use reflection to read the value at runtime. You can use the AssemblyInformationalversion to specify something like you do in the example above which contains .xxx or other text. It also ensures that the version displayed always reflects the information obtained when reading the file properties through Windows Explorer.
In a project where some targets are to be build and run on the build platform and other targets are to be build for a cross platform; what options do we have, when using cmake?
Currently I use CMAKE_BUILD_TYPE to define tool chain, build type and platform (for example -D CMAKE_BUILD_TYPE=arm_debug). In one place in the build, I switch tools (compilers, linke etc.), command line flags, libraries etc. according to the value of CMAKE_BUILD_TYPE. For every build type, I create a build directory.
This approach has it's drawbacks: multiple build directories and no easy way to depend one target from one build type on a target in an other build type (some kind of precompiler needed on the build platform by the build for the cross platform for example).
As currently every build targets has a single tool chain to be used I would love to associate a target with a target platform / tools set. This implies that some libraries have to be build for more than one target platform with different tool sets.
The 'one build type and platform per CMake run' limitation is fundamental and I would strongly advise against trying to work around it.
The proper solution here seems to me to split the build into several stages. In particular, for the scenario where a target from one build type depends on a target from another build type, you should not try to have those two targets in the same CMake project. Proper modularization is key here. Effective use of CMake's include command can help to avoid code duplication in the build scripts.
The big drawback of this approach is that the build process becomes more complex, as you now have several interdependent CMake projects that need to be built in a certain order with specific configurations. Although you already seem to be way beyond the point where you can build your whole system with a single command anyway. CMake can help manage this complexity with tools like ExternalProject, that allows you to build a CMake project from within another. Depending on your particular setup, a non-CMake layer written in your favorite scripting language might also be a viable alternative for ensuring that the different subprojects get built in the correct order.
The sad truth is though that complex build setups are hard to manage. CMake does a great job at providing a number of tools for tackling this complexity but it cannot magically make the problem easier. Most of the limitations that CMake imposes on its user are there for a reason, namely that things would be even harder if you tried to work without them.