Adding Domain and IPAddress comparer
This commit is contained in:
@@ -22,17 +22,17 @@
|
|||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
<ItemGroup Condition="'$(TargetFramework)' == 'net6.0'">
|
<ItemGroup Condition="'$(TargetFramework)' == 'net6.0'">
|
||||||
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="6.0.26" />
|
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="6.0.0" />
|
||||||
<PackageReference Include="Microsoft.EntityFrameworkCore.Relational" Version="6.0.26" />
|
<PackageReference Include="Microsoft.EntityFrameworkCore.Relational" Version="6.0.0" />
|
||||||
<PackageReference Include="Microsoft.Extensions.Configuration" Version="6.0.1" />
|
<PackageReference Include="Microsoft.Extensions.Configuration" Version="6.0.0" />
|
||||||
<PackageReference Include="Microsoft.Extensions.Configuration.Binder" Version="6.0.0" />
|
<PackageReference Include="Microsoft.Extensions.Configuration.Binder" Version="6.0.0" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
<ItemGroup Condition="'$(TargetFramework)' == 'net8.0'">
|
<ItemGroup Condition="'$(TargetFramework)' == 'net8.0'">
|
||||||
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="8.0.1" />
|
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="8.0.0" />
|
||||||
<PackageReference Include="Microsoft.EntityFrameworkCore.Relational" Version="8.0.1" />
|
<PackageReference Include="Microsoft.EntityFrameworkCore.Relational" Version="8.0.0" />
|
||||||
<PackageReference Include="Microsoft.Extensions.Configuration" Version="8.0.0" />
|
<PackageReference Include="Microsoft.Extensions.Configuration" Version="8.0.0" />
|
||||||
<PackageReference Include="Microsoft.Extensions.Configuration.Binder" Version="8.0.1" />
|
<PackageReference Include="Microsoft.Extensions.Configuration.Binder" Version="8.0.0" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
</Project>
|
</Project>
|
||||||
|
|||||||
@@ -27,7 +27,7 @@
|
|||||||
|
|
||||||
<ItemGroup Condition="'$(TargetFramework)' == 'netstandard2.0'">
|
<ItemGroup Condition="'$(TargetFramework)' == 'netstandard2.0'">
|
||||||
<PackageReference Include="Microsoft.AspNetCore.HttpOverrides" Version="2.2.0" />
|
<PackageReference Include="Microsoft.AspNetCore.HttpOverrides" Version="2.2.0" />
|
||||||
<PackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="6.0.4" />
|
<PackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="6.0.0" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
<ItemGroup Condition="'$(TargetFramework)' == 'net8.0'">
|
<ItemGroup Condition="'$(TargetFramework)' == 'net8.0'">
|
||||||
|
|||||||
57
AMWD.Common/Comparer/DomainComparer.cs
Normal file
57
AMWD.Common/Comparer/DomainComparer.cs
Normal file
@@ -0,0 +1,57 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
|
||||||
|
namespace AMWD.Common.Comparer
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Defines a method to compare two domain strings.
|
||||||
|
/// </summary>
|
||||||
|
public class DomainComparer : IComparer<string>
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Compares two domain strings and returns a value indicating
|
||||||
|
/// whether one is less than, equal to, or greater than the other.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="x">The first domain string.</param>
|
||||||
|
/// <param name="y">The second domain string.</param>
|
||||||
|
/// <returns>
|
||||||
|
/// A signed integer that indicates the relative values of x and y, as shown in the following table:
|
||||||
|
/// <list type="table">
|
||||||
|
/// <listheader>
|
||||||
|
/// <term>Value</term>
|
||||||
|
/// <description>Meaning</description>
|
||||||
|
/// </listheader>
|
||||||
|
/// <item>
|
||||||
|
/// <term>Less than zero</term>
|
||||||
|
/// <description>x is less than y</description>
|
||||||
|
/// </item>
|
||||||
|
/// <item>
|
||||||
|
/// <term>Zero</term>
|
||||||
|
/// <description>x equals y</description>
|
||||||
|
/// </item>
|
||||||
|
/// <item>
|
||||||
|
/// <term>Greater than zero</term>
|
||||||
|
/// <description>x is greater than y</description>
|
||||||
|
/// </item>
|
||||||
|
/// </list>
|
||||||
|
/// </returns>
|
||||||
|
public int Compare(string x, string y)
|
||||||
|
{
|
||||||
|
string[] left = x.Split('.');
|
||||||
|
string[] right = y.Split('.');
|
||||||
|
|
||||||
|
int result = left.Length.CompareTo(right.Length);
|
||||||
|
if (result != 0)
|
||||||
|
return result;
|
||||||
|
|
||||||
|
// Compare from TLD to subdomain with string comparison
|
||||||
|
for (int i = left.Length - 1; i >= 0; i--)
|
||||||
|
{
|
||||||
|
result = left[i].CompareTo(right[i]);
|
||||||
|
if (result != 0)
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
71
AMWD.Common/Comparer/IPAddressComparer.cs
Normal file
71
AMWD.Common/Comparer/IPAddressComparer.cs
Normal file
@@ -0,0 +1,71 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Net;
|
||||||
|
|
||||||
|
namespace AMWD.Common.Comparer
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Defines a method to compare two IP addresses.
|
||||||
|
/// </summary>
|
||||||
|
public class IPAddressComparer : IComparer<IPAddress>
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Compares two IP addresses and returns a value indicating whether one is less than,
|
||||||
|
/// equal to, or greater than the other.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="x">The first IP address.</param>
|
||||||
|
/// <param name="y">The second IP address.</param>
|
||||||
|
/// <returns>
|
||||||
|
/// A signed integer that indicates the relative values of x and y, as shown in the following table.
|
||||||
|
/// <list type="table">
|
||||||
|
/// <listheader>
|
||||||
|
/// <term>Value</term>
|
||||||
|
/// <description>Meaning</description>
|
||||||
|
/// </listheader>
|
||||||
|
/// <item>
|
||||||
|
/// <term>Less than zero</term>
|
||||||
|
/// <description>x is less than y.</description>
|
||||||
|
/// </item>
|
||||||
|
/// <item>
|
||||||
|
/// <term>Zero</term>
|
||||||
|
/// <description>x equals y.</description>
|
||||||
|
/// </item>
|
||||||
|
/// <item>
|
||||||
|
/// <term>Greater than zero</term>
|
||||||
|
/// <description>x is greater than y.</description>
|
||||||
|
/// </item>
|
||||||
|
/// </list>
|
||||||
|
/// </returns>
|
||||||
|
public int Compare(IPAddress x, IPAddress y)
|
||||||
|
{
|
||||||
|
if (x == null && y == null)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
if (x == null)
|
||||||
|
return -1;
|
||||||
|
|
||||||
|
if (y == null)
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
byte[] xBytes = x.GetAddressBytes();
|
||||||
|
byte[] yBytes = y.GetAddressBytes();
|
||||||
|
|
||||||
|
// Make IPv4 and IPv6 comparable
|
||||||
|
byte[] left = xBytes.Length == 16
|
||||||
|
? xBytes
|
||||||
|
: [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 255, 255, xBytes[0], xBytes[1], xBytes[2], xBytes[3]];
|
||||||
|
byte[] right = yBytes.Length == 16
|
||||||
|
? yBytes
|
||||||
|
: [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 255, 255, yBytes[0], yBytes[1], yBytes[2], yBytes[3]];
|
||||||
|
|
||||||
|
// Compare byte for byte
|
||||||
|
for (int i = 0; i < left.Length; i++)
|
||||||
|
{
|
||||||
|
int result = left[i].CompareTo(right[i]);
|
||||||
|
if (result != 0)
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -15,7 +15,7 @@ namespace AMWD.Common.Comparer
|
|||||||
|
|
||||||
public class VersionStringComparer : IComparer<string>
|
public class VersionStringComparer : IComparer<string>
|
||||||
{
|
{
|
||||||
private readonly Regex _versionRegex = new("([0-9.]+)");
|
private readonly Regex _versionRegex = new("([0-9.]+)", RegexOptions.Compiled);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@@ -32,16 +32,16 @@ namespace AMWD.Common.Comparer
|
|||||||
/// <description>Meaning</description>
|
/// <description>Meaning</description>
|
||||||
/// </listheader>
|
/// </listheader>
|
||||||
/// <item>
|
/// <item>
|
||||||
/// <term>-1</term>
|
/// <term>Less than zero</term>
|
||||||
/// <description>x is less than y</description>
|
/// <description>x is less than y.</description>
|
||||||
/// </item>
|
/// </item>
|
||||||
/// <item>
|
/// <item>
|
||||||
/// <term>0</term>
|
/// <term>Zero</term>
|
||||||
/// <description>x equals y</description>
|
/// <description>x equals y.</description>
|
||||||
/// </item>
|
/// </item>
|
||||||
/// <item>
|
/// <item>
|
||||||
/// <term>1</term>
|
/// <term>Greater than zero</term>
|
||||||
/// <description>x is greater than y</description>
|
/// <description>x is greater than y.</description>
|
||||||
/// </item>
|
/// </item>
|
||||||
/// </list>
|
/// </list>
|
||||||
/// </returns>
|
/// </returns>
|
||||||
@@ -79,7 +79,7 @@ namespace AMWD.Common.Comparer
|
|||||||
}
|
}
|
||||||
|
|
||||||
#if NET8_0_OR_GREATER
|
#if NET8_0_OR_GREATER
|
||||||
[GeneratedRegex("([0-9.]+)")]
|
[GeneratedRegex("([0-9.]+)", RegexOptions.Compiled)]
|
||||||
private static partial Regex VersionRegex();
|
private static partial Regex VersionRegex();
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -21,6 +21,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|||||||
- `TarReader` and `TarWriter` for TAR archives
|
- `TarReader` and `TarWriter` for TAR archives
|
||||||
- `.AddRange()` for collections
|
- `.AddRange()` for collections
|
||||||
- `.AddIfNotNull()` for collections
|
- `.AddIfNotNull()` for collections
|
||||||
|
- `DomainComparer` ordering alphabetically from TLD to sub-domain
|
||||||
|
- `IPAddressComparer` able to compare IPv4 and IPv6
|
||||||
- `VersionStringComparer` to compare version strings (SemVer)
|
- `VersionStringComparer` to compare version strings (SemVer)
|
||||||
|
|
||||||
### Changed
|
### Changed
|
||||||
|
|||||||
59
UnitTests/Common/Comparer/DomainComparerTests.cs
Normal file
59
UnitTests/Common/Comparer/DomainComparerTests.cs
Normal file
@@ -0,0 +1,59 @@
|
|||||||
|
using AMWD.Common.Comparer;
|
||||||
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
|
|
||||||
|
namespace UnitTests.Common.Comparer
|
||||||
|
{
|
||||||
|
[TestClass]
|
||||||
|
public class DomainComparerTests
|
||||||
|
{
|
||||||
|
[DataTestMethod]
|
||||||
|
[DataRow("int", "internal")]
|
||||||
|
[DataRow("int", "dom.int")]
|
||||||
|
[DataRow("a.ins", "a.int")]
|
||||||
|
[DataRow("a.internal", "b.internal")]
|
||||||
|
[DataRow("sub1.domain.internal", "sub2.domain.internal")]
|
||||||
|
public void ShouldBeLessThan(string left, string right)
|
||||||
|
{
|
||||||
|
// Arrange
|
||||||
|
var comparer = new DomainComparer();
|
||||||
|
|
||||||
|
// Act
|
||||||
|
int result = comparer.Compare(left, right);
|
||||||
|
|
||||||
|
Assert.AreEqual(-1, result);
|
||||||
|
}
|
||||||
|
|
||||||
|
[DataTestMethod]
|
||||||
|
[DataRow("internal", "int")]
|
||||||
|
[DataRow("dom.int", "int")]
|
||||||
|
[DataRow("a.int", "a.ins")]
|
||||||
|
[DataRow("b.internal", "a.internal")]
|
||||||
|
[DataRow("sub2.domain.internal", "sub1.domain.internal")]
|
||||||
|
public void ShouldBeGreaterThan(string left, string right)
|
||||||
|
{
|
||||||
|
// Arrange
|
||||||
|
var comparer = new DomainComparer();
|
||||||
|
|
||||||
|
// Act
|
||||||
|
int result = comparer.Compare(left, right);
|
||||||
|
|
||||||
|
Assert.AreEqual(1, result);
|
||||||
|
}
|
||||||
|
|
||||||
|
[DataTestMethod]
|
||||||
|
[DataRow("internal", "internal")]
|
||||||
|
[DataRow("dom.int", "dom.int")]
|
||||||
|
[DataRow("a.internal", "a.internal")]
|
||||||
|
[DataRow("sub.domain.internal", "sub.domain.internal")]
|
||||||
|
public void ShouldBeEqual(string left, string right)
|
||||||
|
{
|
||||||
|
// Arrange
|
||||||
|
var comparer = new DomainComparer();
|
||||||
|
|
||||||
|
// Act
|
||||||
|
int result = comparer.Compare(left, right);
|
||||||
|
|
||||||
|
Assert.AreEqual(0, result);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
58
UnitTests/Common/Comparer/IPAddressComparerTests.cs
Normal file
58
UnitTests/Common/Comparer/IPAddressComparerTests.cs
Normal file
@@ -0,0 +1,58 @@
|
|||||||
|
using System.Net;
|
||||||
|
using AMWD.Common.Comparer;
|
||||||
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
|
|
||||||
|
namespace UnitTests.Common.Comparer
|
||||||
|
{
|
||||||
|
[TestClass]
|
||||||
|
public class IPAddressComparerTests
|
||||||
|
{
|
||||||
|
[DataTestMethod]
|
||||||
|
[DataRow("127.0.0.0", "127.0.0.1")]
|
||||||
|
[DataRow("fe80::", "fe80::1")]
|
||||||
|
[DataRow("::ffff:7f00:0", "127.0.0.1")]
|
||||||
|
public void ShouldBeLessThan(string left, string right)
|
||||||
|
{
|
||||||
|
// Arrange
|
||||||
|
var comparer = new IPAddressComparer();
|
||||||
|
|
||||||
|
// Act
|
||||||
|
int result = comparer.Compare(IPAddress.Parse(left), IPAddress.Parse(right));
|
||||||
|
|
||||||
|
// Assert
|
||||||
|
Assert.AreEqual(-1, result);
|
||||||
|
}
|
||||||
|
|
||||||
|
[DataTestMethod]
|
||||||
|
[DataRow("127.0.0.1", "127.0.0.0")]
|
||||||
|
[DataRow("fe80::1", "fe80::")]
|
||||||
|
[DataRow("::ffff:7f00:1", "127.0.0.0")]
|
||||||
|
public void ShouldBeGreaterThan(string left, string right)
|
||||||
|
{
|
||||||
|
// Arrange
|
||||||
|
var comparer = new IPAddressComparer();
|
||||||
|
|
||||||
|
// Act
|
||||||
|
int result = comparer.Compare(IPAddress.Parse(left), IPAddress.Parse(right));
|
||||||
|
|
||||||
|
// Assert
|
||||||
|
Assert.AreEqual(1, result);
|
||||||
|
}
|
||||||
|
|
||||||
|
[DataTestMethod]
|
||||||
|
[DataRow("127.0.0.1", "127.0.0.1")]
|
||||||
|
[DataRow("fe80::1", "fe80::1")]
|
||||||
|
[DataRow("::ffff:7f00:1", "127.0.0.1")]
|
||||||
|
public void ShouldBeEqual(string left, string right)
|
||||||
|
{
|
||||||
|
// Arrange
|
||||||
|
var comparer = new IPAddressComparer();
|
||||||
|
|
||||||
|
// Act
|
||||||
|
int result = comparer.Compare(IPAddress.Parse(left), IPAddress.Parse(right));
|
||||||
|
|
||||||
|
// Assert
|
||||||
|
Assert.AreEqual(0, result);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user