internal static CIReleaseInfo Create(Commit commit, CIBranchVersionMode ciVersionMode, string ciBuildName, StringBuilder errors, CommitVersionInfo info) { var actualBaseTag = info.PreviousMaxTag; ReleaseTagVersion ciBaseTag = actualBaseTag ?? ReleaseTagVersion.VeryFirstVersion; string ciBuildVersionNuGet = null, ciBuildVersion = null; // If there is no base release found, we fall back to ZeroTimedBased mode. if (ciVersionMode == CIBranchVersionMode.ZeroTimed || actualBaseTag == null) { DateTime timeRelease = commit.Committer.When.ToUniversalTime().UtcDateTime; ciBuildVersion = CreateSemVerZeroTimed(ciBuildName, timeRelease, actualBaseTag?.ToString()); ciBuildVersionNuGet = CreateNuGetZeroTimed(ciBuildName, timeRelease); } else { Debug.Assert(ciVersionMode == CIBranchVersionMode.LastReleaseBased && actualBaseTag != null); CIBuildDescriptor ci = new CIBuildDescriptor { BranchName = ciBuildName, BuildIndex = info.PreviousMaxCommitDepth }; if (!ci.IsValidForNuGetV2) { errors.AppendLine("Due to NuGet V2 limitation, the branch name must not be longer than 8 characters. "); errors.Append("Adds a VersionName attribute to the branch element in RepositoryInfo.xml with a shorter name: ") .AppendFormat(@"<Branch Name=""{0}"" VersionName=""{1}"" ... />.", ci.BranchName, ci.BranchName.Substring(0, 8)) .AppendLine(); } else { ciBuildVersion = actualBaseTag.ToString(ReleaseTagFormat.SemVer, ci); ciBuildVersionNuGet = actualBaseTag.ToString(ReleaseTagFormat.NuGetPackage, ci); } } Debug.Assert(ciBuildVersion == null || errors.Length == 0); return(ciBuildVersion != null ? new CIReleaseInfo(ciBaseTag, info.PreviousMaxCommitDepth, ciBuildVersion, ciBuildVersionNuGet) : null); }
internal static CIReleaseInfo Create( Commit commit, CIBranchVersionMode ciVersionMode, string ciBuildName, StringBuilder errors, BasicCommitInfo info) { var actualBaseTag = info?.MaxCommit.ThisTag; CSVersion ciBaseTag = actualBaseTag ?? CSVersion.VeryFirstVersion; SVersion ciBuildVersionNuGet = null, ciBuildVersion = null; // If there is no base release found, we fall back to ZeroTimedBased mode. if (ciVersionMode == CIBranchVersionMode.ZeroTimed || actualBaseTag == null) { DateTime timeRelease = commit.Committer.When.ToUniversalTime().UtcDateTime; string vS = CIBuildDescriptor.CreateSemVerZeroTimed(ciBuildName, timeRelease); string vN = CIBuildDescriptor.CreateShortFormZeroTimed(ciBuildName, timeRelease); if (actualBaseTag != null) { string buildMetaData = "+v" + actualBaseTag; vS += buildMetaData; vN += buildMetaData; } ciBuildVersion = SVersion.Parse(vS); ciBuildVersionNuGet = SVersion.Parse(vN, false); return(new CIReleaseInfo(ciBaseTag, 0, ciBuildVersion, ciBuildVersionNuGet, true)); } Debug.Assert(ciVersionMode == CIBranchVersionMode.LastReleaseBased && actualBaseTag != null); CIBuildDescriptor ci = new CIBuildDescriptor { BranchName = ciBuildName, BuildIndex = info.BelowDepth }; if (!ci.IsValidForShortForm) { errors.AppendLine("Due to ShortForm (NuGet V2 compliance) limitation, the branch name must not be longer than 8 characters. "); errors.Append("Adds a VersionName attribute to the branch element in RepositoryInfo.xml with a shorter name: ") .AppendLine() .Append($@"<Branch Name=""{ci.BranchName}"" VersionName=""{ci.BranchName.Substring( 0, 8 )}"" ... />.") .AppendLine(); } else { ciBuildVersion = SVersion.Parse(actualBaseTag.ToString(CSVersionFormat.Normalized, ci)); ciBuildVersionNuGet = SVersion.Parse(actualBaseTag.ToString(CSVersionFormat.NuGetPackage, ci), false); } Debug.Assert(ciBuildVersion == null || errors.Length == 0); return(ciBuildVersion != null ? new CIReleaseInfo(ciBaseTag, info.BelowDepth, ciBuildVersion, ciBuildVersionNuGet, false) : null); }
internal static CIReleaseInfo Create( Commit commit, CIBranchVersionMode ciVersionMode, string ciVersionName, StringBuilder errors, CommitVersionInfo info ) { var actualBaseTag = info.PreviousMaxTag; ReleaseTagVersion ciBaseTag = actualBaseTag ?? ReleaseTagVersion.VeryFirstVersion; string ciBuildVersionNuGet = null, ciBuildVersion = null; // If there is no base release found, we fall back to ZeroTimedBased mode. if( ciVersionMode == CIBranchVersionMode.ZeroTimed || actualBaseTag == null ) { string suffix = actualBaseTag != null ? '+' + actualBaseTag.ToString() : null; var name = string.Format( "0.0.0--ci-{0}.{1:yyyy-MM-ddTHH-mm-ss-ff}", ciVersionName, commit.Committer.When ); ciBuildVersion = name + suffix; TimeSpan delta200 = commit.Committer.When.ToUniversalTime() - new DateTime( 2015, 1, 1, 0, 0, 0, DateTimeKind.Utc ); Debug.Assert( Math.Log( 1000 * 366 * 24 * 60 * (long)60, 62 ) < 7, "Using Base62: 1000 years in seconds on 7 chars!" ); long second = (long)delta200.TotalSeconds; string b62 = ToBase62( second ); string ver = new string( '0', 7 - b62.Length ) + b62; ciBuildVersionNuGet = string.Format( "0.0.0-C{0}-{1}", ciVersionName, ver ); } else { Debug.Assert( ciVersionMode == CIBranchVersionMode.LastReleaseBased && actualBaseTag != null ); CIBuildDescriptor ci = new CIBuildDescriptor { BranchName = ciVersionName, BuildIndex = info.PreviousMaxCommitDepth }; if( !ci.IsValidForNuGetV2 ) { errors.AppendLine( "Due to NuGet V2 limitation, the branch name must not be longer than 8 characters. " ); errors.Append( "Adds a VersionName attribute to the branch element in RepositoryInfo.xml with a shorter name: " ) .AppendFormat( @"<Branch Name=""{0}"" VersionName=""{1}"" ... />.", ci.BranchName, ci.BranchName.Substring( 0, 8 ) ) .AppendLine(); } else { ciBuildVersion = actualBaseTag.ToString( ReleaseTagFormat.SemVer, ci ); ciBuildVersionNuGet = actualBaseTag.ToString( ReleaseTagFormat.NuGetPackage, ci ); } } Debug.Assert( ciBuildVersion == null || errors.Length == 0 ); return ciBuildVersion != null ? new CIReleaseInfo( ciBaseTag, info.PreviousMaxCommitDepth, ciBuildVersion, ciBuildVersionNuGet ) : null; }
internal static CIReleaseInfo Create( Commit commit, CIBranchVersionMode ciVersionMode, string ciBuildName, StringBuilder errors, CommitVersionInfo info ) { var actualBaseTag = info.PreviousMaxTag; ReleaseTagVersion ciBaseTag = actualBaseTag ?? ReleaseTagVersion.VeryFirstVersion; string ciBuildVersionNuGet = null, ciBuildVersion = null; // If there is no base release found, we fall back to ZeroTimedBased mode. if( ciVersionMode == CIBranchVersionMode.ZeroTimed || actualBaseTag == null ) { DateTime timeRelease = commit.Committer.When.ToUniversalTime().UtcDateTime; ciBuildVersion = CreateSemVerZeroTimed( ciBuildName, timeRelease, actualBaseTag?.ToString() ); ciBuildVersionNuGet = CreateNuGetZeroTimed( ciBuildName, timeRelease ); } else { Debug.Assert( ciVersionMode == CIBranchVersionMode.LastReleaseBased && actualBaseTag != null ); CIBuildDescriptor ci = new CIBuildDescriptor { BranchName = ciBuildName, BuildIndex = info.PreviousMaxCommitDepth }; if( !ci.IsValidForNuGetV2 ) { errors.AppendLine( "Due to NuGet V2 limitation, the branch name must not be longer than 8 characters. " ); errors.Append( "Adds a VersionName attribute to the branch element in RepositoryInfo.xml with a shorter name: " ) .AppendFormat( @"<Branch Name=""{0}"" VersionName=""{1}"" ... />.", ci.BranchName, ci.BranchName.Substring( 0, 8 ) ) .AppendLine(); } else { ciBuildVersion = actualBaseTag.ToString( ReleaseTagFormat.SemVer, ci ); ciBuildVersionNuGet = actualBaseTag.ToString( ReleaseTagFormat.NuGetPackage, ci ); } } Debug.Assert( ciBuildVersion == null || errors.Length == 0 ); return ciBuildVersion != null ? new CIReleaseInfo( ciBaseTag, info.PreviousMaxCommitDepth, ciBuildVersion, ciBuildVersionNuGet ) : null; }
/// <summary> /// Gets the string version in the given format. /// </summary> /// <param name="f">Format to use.</param> /// <param name="buildInfo">Not null to generate a post-release version.</param> /// <param name="usePreReleaseNameFromTag">True to use <see cref="PreReleaseNameFromTag"/> instead of standardized <see cref="PreReleaseName"/>.</param> /// <returns>Formated string (or <see cref="ParseErrorMessage"/> if any).</returns> public string ToString(ReleaseTagFormat f, CIBuildDescriptor buildInfo = null, bool usePreReleaseNameFromTag = false) { if (ParseErrorMessage != null) { return(ParseErrorMessage); } if (buildInfo != null && !buildInfo.IsValid) { throw new ArgumentException("buildInfo must be valid."); } if (f == ReleaseTagFormat.FileVersion) { return(ToStringFileVersion(buildInfo != null)); } string prName = usePreReleaseNameFromTag ? PreReleaseNameFromTag : PreReleaseName; switch (f) { case ReleaseTagFormat.NugetPackageV2: { // For NuGetV2, we are obliged to use the initial otherwise the special part for a pre release fix is too long for CI-Build LastReleasedBased. if (usePreReleaseNameFromTag) { throw new ArgumentException("ReleaseTagFormat.NugetPackageV2 can not use PreReleaseNameFromTag."); } prName = PreReleaseNameIdx >= 0 ? _standardNames[PreReleaseNameIdx][0].ToString() : String.Empty; string suffix = IsMarkedInvalid ? Marker : null; bool isCIBuild = buildInfo != null; if (isCIBuild && !buildInfo.IsValidForNuGetV2) { throw new ArgumentException("buildInfo must be valid for NuGetV2 format."); } if (isCIBuild) { suffix = buildInfo.ToStringForNuGetV2() + suffix; } if (IsPreRelease) { if (IsPreReleasePatch) { if (isCIBuild) { return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}{4:00}-{5:00}-{6}", Major, Minor, Patch, prName, PreReleaseNumber, PreReleasePatch, suffix)); } return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}{4:00}-{5:00}{6}", Major, Minor, Patch, prName, PreReleaseNumber, PreReleasePatch, suffix)); } if (PreReleaseNumber > 0) { if (isCIBuild) { return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}{4:00}-00-{5}", Major, Minor, Patch, prName, PreReleaseNumber, suffix)); } return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}{4:00}{5}", Major, Minor, Patch, prName, PreReleaseNumber, suffix)); } if (isCIBuild) { return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}00-00-{4}", Major, Minor, Patch, prName, suffix)); } return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}{4}", Major, Minor, Patch, prName, suffix)); } if (isCIBuild) { return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}-C{3}", Major, Minor, Patch + 1, suffix)); } return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}{3}", Major, Minor, Patch, suffix)); } case ReleaseTagFormat.SemVer: case ReleaseTagFormat.SemVerWithMarker: { string suffix = f == ReleaseTagFormat.SemVerWithMarker ? Marker : string.Empty; bool isCIBuild = buildInfo != null; if (isCIBuild) { suffix = buildInfo.ToString() + suffix; } if (IsPreRelease) { if (IsPreReleasePatch) { if (isCIBuild) { return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}.{4}.{5}.{6}", Major, Minor, Patch, prName, PreReleaseNumber, PreReleasePatch, suffix)); } return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}.{4}.{5}{6}", Major, Minor, Patch, prName, PreReleaseNumber, PreReleasePatch, suffix)); } if (PreReleaseNumber > 0) { if (isCIBuild) { return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}.{4}.0.{5}", Major, Minor, Patch, prName, PreReleaseNumber, suffix)); } return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}.{4}{5}", Major, Minor, Patch, prName, PreReleaseNumber, suffix)); } if (isCIBuild) { return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}.0.0.{4}", Major, Minor, Patch, prName, suffix)); } return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}{4}", Major, Minor, Patch, prName, suffix)); } if (isCIBuild) { return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}--{3}", Major, Minor, Patch + 1, suffix)); } return(string.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}{3}", Major, Minor, Patch, suffix)); } default: { Debug.Assert(f == ReleaseTagFormat.Normalized); if (IsPreRelease) { if (IsPreReleasePatch) { return(string.Format(CultureInfo.InvariantCulture, "v{0}.{1}.{2}-{3}.{4}.{5}{6}", Major, Minor, Patch, prName, PreReleaseNumber, PreReleasePatch, Marker)); } if (PreReleaseNumber > 0) { return(string.Format(CultureInfo.InvariantCulture, "v{0}.{1}.{2}-{3}.{4}{5}", Major, Minor, Patch, prName, PreReleaseNumber, Marker)); } return(string.Format(CultureInfo.InvariantCulture, "v{0}.{1}.{2}-{3}{4}", Major, Minor, Patch, prName, Marker)); } return(string.Format(CultureInfo.InvariantCulture, "v{0}.{1}.{2}{3}", Major, Minor, Patch, Marker)); } } }
/// <summary> /// Gets the string version in the given format. /// </summary> /// <param name="f">Format to use.</param> /// <param name="buildInfo">Not null to generate a post-release version.</param> /// <param name="usePreReleaseNameFromTag">True to use <see cref="PreReleaseNameFromTag"/> instead of standardized <see cref="PreReleaseName"/>.</param> /// <returns>Formated string (or <see cref="ParseErrorMessage"/> if any).</returns> public string ToString( ReleaseTagFormat f, CIBuildDescriptor buildInfo = null, bool usePreReleaseNameFromTag = false ) { if( ParseErrorMessage != null ) return ParseErrorMessage; if( buildInfo != null && !buildInfo.IsValid ) throw new ArgumentException( "buildInfo must be valid." ); if( f == ReleaseTagFormat.FileVersion ) { return ToStringFileVersion( buildInfo != null ); } string prName = usePreReleaseNameFromTag ? PreReleaseNameFromTag : PreReleaseName; switch( f ) { case ReleaseTagFormat.NugetPackageV2: { // For NuGetV2, we are obliged to use the initial otherwise the special part for a pre release fix is too long for CI-Build LastReleasedBased. if( usePreReleaseNameFromTag ) throw new ArgumentException( "ReleaseTagFormat.NugetPackageV2 can not use PreReleaseNameFromTag." ); prName = PreReleaseNameIdx >= 0 ? _standardNames[PreReleaseNameIdx][0].ToString() : String.Empty; string suffix = IsMarkedInvalid ? Marker : null; bool isCIBuild = buildInfo != null; if( isCIBuild && !buildInfo.IsValidForNuGetV2 ) throw new ArgumentException( "buildInfo must be valid for NuGetV2 format." ); if( isCIBuild ) { suffix = buildInfo.ToStringForNuGetV2() + suffix; } if( IsPreRelease ) { if( IsPreReleasePatch ) { if( isCIBuild ) { return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}{4:00}-{5:00}-{6}", Major, Minor, Patch, prName, PreReleaseNumber, PreReleasePatch, suffix ); } return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}{4:00}-{5:00}{6}", Major, Minor, Patch, prName, PreReleaseNumber, PreReleasePatch, suffix ); } if( PreReleaseNumber > 0 ) { if( isCIBuild ) { return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}{4:00}-00-{5}", Major, Minor, Patch, prName, PreReleaseNumber, suffix ); } return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}{4:00}{5}", Major, Minor, Patch, prName, PreReleaseNumber, suffix ); } if( isCIBuild ) { return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}00-00-{4}", Major, Minor, Patch, prName, suffix ); } return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}{4}", Major, Minor, Patch, prName, suffix ); } if( isCIBuild ) { return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}-C{3}", Major, Minor, Patch+1, suffix ); } return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}{3}", Major, Minor, Patch, suffix ); } case ReleaseTagFormat.SemVer: case ReleaseTagFormat.SemVerWithMarker: { string suffix = f == ReleaseTagFormat.SemVerWithMarker ? Marker : string.Empty; bool isCIBuild = buildInfo != null; if( isCIBuild ) { suffix = buildInfo.ToString() + suffix; } if( IsPreRelease ) { if( IsPreReleasePatch ) { if( isCIBuild ) { return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}.{4}.{5}.{6}", Major, Minor, Patch, prName, PreReleaseNumber, PreReleasePatch, suffix ); } return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}.{4}.{5}{6}", Major, Minor, Patch, prName, PreReleaseNumber, PreReleasePatch, suffix ); } if( PreReleaseNumber > 0 ) { if( isCIBuild ) { return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}.{4}.0.{5}", Major, Minor, Patch, prName, PreReleaseNumber, suffix ); } return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}.{4}{5}", Major, Minor, Patch, prName, PreReleaseNumber, suffix ); } if( isCIBuild ) { return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}.0.0.{4}", Major, Minor, Patch, prName, suffix ); } return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}-{3}{4}", Major, Minor, Patch, prName, suffix ); } if( isCIBuild ) { return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}--{3}", Major, Minor, Patch+1, suffix ); } return string.Format( CultureInfo.InvariantCulture, "{0}.{1}.{2}{3}", Major, Minor, Patch, suffix ); } default: { Debug.Assert( f == ReleaseTagFormat.Normalized ); if( IsPreRelease ) { if( IsPreReleasePatch ) { return string.Format( CultureInfo.InvariantCulture, "v{0}.{1}.{2}-{3}.{4}.{5}{6}", Major, Minor, Patch, prName, PreReleaseNumber, PreReleasePatch, Marker ); } if( PreReleaseNumber > 0 ) { return string.Format( CultureInfo.InvariantCulture, "v{0}.{1}.{2}-{3}.{4}{5}", Major, Minor, Patch, prName, PreReleaseNumber, Marker ); } return string.Format( CultureInfo.InvariantCulture, "v{0}.{1}.{2}-{3}{4}", Major, Minor, Patch, prName, Marker ); } return string.Format( CultureInfo.InvariantCulture, "v{0}.{1}.{2}{3}", Major, Minor, Patch, Marker ); } } }