Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
Use git tag information to version nuget packages with FAKE scripts
open Fake
open Fake.Git
module GitFlowVersioning =
// ----------------------------------------------
// START: Version from git tag
// ----------------------------------------------
type ReleaseType = Release | Beta | Alpha | ReleaseCandidate
/// Get the SHA1 for the last available tag or None, if not tags set in repository
let getShaFromLastTag =
let gitLastTagShaCommand = "rev-list --tags --max-count=1"
let ok,msg,error = runGitCommand "" gitLastTagShaCommand
if ok then Some msg.[0] else None
/// Get the tag name for the given SHA1 commit or None, if no tag for this commit
let getTagForCommit sha =
let gitLastTagCommand = sprintf "describe --tag %s" sha
let ok,msg,error = runGitCommand "" gitLastTagCommand
if ok then Some (msg |> Seq.head) else None
/// Get version from the last tag in git or "0.0.0" version as fallback
let getLastTag prefix =
let fallbackVersion = "0.0.0"
let tagVersion =
match getShaFromLastTag with
| Some s ->
match getTagForCommit s with
| Some ss -> ss
| None _ -> prefix + fallbackVersion
| None _ -> prefix + fallbackVersion
let pattern =
if isNullOrEmpty prefix then "^" else sprintf "(?<=^%s){1}" prefix
let pattern = sprintf "%s%s" pattern "(\d+\.\d+){1}(\.\d+){0,2}$"
let versionRegex = System.Text.RegularExpressions.Regex(pattern)
match versionRegex.Match tagVersion with
| s when s.Success -> SemVerHelper.parse s.Value
| _ -> SemVerHelper.parse fallbackVersion
/// Release state
let getReleaseState =
let currentBranch = environVarOrDefault "CI_CURRENT_BRANCH" (Git.Information.getBranchName "")
match currentBranch with
| "master" -> Release
| "develop" -> Beta
| s when startsWith s "hotfix/" -> ReleaseCandidate
| s when startsWith s "release/" -> ReleaseCandidate
| _ -> Alpha
/// Get the version for assembly (+1 on patch level, if not on master)
let getAssemblyVersion prefix buildCounter =
let version = getLastTag prefix
let patch =
match getReleaseState with
| Release -> version.Patch
| _ -> version.Patch + 1
sprintf "%d.%d.%d.%s" version.Major version.Minor patch buildCounter
/// Get the version for nuget package (+1 on patch level, if not on master)
let getNugetVersion prefix buildCounter =
let version = getLastTag prefix
let releaseState = getReleaseState
let patch =
match releaseState with
| Release -> version.Patch
| _ -> version.Patch + 1
match releaseState with
| Release -> sprintf "%d.%d.%d" version.Major version.Minor patch
| s -> sprintf "%d.%d.%d-%A%s" version.Major version.Minor patch s buildCounter
/// TRUE: stable realease
let isStableRelease =
match getReleaseState with
| Release -> true
| _ -> false
// ----------------------------------------------
// END: Version from git tag
// ----------------------------------------------
@WebDucer

This comment has been minimized.

Copy link
Owner Author

commented Apr 30, 2016

Usefull for working on packages with git-flow branching model.

With CI_CURRENT_BRANCH environment variable you can set the current branch, if your CI server only support headless checkout (like GitLab CI do).

Examples

X - Build counter from CI system

  • Tag: 0.1 on developer branch
    • getAssemblyVersion: 0.1.1.X
    • getNugetVersion: 0.1.1-BetaX
  • Tag: 0.2 on master branch
    • getAssemblyVersion: 0.2.0.X
    • getNugetVersion: 0.2.0
  • Tag: 0.3.7 on feature branch
    • getAssemblyVersion: 0.3.8.X
    • getNugetVersion: 0.3.8-AlphaX
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.