diff --git a/src/Microsoft.DotNet.Build.Tasks.Packaging/src/GenerateRuntimeGraph.cs b/src/Microsoft.DotNet.Build.Tasks.Packaging/src/GenerateRuntimeGraph.cs index f40decc0551..c7b40ddf1a7 100644 --- a/src/Microsoft.DotNet.Build.Tasks.Packaging/src/GenerateRuntimeGraph.cs +++ b/src/Microsoft.DotNet.Build.Tasks.Packaging/src/GenerateRuntimeGraph.cs @@ -309,6 +309,12 @@ private void AddInferredRuntimeIdentifiers(ICollection runtimeGrou continue; } + if (!rid.HasVersion()) + { + closestGroup = candidate; + continue; + } + foreach(var version in candidate.Versions) { if (closestVersion == null || @@ -344,7 +350,7 @@ private void AddInferredRuntimeIdentifiers(ICollection runtimeGrou candidateRuntimeGroups.Add(runtimeGroup); } - else if (closestVersion != rid.Version) + else if (rid.HasVersion() && closestVersion != rid.Version) { closestGroup.Versions.Add(rid.Version); } diff --git a/src/Microsoft.DotNet.Build.Tasks.Packaging/src/RuntimeVersion.cs b/src/Microsoft.DotNet.Build.Tasks.Packaging/src/RuntimeVersion.cs index 977ba6800b2..66b44439121 100644 --- a/src/Microsoft.DotNet.Build.Tasks.Packaging/src/RuntimeVersion.cs +++ b/src/Microsoft.DotNet.Build.Tasks.Packaging/src/RuntimeVersion.cs @@ -50,7 +50,12 @@ public int CompareTo(object obj) public int CompareTo(RuntimeVersion other) { - int versionResult = version.CompareTo(other.version); + if (other == null) + { + return 1; + } + + int versionResult = version.CompareTo(other?.version); if (versionResult == 0) { @@ -73,7 +78,8 @@ public int CompareTo(RuntimeVersion other) public bool Equals(RuntimeVersion other) { return object.ReferenceEquals(other, this) || - versionString.Equals(other.versionString, StringComparison.Ordinal); + (other != null && + versionString.Equals(other.versionString, StringComparison.Ordinal)); } public override bool Equals(object obj) diff --git a/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/GenerateRuntimeGraphTests.CanInferNewArchitecture.runtime.json b/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/GenerateRuntimeGraphTests.CanInferNewArchitecture.runtime.json new file mode 100644 index 00000000000..852e12e2079 --- /dev/null +++ b/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/GenerateRuntimeGraphTests.CanInferNewArchitecture.runtime.json @@ -0,0 +1,1107 @@ +{ + "runtimes": { + "any": { + "#import": [] + }, + "aot": { + "#import": [] + }, + "centos": { + "#import": [ + "rhel" + ] + }, + "centos-arm64": { + "#import": [ + "centos", + "rhel-arm64" + ] + }, + "centos-x64": { + "#import": [ + "centos", + "rhel-x64" + ] + }, + "centos.7": { + "#import": [ + "centos", + "rhel.7" + ] + }, + "centos.7-x64": { + "#import": [ + "centos.7", + "centos-x64", + "rhel.7-x64" + ] + }, + "centos.8": { + "#import": [ + "centos", + "rhel.8" + ] + }, + "centos.8-arm64": { + "#import": [ + "centos.8", + "centos-arm64", + "rhel.8-arm64" + ] + }, + "centos.8-x64": { + "#import": [ + "centos.8", + "centos-x64", + "rhel.8-x64" + ] + }, + "centos.9": { + "#import": [ + "centos", + "rhel.9" + ] + }, + "centos.9-arm64": { + "#import": [ + "centos.9", + "centos-arm64", + "rhel.9-arm64" + ] + }, + "centos.9-x64": { + "#import": [ + "centos.9", + "centos-x64", + "rhel.9-x64" + ] + }, + "debian": { + "#import": [ + "linux" + ] + }, + "debian-arm": { + "#import": [ + "debian", + "linux-arm" + ] + }, + "debian-arm64": { + "#import": [ + "debian", + "linux-arm64" + ] + }, + "debian-armel": { + "#import": [ + "debian", + "linux-armel" + ] + }, + "debian-x64": { + "#import": [ + "debian", + "linux-x64" + ] + }, + "debian-x86": { + "#import": [ + "debian", + "linux-x86" + ] + }, + "debian.10": { + "#import": [ + "debian" + ] + }, + "debian.10-arm": { + "#import": [ + "debian.10", + "debian-arm" + ] + }, + "debian.10-arm64": { + "#import": [ + "debian.10", + "debian-arm64" + ] + }, + "debian.10-armel": { + "#import": [ + "debian.10", + "debian-armel" + ] + }, + "debian.10-x64": { + "#import": [ + "debian.10", + "debian-x64" + ] + }, + "debian.10-x86": { + "#import": [ + "debian.10", + "debian-x86" + ] + }, + "debian.8": { + "#import": [ + "debian" + ] + }, + "debian.8-arm": { + "#import": [ + "debian.8", + "debian-arm" + ] + }, + "debian.8-arm64": { + "#import": [ + "debian.8", + "debian-arm64" + ] + }, + "debian.8-armel": { + "#import": [ + "debian.8", + "debian-armel" + ] + }, + "debian.8-x64": { + "#import": [ + "debian.8", + "debian-x64" + ] + }, + "debian.8-x86": { + "#import": [ + "debian.8", + "debian-x86" + ] + }, + "debian.9": { + "#import": [ + "debian" + ] + }, + "debian.9-arm": { + "#import": [ + "debian.9", + "debian-arm" + ] + }, + "debian.9-arm64": { + "#import": [ + "debian.9", + "debian-arm64" + ] + }, + "debian.9-armel": { + "#import": [ + "debian.9", + "debian-armel" + ] + }, + "debian.9-x64": { + "#import": [ + "debian.9", + "debian-x64" + ] + }, + "debian.9-x86": { + "#import": [ + "debian.9", + "debian-x86" + ] + }, + "linux": { + "#import": [ + "unix" + ] + }, + "linux-arm": { + "#import": [ + "linux", + "unix-arm" + ] + }, + "linux-arm64": { + "#import": [ + "linux", + "unix-arm64" + ] + }, + "linux-armel": { + "#import": [ + "linux", + "unix-armel" + ] + }, + "linux-mips64": { + "#import": [ + "linux", + "unix-mips64" + ] + }, + "linux-x64": { + "#import": [ + "linux", + "unix-x64" + ] + }, + "linux-x86": { + "#import": [ + "linux", + "unix-x86" + ] + }, + "osx": { + "#import": [ + "unix" + ] + }, + "osx-arm64": { + "#import": [ + "osx", + "unix-arm64" + ] + }, + "osx-x64": { + "#import": [ + "osx", + "unix-x64" + ] + }, + "osx.10.10": { + "#import": [ + "osx" + ] + }, + "osx.10.10-arm64": { + "#import": [ + "osx.10.10", + "osx-arm64" + ] + }, + "osx.10.10-x64": { + "#import": [ + "osx.10.10", + "osx-x64" + ] + }, + "osx.10.11": { + "#import": [ + "osx.10.10" + ] + }, + "osx.10.11-arm64": { + "#import": [ + "osx.10.11", + "osx.10.10-arm64" + ] + }, + "osx.10.11-x64": { + "#import": [ + "osx.10.11", + "osx.10.10-x64" + ] + }, + "osx.10.12": { + "#import": [ + "osx.10.11" + ] + }, + "osx.10.12-arm64": { + "#import": [ + "osx.10.12", + "osx.10.11-arm64" + ] + }, + "osx.10.12-x64": { + "#import": [ + "osx.10.12", + "osx.10.11-x64" + ] + }, + "osx.10.13": { + "#import": [ + "osx.10.12" + ] + }, + "osx.10.13-arm64": { + "#import": [ + "osx.10.13", + "osx.10.12-arm64" + ] + }, + "osx.10.13-x64": { + "#import": [ + "osx.10.13", + "osx.10.12-x64" + ] + }, + "osx.10.14": { + "#import": [ + "osx.10.13" + ] + }, + "osx.10.14-arm64": { + "#import": [ + "osx.10.14", + "osx.10.13-arm64" + ] + }, + "osx.10.14-x64": { + "#import": [ + "osx.10.14", + "osx.10.13-x64" + ] + }, + "osx.10.15": { + "#import": [ + "osx.10.14" + ] + }, + "osx.10.15-arm64": { + "#import": [ + "osx.10.15", + "osx.10.14-arm64" + ] + }, + "osx.10.15-x64": { + "#import": [ + "osx.10.15", + "osx.10.14-x64" + ] + }, + "osx.10.16": { + "#import": [ + "osx.10.15" + ] + }, + "osx.10.16-arm64": { + "#import": [ + "osx.10.16", + "osx.10.15-arm64" + ] + }, + "osx.10.16-x64": { + "#import": [ + "osx.10.16", + "osx.10.15-x64" + ] + }, + "osx.11.0": { + "#import": [ + "osx.10.16" + ] + }, + "osx.11.0-arm64": { + "#import": [ + "osx.11.0", + "osx.10.16-arm64" + ] + }, + "osx.11.0-x64": { + "#import": [ + "osx.11.0", + "osx.10.16-x64" + ] + }, + "rhel": { + "#import": [ + "linux" + ] + }, + "rhel-arm64": { + "#import": [ + "rhel", + "linux-arm64" + ] + }, + "rhel-x64": { + "#import": [ + "rhel", + "linux-x64" + ] + }, + "rhel.6": { + "#import": [ + "rhel" + ] + }, + "rhel.6-x64": { + "#import": [ + "rhel.6", + "rhel-x64" + ] + }, + "rhel.7": { + "#import": [ + "rhel" + ] + }, + "rhel.7-x64": { + "#import": [ + "rhel.7", + "rhel-x64" + ] + }, + "rhel.7.0": { + "#import": [ + "rhel.7" + ] + }, + "rhel.7.0-x64": { + "#import": [ + "rhel.7.0", + "rhel.7-x64" + ] + }, + "rhel.7.1": { + "#import": [ + "rhel.7.0" + ] + }, + "rhel.7.1-x64": { + "#import": [ + "rhel.7.1", + "rhel.7.0-x64" + ] + }, + "rhel.7.2": { + "#import": [ + "rhel.7.1" + ] + }, + "rhel.7.2-x64": { + "#import": [ + "rhel.7.2", + "rhel.7.1-x64" + ] + }, + "rhel.7.3": { + "#import": [ + "rhel.7.2" + ] + }, + "rhel.7.3-x64": { + "#import": [ + "rhel.7.3", + "rhel.7.2-x64" + ] + }, + "rhel.7.4": { + "#import": [ + "rhel.7.3" + ] + }, + "rhel.7.4-x64": { + "#import": [ + "rhel.7.4", + "rhel.7.3-x64" + ] + }, + "rhel.7.5": { + "#import": [ + "rhel.7.4" + ] + }, + "rhel.7.5-x64": { + "#import": [ + "rhel.7.5", + "rhel.7.4-x64" + ] + }, + "rhel.7.6": { + "#import": [ + "rhel.7.5" + ] + }, + "rhel.7.6-x64": { + "#import": [ + "rhel.7.6", + "rhel.7.5-x64" + ] + }, + "rhel.8": { + "#import": [ + "rhel" + ] + }, + "rhel.8-arm64": { + "#import": [ + "rhel.8", + "rhel-arm64" + ] + }, + "rhel.8-x64": { + "#import": [ + "rhel.8", + "rhel-x64" + ] + }, + "rhel.8.0": { + "#import": [ + "rhel.8" + ] + }, + "rhel.8.0-arm64": { + "#import": [ + "rhel.8.0", + "rhel.8-arm64" + ] + }, + "rhel.8.0-x64": { + "#import": [ + "rhel.8.0", + "rhel.8-x64" + ] + }, + "rhel.8.1": { + "#import": [ + "rhel.8.0" + ] + }, + "rhel.8.1-arm64": { + "#import": [ + "rhel.8.1", + "rhel.8.0-arm64" + ] + }, + "rhel.8.1-x64": { + "#import": [ + "rhel.8.1", + "rhel.8.0-x64" + ] + }, + "rhel.9": { + "#import": [ + "rhel" + ] + }, + "rhel.9-arm64": { + "#import": [ + "rhel.9", + "rhel-arm64" + ] + }, + "rhel.9-x64": { + "#import": [ + "rhel.9", + "rhel-x64" + ] + }, + "ubuntu": { + "#import": [ + "debian" + ] + }, + "ubuntu-arm": { + "#import": [ + "ubuntu", + "debian-arm" + ] + }, + "ubuntu-x64": { + "#import": [ + "ubuntu", + "debian-x64" + ] + }, + "ubuntu-x86": { + "#import": [ + "ubuntu", + "debian-x86" + ] + }, + "ubuntu.14.04": { + "#import": [ + "ubuntu" + ] + }, + "ubuntu.14.04-arm": { + "#import": [ + "ubuntu.14.04", + "ubuntu-arm" + ] + }, + "ubuntu.14.04-x64": { + "#import": [ + "ubuntu.14.04", + "ubuntu-x64" + ] + }, + "ubuntu.14.04-x86": { + "#import": [ + "ubuntu.14.04", + "ubuntu-x86" + ] + }, + "ubuntu.14.10": { + "#import": [ + "ubuntu" + ] + }, + "ubuntu.14.10-arm": { + "#import": [ + "ubuntu.14.10", + "ubuntu-arm" + ] + }, + "ubuntu.14.10-x64": { + "#import": [ + "ubuntu.14.10", + "ubuntu-x64" + ] + }, + "ubuntu.14.10-x86": { + "#import": [ + "ubuntu.14.10", + "ubuntu-x86" + ] + }, + "ubuntu.15.04": { + "#import": [ + "ubuntu" + ] + }, + "ubuntu.15.04-arm": { + "#import": [ + "ubuntu.15.04", + "ubuntu-arm" + ] + }, + "ubuntu.15.04-x64": { + "#import": [ + "ubuntu.15.04", + "ubuntu-x64" + ] + }, + "ubuntu.15.04-x86": { + "#import": [ + "ubuntu.15.04", + "ubuntu-x86" + ] + }, + "ubuntu.15.10": { + "#import": [ + "ubuntu" + ] + }, + "ubuntu.15.10-arm": { + "#import": [ + "ubuntu.15.10", + "ubuntu-arm" + ] + }, + "ubuntu.15.10-x64": { + "#import": [ + "ubuntu.15.10", + "ubuntu-x64" + ] + }, + "ubuntu.15.10-x86": { + "#import": [ + "ubuntu.15.10", + "ubuntu-x86" + ] + }, + "unix": { + "#import": [ + "any" + ] + }, + "unix-arm": { + "#import": [ + "unix" + ] + }, + "unix-arm64": { + "#import": [ + "unix" + ] + }, + "unix-armel": { + "#import": [ + "unix" + ] + }, + "unix-mips64": { + "#import": [ + "unix" + ] + }, + "unix-x64": { + "#import": [ + "unix" + ] + }, + "unix-x86": { + "#import": [ + "unix" + ] + }, + "win": { + "#import": [ + "any" + ] + }, + "win-aot": { + "#import": [ + "win", + "aot" + ] + }, + "win-arm": { + "#import": [ + "win" + ] + }, + "win-arm-aot": { + "#import": [ + "win-aot", + "win-arm" + ] + }, + "win-arm64": { + "#import": [ + "win" + ] + }, + "win-arm64-aot": { + "#import": [ + "win-aot", + "win-arm64" + ] + }, + "win-x128": { + "#import": [ + "win" + ] + }, + "win-x128-aot": { + "#import": [ + "win-aot", + "win-x128" + ] + }, + "win-x64": { + "#import": [ + "win" + ] + }, + "win-x64-aot": { + "#import": [ + "win-aot", + "win-x64" + ] + }, + "win-x86": { + "#import": [ + "win" + ] + }, + "win-x86-aot": { + "#import": [ + "win-aot", + "win-x86" + ] + }, + "win10": { + "#import": [ + "win81" + ] + }, + "win10-aot": { + "#import": [ + "win10", + "win81-aot" + ] + }, + "win10-arm": { + "#import": [ + "win10", + "win81-arm" + ] + }, + "win10-arm-aot": { + "#import": [ + "win10-aot", + "win10-arm", + "win10", + "win81-arm-aot" + ] + }, + "win10-arm64": { + "#import": [ + "win10", + "win81-arm64" + ] + }, + "win10-arm64-aot": { + "#import": [ + "win10-aot", + "win10-arm64", + "win10", + "win81-arm64-aot" + ] + }, + "win10-x64": { + "#import": [ + "win10", + "win81-x64" + ] + }, + "win10-x64-aot": { + "#import": [ + "win10-aot", + "win10-x64", + "win10", + "win81-x64-aot" + ] + }, + "win10-x86": { + "#import": [ + "win10", + "win81-x86" + ] + }, + "win10-x86-aot": { + "#import": [ + "win10-aot", + "win10-x86", + "win10", + "win81-x86-aot" + ] + }, + "win12": { + "#import": [ + "win" + ] + }, + "win12-aot": { + "#import": [ + "win12", + "win-aot" + ] + }, + "win12-x128": { + "#import": [ + "win12", + "win-x128" + ] + }, + "win12-x128-aot": { + "#import": [ + "win12-aot", + "win12-x128", + "win12", + "win-x128-aot" + ] + }, + "win7": { + "#import": [ + "win" + ] + }, + "win7-aot": { + "#import": [ + "win7", + "win-aot" + ] + }, + "win7-arm": { + "#import": [ + "win7", + "win-arm" + ] + }, + "win7-arm-aot": { + "#import": [ + "win7-aot", + "win7-arm", + "win7", + "win-arm-aot" + ] + }, + "win7-arm64": { + "#import": [ + "win7", + "win-arm64" + ] + }, + "win7-arm64-aot": { + "#import": [ + "win7-aot", + "win7-arm64", + "win7", + "win-arm64-aot" + ] + }, + "win7-x64": { + "#import": [ + "win7", + "win-x64" + ] + }, + "win7-x64-aot": { + "#import": [ + "win7-aot", + "win7-x64", + "win7", + "win-x64-aot" + ] + }, + "win7-x86": { + "#import": [ + "win7", + "win-x86" + ] + }, + "win7-x86-aot": { + "#import": [ + "win7-aot", + "win7-x86", + "win7", + "win-x86-aot" + ] + }, + "win8": { + "#import": [ + "win7" + ] + }, + "win8-aot": { + "#import": [ + "win8", + "win7-aot" + ] + }, + "win8-arm": { + "#import": [ + "win8", + "win7-arm" + ] + }, + "win8-arm-aot": { + "#import": [ + "win8-aot", + "win8-arm", + "win8", + "win7-arm-aot" + ] + }, + "win8-arm64": { + "#import": [ + "win8", + "win7-arm64" + ] + }, + "win8-arm64-aot": { + "#import": [ + "win8-aot", + "win8-arm64", + "win8", + "win7-arm64-aot" + ] + }, + "win8-x64": { + "#import": [ + "win8", + "win7-x64" + ] + }, + "win8-x64-aot": { + "#import": [ + "win8-aot", + "win8-x64", + "win8", + "win7-x64-aot" + ] + }, + "win8-x86": { + "#import": [ + "win8", + "win7-x86" + ] + }, + "win8-x86-aot": { + "#import": [ + "win8-aot", + "win8-x86", + "win8", + "win7-x86-aot" + ] + }, + "win81": { + "#import": [ + "win8" + ] + }, + "win81-aot": { + "#import": [ + "win81", + "win8-aot" + ] + }, + "win81-arm": { + "#import": [ + "win81", + "win8-arm" + ] + }, + "win81-arm-aot": { + "#import": [ + "win81-aot", + "win81-arm", + "win81", + "win8-arm-aot" + ] + }, + "win81-arm64": { + "#import": [ + "win81", + "win8-arm64" + ] + }, + "win81-arm64-aot": { + "#import": [ + "win81-aot", + "win81-arm64", + "win81", + "win8-arm64-aot" + ] + }, + "win81-x64": { + "#import": [ + "win81", + "win8-x64" + ] + }, + "win81-x64-aot": { + "#import": [ + "win81-aot", + "win81-x64", + "win81", + "win8-x64-aot" + ] + }, + "win81-x86": { + "#import": [ + "win81", + "win8-x86" + ] + }, + "win81-x86-aot": { + "#import": [ + "win81-aot", + "win81-x86", + "win81", + "win8-x86-aot" + ] + } + } +} \ No newline at end of file diff --git a/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/GenerateRuntimeGraphTests.cs b/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/GenerateRuntimeGraphTests.cs index 59fd0ec07dd..c129187388d 100644 --- a/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/GenerateRuntimeGraphTests.cs +++ b/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/GenerateRuntimeGraphTests.cs @@ -60,6 +60,26 @@ public void CanInferRids() _log.WarningsLogged.Should().Be(0); } + [Fact] + public void CanInferNewArchitecture() + { + string runtimeFile = $"{nameof(GenerateRuntimeGraphTests)}.{nameof(CanInferNewArchitecture)}.runtime.json"; + + // will generate and compare to existing file. + GenerateRuntimeGraph task = new GenerateRuntimeGraph() + { + BuildEngine = _engine, + RuntimeGroups = runtimeGroups, + RuntimeJson = runtimeFile, + InferRuntimeIdentifiers = new[] { "win12-x128" } + }; + + _log.Reset(); + task.Execute(); + _log.ErrorsLogged.Should().Be(0); + _log.WarningsLogged.Should().Be(0); + } + [Fact] public void CanIgnoreExistingInferRids() { @@ -72,7 +92,7 @@ public void CanIgnoreExistingInferRids() BuildEngine = _engine, RuntimeGroups = runtimeGroups, RuntimeJson = runtimeFile, - InferRuntimeIdentifiers = new[] { "rhel.9-x64", "centos.9-arm64" } + InferRuntimeIdentifiers = new[] { "rhel.9-x64", "centos.9-arm64", "win-x64" } }; _log.Reset(); diff --git a/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/Microsoft.DotNet.Build.Tasks.Packaging.Tests.csproj b/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/Microsoft.DotNet.Build.Tasks.Packaging.Tests.csproj index 6ef0aa4f18c..63323c0d13b 100644 --- a/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/Microsoft.DotNet.Build.Tasks.Packaging.Tests.csproj +++ b/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/Microsoft.DotNet.Build.Tasks.Packaging.Tests.csproj @@ -39,12 +39,7 @@ - - PreserveNewest - - - PreserveNewest - + diff --git a/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/RidTests.cs b/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/RidTests.cs index cc66ac9f31e..762309bd79a 100644 --- a/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/RidTests.cs +++ b/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/RidTests.cs @@ -1,14 +1,8 @@ // Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. -using NuGet.Frameworks; -using NuGet.RuntimeModel; -using System.IO; -using Xunit; -using Xunit.Abstractions; -using FluentAssertions; -using Microsoft.DotNet.Build.Tasks.Packaging; using System.Collections.Generic; +using Xunit; namespace Microsoft.DotNet.Build.Tasks.Packaging.Tests { @@ -21,8 +15,9 @@ public static IEnumerable ValidRIDData() yield return new object[] { "linux", new RID() { BaseRID = "linux" } }; yield return new object[] { "linux-x64", new RID() { BaseRID = "linux", Architecture = "x64" } }; yield return new object[] { "linux-x64", new RID() { BaseRID = "linux", Architecture = "x64" } }; - yield return new object[] { "debian.10-x64", new RID() { BaseRID = "debian", Version = new RuntimeVersion("10"), Architecture = "x64" } }; + yield return new object[] { "debian.10-x64", new RID() { BaseRID = "debian", Version = new RuntimeVersion("10"), Architecture = "x64" } }; yield return new object[] { "linuxmint.19.2-x64", new RID() { BaseRID = "linuxmint", Version = new RuntimeVersion("19.2"), Architecture = "x64" } }; + yield return new object[] { "ubuntu.14.04-x64", new RID() { BaseRID = "ubuntu", Version = new RuntimeVersion("14.04"), Architecture = "x64" } }; yield return new object[] { "foo-bar.42-arm", new RID() { BaseRID = "foo-bar", Version = new RuntimeVersion("42"), Architecture = "arm" } }; yield return new object[] { "foo-bar-arm", new RID() { BaseRID = "foo", Architecture = "bar", Qualifier = "arm" } }; // demonstrates ambiguity, avoid using `-` in base } diff --git a/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/RuntimeVersionTests.cs b/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/RuntimeVersionTests.cs new file mode 100644 index 00000000000..579f14cf0f7 --- /dev/null +++ b/src/Microsoft.DotNet.Build.Tasks.Packaging/tests/RuntimeVersionTests.cs @@ -0,0 +1,233 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using System.Collections.Generic; +using Xunit; + +namespace Microsoft.DotNet.Build.Tasks.Packaging.Tests +{ + public class RuntimeVersionTests + { + public enum Comparison + { + LessThan, + Equal, + GreaterThan + } + + public static IEnumerable ComparisonData() + { + yield return new object[] { "0.0", "00.0", Comparison.LessThan }; + yield return new object[] { "2.0", "1.0", Comparison.GreaterThan }; + yield return new object[] { "2", "1.0", Comparison.GreaterThan }; + yield return new object[] { "2", "1", Comparison.GreaterThan }; + yield return new object[] { "10", "10.0", Comparison.LessThan }; + yield return new object[] { "10", "10.00", Comparison.LessThan }; + yield return new object[] { "10.0", "10.0", Comparison.Equal }; + yield return new object[] { "10.0", null, Comparison.GreaterThan }; + yield return new object[] { "8", "8", Comparison.Equal }; + } + + [MemberData(nameof(ComparisonData))] + [Theory] + public static void CompareTo(string vs1, string vs2, Comparison expected) + { + RuntimeVersion v1 = new RuntimeVersion(vs1); + RuntimeVersion v2 = vs2 == null ? null : new RuntimeVersion(vs2); + int actual = v1.CompareTo(v2); + int invActual = v2?.CompareTo(v1) ?? -1; + + switch (expected) + { + case Comparison.LessThan: + Assert.True(actual < 0); + Assert.True(invActual > 0); + break; + case Comparison.Equal: + Assert.Equal(0, actual); + Assert.Equal(0, invActual); + break; + case Comparison.GreaterThan: + Assert.True(actual > 0); + Assert.True(invActual < 0); + break; + } + } + + [MemberData(nameof(ComparisonData))] + [Theory] + public static void GreaterThan(string vs1, string vs2, Comparison expected) + { + RuntimeVersion v1 = new RuntimeVersion(vs1); + RuntimeVersion v2 = vs2 == null ? null : new RuntimeVersion(vs2); + bool actual = v1 > v2; + bool invActual = v2 > v1; + + switch (expected) + { + case Comparison.LessThan: + Assert.False(actual); + Assert.True(invActual); + break; + case Comparison.Equal: + Assert.False(actual); + Assert.False(invActual); + break; + case Comparison.GreaterThan: + Assert.True(actual); + Assert.False(invActual); + break; + } + } + + [MemberData(nameof(ComparisonData))] + [Theory] + public static void GreaterThanOrEqual(string vs1, string vs2, Comparison expected) + { + RuntimeVersion v1 = new RuntimeVersion(vs1); + RuntimeVersion v2 = vs2 == null ? null : new RuntimeVersion(vs2); + bool actual = v1 >= v2; + bool invActual = v2 >= v1; + + switch (expected) + { + case Comparison.LessThan: + Assert.False(actual); + Assert.True(invActual); + break; + case Comparison.Equal: + Assert.True(actual); + Assert.True(invActual); + break; + case Comparison.GreaterThan: + Assert.True(actual); + Assert.False(invActual); + break; + } + } + + [MemberData(nameof(ComparisonData))] + [Theory] + public static void LessThan(string vs1, string vs2, Comparison expected) + { + RuntimeVersion v1 = new RuntimeVersion(vs1); + RuntimeVersion v2 = vs2 == null ? null : new RuntimeVersion(vs2); + bool actual = v1 < v2; + bool invActual = v2 < v1; + + switch (expected) + { + case Comparison.LessThan: + Assert.True(actual); + Assert.False(invActual); + break; + case Comparison.Equal: + Assert.False(actual); + Assert.False(invActual); + break; + case Comparison.GreaterThan: + Assert.False(actual); + Assert.True(invActual); + break; + } + } + + [MemberData(nameof(ComparisonData))] + [Theory] + public static void LessThanOrEqual(string vs1, string vs2, Comparison expected) + { + RuntimeVersion v1 = new RuntimeVersion(vs1); + RuntimeVersion v2 = vs2 == null ? null : new RuntimeVersion(vs2); + bool actual = v1 <= v2; + bool invActual = v2 <= v1; + + switch (expected) + { + case Comparison.LessThan: + Assert.True(actual); + Assert.False(invActual); + break; + case Comparison.Equal: + Assert.True(actual); + Assert.True(invActual); + break; + case Comparison.GreaterThan: + Assert.False(actual); + Assert.True(invActual); + break; + } + } + + [MemberData(nameof(ComparisonData))] + [Theory] + public static void Equal(string vs1, string vs2, Comparison expected) + { + RuntimeVersion v1 = new RuntimeVersion(vs1); + RuntimeVersion v2 = vs2 == null ? null : new RuntimeVersion(vs2); + bool actual = v1 == v2; + bool invActual = v2 == v1; + + switch (expected) + { + case Comparison.LessThan: + Assert.False(actual); + Assert.False(invActual); + break; + case Comparison.Equal: + Assert.True(actual); + Assert.True(invActual); + break; + case Comparison.GreaterThan: + Assert.False(actual); + Assert.False(invActual); + break; + } + } + + [MemberData(nameof(ComparisonData))] + [Theory] + public static void GetHashCodeUnique(string vs1, string vs2, Comparison expected) + { + RuntimeVersion v1 = new RuntimeVersion(vs1); + RuntimeVersion v2 = vs2 == null ? null : new RuntimeVersion(vs2); + int h1 = v1.GetHashCode(); + int h2 = v2?.GetHashCode() ?? 0; + + switch (expected) + { + case Comparison.LessThan: + Assert.NotEqual(h1, h2); + break; + case Comparison.Equal: + Assert.Equal(h1, h2); + break; + case Comparison.GreaterThan: + Assert.NotEqual(h1, h2); + break; + } + } + public static IEnumerable ValidVersions() + { + yield return new object[] { "0" }; + yield return new object[] { "00" }; + yield return new object[] { "000" }; + yield return new object[] { "1" }; + yield return new object[] { "1.0" }; + yield return new object[] { "1.1" }; + yield return new object[] { "1.01" }; + yield return new object[] { "1.2.3.4" }; + yield return new object[] { "1.02.03.04" }; + } + + + [MemberData(nameof(ValidVersions))] + [Theory] + public static void RoundTripToString(string expected) + { + RuntimeVersion version = new RuntimeVersion(expected); + string actual = version.ToString(); + Assert.Equal(expected, actual); + } + + } +}