Versioning Artifacts
Whenever a build produces artifacts, those should be identifiable with a unique version number. This avoids making wrong expectations about available features or fixed bugs, and allows for clear discussions between developers, QA team, and product users. The most common version approaches are are semantic versioning and calendar versioning.
Repository-based Versioning​
NUKE supports 4 different tools that help generating version numbers from your repository and its commits. Each of these tools comes with its own attribute that populates the field with the information calculated:
- GitVersion
- Nerdbank
- OctoVersion
- MinVer
Please refer to the GitVersion documentation for any questions.
nuke :add-package GitVersion.Tool
[GitVersion]
readonly GitVersion GitVersion;
Target Print => _ => _
.Executes(() =>
{
Log.Information("GitVersion = {Value}", GitVersion.MajorMinorPatch);
});
Please refer to the Nerdbank.GitVersioning documentation for any questions.
nuke :add-package Nerdbank.GitVersioning
[NerdbankGitVersioning]
readonly NerdbankGitVersioning NerdbankVersioning;
Target Print => _ => _
.Executes(() =>
{
Log.Information("NerdbankVersioning = {Value}", NerdbankVersioning.SimpleVersion);
});
Please refer to the OctoVersion documentation for any questions.
nuke :add-package Octopus.OctoVersion.Tool
[OctoVersion]
readonly OctoVersionInfo OctoVersionInfo;
Target Print => _ => _
.Executes(() =>
{
Log.Information("OctoVersionInfo = {Value}", OctoVersionInfo.MajorMinorPatch);
});
Please refer to the MinVer documentation for any questions.
nuke :add-package minver-cli
[MinVer]
readonly MinVer MinVer;
Target Print => _ => _
.Executes(() =>
{
Log.Information("MinVer = {Value}", MinVer.Version);
});
Note that when the versioning tool fails to calculate version numbers, a warning will be logged and the attributed field remains uninitialized. In that case, you can try executing the issued command manually or nuke --verbosity verbose
to reveal more detailed information. In most cases, the repository is either not initialized, has no commits, or is missing the tool-specific configuration file.
Dependency-based Versioning​
When your versioning is affected by external dependencies, NUKE provides another mechanism to load the latest version of those prior to build execution. Each attribute provides various properties to control which versions should be considered and how it should be transformed:
- NuGet Packages
- GitHub Releases
- MyGet Feeds
- Maven Packages
[LatestNuGetVersion(
packageId: "JetBrains.ReSharper.SDK",
IncludePrerelease = true)]
readonly NuGetVersion ReSharperVersion;
Target Print => _ => _
.Executes(() =>
{
Log.Information("ReSharperVersion = {Value}", ReSharperVersion);
});
[LatestGitHubRelease(
identifier: "JetBrains/gradle-intellij-plugin",
Pattern = @"v?(?<version>\d+\.\d+(?:\.\d+)?(?:\.\d+)?(?:-\w+)?)")] // default pattern
readonly string GradlePluginVersion;
Target Print => _ => _
.Executes(() =>
{
Log.Information("GradlePluginVersion = {Value}", GradlePluginVersion);
});
[LatestMyGetVersion(
feed: "rd-snapshots",
package: "rd-gen")]
readonly string RdGenVersion;
Target Print => _ => _
.Executes(() =>
{
Log.Information("RdGenVersion = {Value}", RdGenVersion);
});
[LatestMavenVersion(
repository: "plugins.gradle.org/m2",
groupId: "org.jetbrains.kotlin.jvm",
artifactId: "org.jetbrains.kotlin.jvm.gradle.plugin")]
readonly string KotlinJvmVersion;
Target Print => _ => _
.Executes(() =>
{
Log.Information("KotlinJvmVersion = {Value}", KotlinJvmVersion);
});
Related Resources​
You can learn more about different versioning aspects from the following resources:
- Why I don't start versions at 0.x any more by Jon Skeet
- Versioning, and how it makes our heads hurt by Jon Skeet