From 8e48e266e9483a226c8167366dbe9077f24e8229 Mon Sep 17 00:00:00 2001 From: smaillet <25911635+smaillet@users.noreply.github.com> Date: Wed, 2 Jul 2025 14:12:23 -0700 Subject: [PATCH 1/2] Minor updates * Doc comment updates/clarifications * Moved GetOrdering to an extension method for IFormatProvider. * Renamed test namespace for consistency --- .../FileVersionQuadTests.cs | 2 +- .../ParsedBuildVersionXmlTests.cs | 2 +- .../PrereleaseVersionTests.cs | 2 +- .../AlphaNumericOrdering.cs | 2 +- src/Ubiquity.NET.Versioning/CSemVer.cs | 2 ++ src/Ubiquity.NET.Versioning/CSemVerCI.cs | 2 ++ .../FormatProviderExtensions.cs | 7 +++++ src/Ubiquity.NET.Versioning/PackageReadMe.md | 30 +++++++++++-------- src/Ubiquity.NET.Versioning/SemVer.cs | 7 +---- 9 files changed, 34 insertions(+), 22 deletions(-) diff --git a/src/Ubiquity.NET.Versioning.UT/FileVersionQuadTests.cs b/src/Ubiquity.NET.Versioning.UT/FileVersionQuadTests.cs index b8be869..f0fd979 100644 --- a/src/Ubiquity.NET.Versioning.UT/FileVersionQuadTests.cs +++ b/src/Ubiquity.NET.Versioning.UT/FileVersionQuadTests.cs @@ -8,7 +8,7 @@ using Microsoft.VisualStudio.TestTools.UnitTesting; -namespace Ubiquity.NET.Versioning.Tests +namespace Ubiquity.NET.Versioning.UT { [TestClass] public class FileVersionQuadTests diff --git a/src/Ubiquity.NET.Versioning.UT/ParsedBuildVersionXmlTests.cs b/src/Ubiquity.NET.Versioning.UT/ParsedBuildVersionXmlTests.cs index 03f8f29..40fdffd 100644 --- a/src/Ubiquity.NET.Versioning.UT/ParsedBuildVersionXmlTests.cs +++ b/src/Ubiquity.NET.Versioning.UT/ParsedBuildVersionXmlTests.cs @@ -10,7 +10,7 @@ using Microsoft.VisualStudio.TestTools.UnitTesting; -namespace Ubiquity.NET.Versioning.Tests +namespace Ubiquity.NET.Versioning.UT { [TestClass] public class ParsedBuildVersionXmlTests diff --git a/src/Ubiquity.NET.Versioning.UT/PrereleaseVersionTests.cs b/src/Ubiquity.NET.Versioning.UT/PrereleaseVersionTests.cs index 957f92d..ed3d2dc 100644 --- a/src/Ubiquity.NET.Versioning.UT/PrereleaseVersionTests.cs +++ b/src/Ubiquity.NET.Versioning.UT/PrereleaseVersionTests.cs @@ -9,7 +9,7 @@ using Microsoft.VisualStudio.TestTools.UnitTesting; -namespace Ubiquity.NET.Versioning.Tests +namespace Ubiquity.NET.Versioning.UT { [TestClass] public class PrereleaseVersionTests diff --git a/src/Ubiquity.NET.Versioning/AlphaNumericOrdering.cs b/src/Ubiquity.NET.Versioning/AlphaNumericOrdering.cs index 1f91b78..87e8523 100644 --- a/src/Ubiquity.NET.Versioning/AlphaNumericOrdering.cs +++ b/src/Ubiquity.NET.Versioning/AlphaNumericOrdering.cs @@ -9,7 +9,7 @@ namespace Ubiquity.NET.Versioning /// Identifies the sort ordering expected for a given version public enum AlphaNumericOrdering { - /// Indicates no sort ordering + /// Indicates an invalid sort ordering /// /// This value is the default for this type and is ALWAYS invalid. /// diff --git a/src/Ubiquity.NET.Versioning/CSemVer.cs b/src/Ubiquity.NET.Versioning/CSemVer.cs index 1b299fc..13f7a7e 100644 --- a/src/Ubiquity.NET.Versioning/CSemVer.cs +++ b/src/Ubiquity.NET.Versioning/CSemVer.cs @@ -261,6 +261,7 @@ public static CSemVer From( string buildVersionXmlPath, ImmutableArray b /// public static new CSemVer Parse( string s, IFormatProvider? provider ) { + // Throw if provider isn't one that is ignorable. provider.ThrowIfCaseSensitive(); return TryParse( s, out CSemVer? retVal, out Exception? ex ) ? retVal : throw ex; } @@ -271,6 +272,7 @@ public static CSemVer From( string buildVersionXmlPath, ImmutableArray b /// public static bool TryParse( [NotNullWhen( true )] string? s, IFormatProvider? provider, [MaybeNullWhen( false )] out CSemVer result ) { + // Throw if provider isn't one that is ignorable. provider.ThrowIfCaseSensitive(); return TryParse( s, out result, out _ ); } diff --git a/src/Ubiquity.NET.Versioning/CSemVerCI.cs b/src/Ubiquity.NET.Versioning/CSemVerCI.cs index 746dc5e..3694d26 100644 --- a/src/Ubiquity.NET.Versioning/CSemVerCI.cs +++ b/src/Ubiquity.NET.Versioning/CSemVerCI.cs @@ -177,6 +177,7 @@ public static bool TryFrom( /// public static new CSemVerCI Parse( string s, IFormatProvider? provider ) { + // Throw if provider isn't one that is ignorable. provider.ThrowIfCaseSensitive(); return TryParse(s, out CSemVerCI? retVal, out Exception? ex) ? retVal : throw ex; } @@ -184,6 +185,7 @@ public static bool TryFrom( /// public static bool TryParse( [NotNullWhen( true )] string? s, IFormatProvider? provider, [MaybeNullWhen( false )] out CSemVerCI result ) { + // Throw if provider isn't one that is ignorable. provider.ThrowIfCaseSensitive(); return TryParse(s, out result, out _); } diff --git a/src/Ubiquity.NET.Versioning/FormatProviderExtensions.cs b/src/Ubiquity.NET.Versioning/FormatProviderExtensions.cs index 4cfaa86..a1fd8a4 100644 --- a/src/Ubiquity.NET.Versioning/FormatProviderExtensions.cs +++ b/src/Ubiquity.NET.Versioning/FormatProviderExtensions.cs @@ -22,5 +22,12 @@ public static void ThrowIfCaseSensitive(this IFormatProvider? provider, [CallerA } } } + + public static AlphaNumericOrdering GetOrdering(this IFormatProvider provider) + { + ArgumentNullException.ThrowIfNull(provider); + + return (AlphaNumericOrdering?)provider.GetFormat(typeof(AlphaNumericOrdering)) ?? AlphaNumericOrdering.None; + } } } diff --git a/src/Ubiquity.NET.Versioning/PackageReadMe.md b/src/Ubiquity.NET.Versioning/PackageReadMe.md index d226235..d220eab 100644 --- a/src/Ubiquity.NET.Versioning/PackageReadMe.md +++ b/src/Ubiquity.NET.Versioning/PackageReadMe.md @@ -10,15 +10,17 @@ versioning at runtime.) ## Example ``` C# -var epectedMinimum = new CSemVer(20, 1, 5, "alpha"); -var actual = CSemVer.From(SomeAPIToRetrieveAVersionAsUInt64()); +var epectedMinimum = new CSemVer(20, 1, 5, "alpha"); // Usually static +//... + +var versionQuad = new FileVersionQuad(SomeAPIToRetrieveAVersionAsUInt64()); +SemVer actual = versionQuad.ToSemVer(); if (actual < expectedMinimum) { // Uh-OH! "older" version! } // Good to go... - ``` ## Formatting @@ -30,20 +32,24 @@ The library contains support for parsing of strings based on the rules of a SemVer, CSemVer, and CSemVer-CI ## Ordering -The types all support `IComparable`[1](#footnote_1) and properly handle correct sort ordering of the -versions according to the rules of SemVer (Which, CSemVer and CSemVer-CI follow) +The types all support `IComparable`[1](#footnote_1) and properly handle correct +sort ordering of the versions according to the rules of SemVer (Which, CSemVer and CSemVer-CI +follow) >[!WARNING] -> The formal 'spec' for [CSemVer](https://csemver.org) remains mostly silent on the point of -> the short format. See this [known issue](https://github.com/CK-Build/csemver.org/issues/2). +> The formal 'spec' for [CSemVer](https://csemver.org) remains mostly silent on the point +> of the short format. See this [known issue](https://github.com/CK-Build/csemver.org/issues/2). > Since, the existence of that form was to support NuGet V2, which is now obsolete, this > library does not support the short form at all. (This choice keeps documentation clarity > [NOT SUPPORTED] and implementation simplicity) ------ -1 `SemVer` does NOT support `IComparable` as the spec is -not explicit on case sensitive comparison of AlphaNumeric Identifiers. Unfortunately, major -repositories using SemVer have chosen to use different comparisons. Thus, a consumer is required -to know a-priori if the version is compared insensitive or not. `IComparer` instances -are available for both cases via the static class `SemVerComparer`. +1Unfortunately, major repositories using SemVer have +chosen to use different comparisons. Thus, a consumer is required to know a-priori if the +version is compared insensitive or not. Thus all constructors accept an enum indicating +the sort ordering to use. Additional, parsing accepts an IFormatProvider, which should +provide an `AlphaNumeirvOrdering` value to specify the ordering. If none is provided, the +default is used. (SemVer uses CaseSensitive comparisons, CSemVer and CSemVerCI ALWAYS use +case insensitive) `IComparer` instances are available for cases where the versions +are from mixed sources and the application wishes to order the versions. diff --git a/src/Ubiquity.NET.Versioning/SemVer.cs b/src/Ubiquity.NET.Versioning/SemVer.cs index 1ba2884..e57a1d4 100644 --- a/src/Ubiquity.NET.Versioning/SemVer.cs +++ b/src/Ubiquity.NET.Versioning/SemVer.cs @@ -259,7 +259,7 @@ internal static bool TryParse( ArgumentNullException.ThrowIfNull( s ); provider ??= SemVerFormatProvider.CaseSensitive; - IResult parseResult = SemVerGrammar.SemanticVersion(GetOrdering(provider)).TryParse(s); + IResult parseResult = SemVerGrammar.SemanticVersion(provider.GetOrdering()).TryParse(s); if(parseResult.Failed(out ex)) { result = default; @@ -303,10 +303,5 @@ private static ImmutableArray ValidateElementsWithParser( return value.Value; } - - private static AlphaNumericOrdering GetOrdering(IFormatProvider? provider) - { - return (AlphaNumericOrdering?)provider?.GetFormat(typeof(AlphaNumericOrdering)) ?? AlphaNumericOrdering.None; - } } } From b75151cf392205dc88eba65ea5afeba9eb008d53 Mon Sep 17 00:00:00 2001 From: smaillet <25911635+smaillet@users.noreply.github.com> Date: Wed, 2 Jul 2025 14:39:40 -0700 Subject: [PATCH 2/2] minor comment add to re-trigger actions (hopefully) --- src/Ubiquity.NET.Versioning/AppContextSwitches.cs | 1 + 1 file changed, 1 insertion(+) diff --git a/src/Ubiquity.NET.Versioning/AppContextSwitches.cs b/src/Ubiquity.NET.Versioning/AppContextSwitches.cs index db215fa..67b6bb4 100644 --- a/src/Ubiquity.NET.Versioning/AppContextSwitches.cs +++ b/src/Ubiquity.NET.Versioning/AppContextSwitches.cs @@ -62,6 +62,7 @@ public static bool CSemVerCIOnlySupportsBuildMetaOnZeroTimedVersions set => AppContext.SetSwitch(CSemVerCIOnlySupportsBuildMetaOnZeroTimedVersionsName, value); } + // internal utility to read a switch and default to false if not found. private static bool GetSwitchValue(string name) { bool found = AppContext.TryGetSwitch(name, out bool currentVal);