|
| 1 | +using System.Diagnostics; |
| 2 | +using System.Linq; |
| 3 | +using System.Text.RegularExpressions; |
| 4 | +using NETworkManager.Utilities; |
| 5 | +using Xunit; |
| 6 | + |
| 7 | +namespace NETworkManager.Tests.Utilities; |
| 8 | + |
| 9 | +public class RegexHelperTests |
| 10 | +{ |
| 11 | + [Theory] |
| 12 | + [InlineData("00:11:22:33:44:55", true)] |
| 13 | + [InlineData("00-11-22-33-44-55", true)] |
| 14 | + [InlineData("001122334455", true)] |
| 15 | + [InlineData("0011.2233.4455", true)] |
| 16 | + [InlineData("0011 2233 4455", false)] |
| 17 | + [InlineData("0011x2233x4455", false)] |
| 18 | + [InlineData("00:11:22:33:44", false)] |
| 19 | + public void MACAddress(string input, bool isMatch) |
| 20 | + { |
| 21 | + Assert.Equal(isMatch, Regex.IsMatch(input, RegexHelper.MACAddressRegex)); |
| 22 | + } |
| 23 | + |
| 24 | + [Theory] |
| 25 | + [InlineData("00:11:22", true)] |
| 26 | + [InlineData("001122", true)] |
| 27 | + [InlineData("0011.22", true)] |
| 28 | + [InlineData("0011 22", false)] |
| 29 | + [InlineData("0011x22", false)] |
| 30 | + public void MACAddressFirst3Bytes(string input, bool isMatch) |
| 31 | + { |
| 32 | + Assert.Equal(isMatch, Regex.IsMatch(input, RegexHelper.MACAddressFirst3BytesRegex)); |
| 33 | + } |
| 34 | + |
| 35 | + [Theory] |
| 36 | + [InlineData("2001:db8::/32", true)] |
| 37 | + [InlineData("::ffff:192.168.0.1/96", true)] |
| 38 | + [InlineData("sss2001:db8::/32", false)] |
| 39 | + [InlineData("2001:db8::/129", false)] |
| 40 | + public void IPv6AddressCidr(string input, bool isMatch) |
| 41 | + { |
| 42 | + Assert.Equal(isMatch, Regex.IsMatch(input, RegexHelper.IPv6AddressCidrRegex)); |
| 43 | + } |
| 44 | + |
| 45 | + [Theory] |
| 46 | + [InlineData("1", true)] |
| 47 | + [InlineData("3389", true)] |
| 48 | + [InlineData("65535", true)] |
| 49 | + [InlineData("", false)] |
| 50 | + [InlineData("0", false)] |
| 51 | + [InlineData("65536", false)] |
| 52 | + [InlineData("05555", false)] |
| 53 | + public void Port(string input, bool isMatch) |
| 54 | + { |
| 55 | + Assert.Equal(isMatch, Regex.IsMatch(input, RegexHelper.PortRegex)); |
| 56 | + } |
| 57 | + |
| 58 | + [Theory] |
| 59 | + [InlineData("server-01", true)] |
| 60 | + [InlineData("server-01.example.com", true)] |
| 61 | + [InlineData("example.com.", true)] |
| 62 | + [InlineData("123abc", true)] |
| 63 | + [InlineData("-server", false)] |
| 64 | + [InlineData("server-", false)] |
| 65 | + [InlineData("server.-bad-.com", false)] |
| 66 | + [InlineData("a..b", false)] |
| 67 | + // IPv4 addresses, shortened or partly typed ones are not hostnames (checked separately) |
| 68 | + [InlineData("10.0.0.1", false)] |
| 69 | + [InlineData("10.0.0.", false)] |
| 70 | + [InlineData("192.168.1", false)] |
| 71 | + [InlineData("1234", false)] |
| 72 | + public void HostnameOrDomain(string input, bool isMatch) |
| 73 | + { |
| 74 | + Assert.Equal(isMatch, RegexHelper.HostnameOrDomainRegex().IsMatch(input)); |
| 75 | + } |
| 76 | + |
| 77 | + [Theory] |
| 78 | + [InlineData("borntoberoot.net", true)] |
| 79 | + [InlineData("local.example.com", true)] |
| 80 | + [InlineData("example", false)] |
| 81 | + public void Domain(string input, bool isMatch) |
| 82 | + { |
| 83 | + Assert.Equal(isMatch, Regex.IsMatch(input, RegexHelper.DomainRegex)); |
| 84 | + } |
| 85 | + |
| 86 | + [Theory] |
| 87 | + [InlineData("22", true)] |
| 88 | + [InlineData("22/tcp", true)] |
| 89 | + [InlineData("22/TCP", true)] |
| 90 | + [InlineData("80-90", true)] |
| 91 | + [InlineData("80-90/udp", true)] |
| 92 | + [InlineData("22;80-90/tcp;443", true)] |
| 93 | + [InlineData("22;", false)] |
| 94 | + [InlineData("ssh", false)] |
| 95 | + [InlineData("22/http", false)] |
| 96 | + [InlineData("123456", false)] |
| 97 | + public void PortLookupEntries(string input, bool isMatch) |
| 98 | + { |
| 99 | + Assert.Equal(isMatch, RegexHelper.PortLookupEntriesRegex().IsMatch(input)); |
| 100 | + } |
| 101 | + |
| 102 | + [Theory] |
| 103 | + [InlineData("22", true, false, false, false)] |
| 104 | + [InlineData("22/tcp", false, true, false, false)] |
| 105 | + [InlineData("80-90", false, false, true, false)] |
| 106 | + [InlineData("80-90/sctp", false, false, false, true)] |
| 107 | + [InlineData("ssh", false, false, false, false)] |
| 108 | + public void PortLookupEntry(string input, bool port, bool portAndProtocol, bool portRange, |
| 109 | + bool portRangeAndProtocol) |
| 110 | + { |
| 111 | + Assert.Equal(port, RegexHelper.PortLookupPortRegex().IsMatch(input)); |
| 112 | + Assert.Equal(portAndProtocol, RegexHelper.PortLookupPortAndProtocolRegex().IsMatch(input)); |
| 113 | + Assert.Equal(portRange, RegexHelper.PortLookupPortRangeRegex().IsMatch(input)); |
| 114 | + Assert.Equal(portRangeAndProtocol, RegexHelper.PortLookupPortRangeAndProtocolRegex().IsMatch(input)); |
| 115 | + } |
| 116 | + |
| 117 | + [Theory] |
| 118 | + [InlineData("00:11:22", true)] |
| 119 | + [InlineData("00-11-22", true)] |
| 120 | + [InlineData("001122", false)] |
| 121 | + [InlineData("facade", false)] |
| 122 | + public void MACAddressFirst3BytesWithSeparator(string input, bool isMatch) |
| 123 | + { |
| 124 | + Assert.Equal(isMatch, RegexHelper.MACAddressFirst3BytesWithSeparatorRegex().IsMatch(input)); |
| 125 | + } |
| 126 | + |
| 127 | + [Theory] |
| 128 | + [InlineData("AS13335", true)] |
| 129 | + [InlineData("as13335", true)] |
| 130 | + [InlineData("13335", false)] |
| 131 | + [InlineData("AS", false)] |
| 132 | + public void ASNumberWithPrefix(string input, bool isMatch) |
| 133 | + { |
| 134 | + Assert.Equal(isMatch, RegexHelper.ASNumberWithPrefixRegex().IsMatch(input)); |
| 135 | + } |
| 136 | + |
| 137 | + [Theory] |
| 138 | + [InlineData("https://borntoberoot.net", true)] |
| 139 | + [InlineData("HTTP://borntoberoot.net", true)] |
| 140 | + [InlineData("ftp://borntoberoot.net", false)] |
| 141 | + [InlineData("borntoberoot.net", false)] |
| 142 | + public void HttpOrHttpsScheme(string input, bool isMatch) |
| 143 | + { |
| 144 | + Assert.Equal(isMatch, RegexHelper.HttpOrHttpsSchemeRegex().IsMatch(input)); |
| 145 | + } |
| 146 | + |
| 147 | + // An invalid input with many labels took exponentially long (catastrophic backtracking). |
| 148 | + [Fact] |
| 149 | + public void DomainAndHostnameNoBacktracking() |
| 150 | + { |
| 151 | + var input = "a" + string.Concat(Enumerable.Repeat(".a", 100)) + "!"; |
| 152 | + |
| 153 | + var stopwatch = Stopwatch.StartNew(); |
| 154 | + |
| 155 | + Assert.DoesNotMatch(RegexHelper.DomainRegex, input); |
| 156 | + Assert.DoesNotMatch(RegexHelper.HostnameOrDomainRegex(), input); |
| 157 | + |
| 158 | + Assert.True(stopwatch.ElapsedMilliseconds < 1000); |
| 159 | + } |
| 160 | +} |
0 commit comments