From 92ce30af09e3ed36d1180a533b7970a00e9f4361 Mon Sep 17 00:00:00 2001
From: xljiulang <366193849@qq.com>
Date: Sat, 17 Jul 2021 21:34:04 +0800
Subject: [PATCH] =?UTF-8?q?=E5=A2=9E=E5=8A=A0FastGithubException=E5=BC=82?=
=?UTF-8?q?=E5=B8=B8?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
FastGithub.Core/DomainMatch.cs | 43 ++++++++++
FastGithub.Core/FastGithubException.cs | 29 +++++++
FastGithub.Core/FastGithubOptions.cs | 80 +++++++++----------
...{DnsIPEndPoint.cs => IPEndPointOptions.cs} | 19 ++---
FastGithub.ReverseProxy/DomainResolver.cs | 10 ++-
.../ReverseProxyException.cs | 20 -----
FastGithub/Program.cs | 2 +-
7 files changed, 121 insertions(+), 82 deletions(-)
create mode 100644 FastGithub.Core/DomainMatch.cs
create mode 100644 FastGithub.Core/FastGithubException.cs
rename FastGithub.Core/{DnsIPEndPoint.cs => IPEndPointOptions.cs} (77%)
delete mode 100644 FastGithub.ReverseProxy/ReverseProxyException.cs
diff --git a/FastGithub.Core/DomainMatch.cs b/FastGithub.Core/DomainMatch.cs
new file mode 100644
index 0000000..c5215e1
--- /dev/null
+++ b/FastGithub.Core/DomainMatch.cs
@@ -0,0 +1,43 @@
+using System.Text.RegularExpressions;
+
+namespace FastGithub
+{
+ ///
+ /// 域名匹配
+ ///
+ sealed class DomainMatch
+ {
+ private readonly Regex regex;
+ private readonly string pattern;
+
+ ///
+ /// 域名匹配
+ ///
+ /// 域名表达式
+ public DomainMatch(string pattern)
+ {
+ this.pattern = pattern;
+ var regexPattern = Regex.Escape(pattern).Replace(@"\*", ".*");
+ this.regex = new Regex($"^{regexPattern}$", RegexOptions.IgnoreCase);
+ }
+
+ ///
+ /// 是否与指定域名匹配
+ ///
+ ///
+ ///
+ public bool IsMatch(string domain)
+ {
+ return this.regex.IsMatch(domain);
+ }
+
+ ///
+ /// 转换为文本
+ ///
+ ///
+ public override string ToString()
+ {
+ return this.pattern;
+ }
+ }
+}
diff --git a/FastGithub.Core/FastGithubException.cs b/FastGithub.Core/FastGithubException.cs
new file mode 100644
index 0000000..d601770
--- /dev/null
+++ b/FastGithub.Core/FastGithubException.cs
@@ -0,0 +1,29 @@
+using System;
+
+namespace FastGithub
+{
+ ///
+ /// 表示FastGithub异常
+ ///
+ public class FastGithubException : Exception
+ {
+ ///
+ /// FastGithub异常
+ ///
+ ///
+ public FastGithubException(string message)
+ : base(message)
+ {
+ }
+
+ ///
+ /// FastGithub异常
+ ///
+ ///
+ ///
+ public FastGithubException(string message, Exception? innerException)
+ : base(message, innerException)
+ {
+ }
+ }
+}
diff --git a/FastGithub.Core/FastGithubOptions.cs b/FastGithub.Core/FastGithubOptions.cs
index a57918a..db884a1 100644
--- a/FastGithub.Core/FastGithubOptions.cs
+++ b/FastGithub.Core/FastGithubOptions.cs
@@ -1,6 +1,7 @@
-using System.Collections.Generic;
+using System;
+using System.Collections.Generic;
using System.Linq;
-using System.Text.RegularExpressions;
+using System.Net;
namespace FastGithub
{
@@ -13,22 +14,52 @@ namespace FastGithub
/// 域名
///
private DomainMatch[]? domainMatches;
+ private IPEndPoint? trustedDnsEndPoint;
+ private IPEndPoint? unTrustedDnsEndPoint;
///
/// 受信任的dns服务
///
- public DnsIPEndPoint TrustedDns { get; set; } = new DnsIPEndPoint { IPAddress = "127.0.0.1", Port = 5533 };
+ public IPEndPointOptions TrustedDns { get; set; } = new IPEndPointOptions { IPAddress = "127.0.0.1", Port = 5533 };
///
/// 不受信任的dns服务
///
- public DnsIPEndPoint UntrustedDns { get; set; } = new DnsIPEndPoint { IPAddress = "114.114.114.114", Port = 53 };
+ public IPEndPointOptions UntrustedDns { get; set; } = new IPEndPointOptions { IPAddress = "114.114.114.114", Port = 53 };
///
/// 代理的域名匹配
///
public HashSet DomainMatches { get; set; } = new();
+ ///
+ /// 验证选项值
+ ///
+ ///
+ public void Validate()
+ {
+ this.trustedDnsEndPoint = this.TrustedDns.ToIPEndPoint();
+ this.unTrustedDnsEndPoint = this.UntrustedDns.ToIPEndPoint();
+ this.domainMatches = this.DomainMatches.Select(item => new DomainMatch(item)).ToArray();
+ }
+
+
+ ///
+ /// 受信任的dns服务节点
+ ///
+ public IPEndPoint GetTrustedDns()
+ {
+ return this.trustedDnsEndPoint ?? throw new InvalidOperationException();
+ }
+
+ ///
+ /// 不受信任的dns服务节点
+ ///
+ public IPEndPoint GetUnTrustedDns()
+ {
+ return this.unTrustedDnsEndPoint ?? throw new InvalidOperationException();
+ }
+
///
/// 是否匹配指定的域名
///
@@ -38,48 +69,9 @@ namespace FastGithub
{
if (this.domainMatches == null)
{
- this.domainMatches = this.DomainMatches.Select(item => new DomainMatch(item)).ToArray();
+ throw new InvalidOperationException();
}
return this.domainMatches.Any(item => item.IsMatch(domain));
}
-
- ///
- /// 域名匹配
- ///
- private class DomainMatch
- {
- private readonly Regex regex;
- private readonly string pattern;
-
- ///
- /// 域名匹配
- ///
- /// 域名表达式
- public DomainMatch(string pattern)
- {
- this.pattern = pattern;
- var regexPattern = Regex.Escape(pattern).Replace(@"\*", ".*");
- this.regex = new Regex($"^{regexPattern}$", RegexOptions.IgnoreCase);
- }
-
- ///
- /// 是否与指定域名匹配
- ///
- ///
- ///
- public bool IsMatch(string domain)
- {
- return this.regex.IsMatch(domain);
- }
-
- ///
- /// 转换为文本
- ///
- ///
- public override string ToString()
- {
- return this.pattern;
- }
- }
}
}
diff --git a/FastGithub.Core/DnsIPEndPoint.cs b/FastGithub.Core/IPEndPointOptions.cs
similarity index 77%
rename from FastGithub.Core/DnsIPEndPoint.cs
rename to FastGithub.Core/IPEndPointOptions.cs
index aa70b35..3a523be 100644
--- a/FastGithub.Core/DnsIPEndPoint.cs
+++ b/FastGithub.Core/IPEndPointOptions.cs
@@ -7,7 +7,7 @@ namespace FastGithub
///
/// dns的终节点
///
- public class DnsIPEndPoint
+ public class IPEndPointOptions
{
///
/// IP地址
@@ -24,29 +24,20 @@ namespace FastGithub
/// 转换为IPEndPoint
///
///
+ ///
public IPEndPoint ToIPEndPoint()
- {
- return new IPEndPoint(System.Net.IPAddress.Parse(this.IPAddress), this.Port);
- }
-
- ///
- /// 验证dns
- /// 防止使用自己使用自己来解析域名造成死循环
- ///
- ///
- public bool Validate()
{
if (System.Net.IPAddress.TryParse(this.IPAddress, out var address) == false)
{
- return false;
+ throw new FastGithubException($"无效的ip:{this.IPAddress}");
}
if (this.Port == 53 && IsLocalMachineIPAddress(address))
{
- return false;
+ throw new FastGithubException($"配置的dns值不能指向{nameof(FastGithub)}自身:{this.IPAddress}:{this.Port}");
}
- return true;
+ return new IPEndPoint(address, this.Port);
}
///
diff --git a/FastGithub.ReverseProxy/DomainResolver.cs b/FastGithub.ReverseProxy/DomainResolver.cs
index 04886b2..e8908e9 100644
--- a/FastGithub.ReverseProxy/DomainResolver.cs
+++ b/FastGithub.ReverseProxy/DomainResolver.cs
@@ -63,20 +63,24 @@ namespace FastGithub.ReverseProxy
var address = addresses?.FirstOrDefault();
if (address == null)
{
- throw new Exception($"解析不到{domain}的ip");
+ throw new FastGithubException($"dns({endpoint}):解析不到{domain}的ip");
}
// 受干扰的dns,常常返回127.0.0.1来阻断请求
// 如果解析到的ip为本机ip,会产生反向代理请求死循环
if (address.Equals(IPAddress.Loopback))
{
- throw new Exception($"dns受干扰,解析{domain}的ip为{address}");
+ throw new FastGithubException($"dns({endpoint}):解析{domain}被干扰为{address}");
}
return address;
}
+ catch (FastGithubException)
+ {
+ throw;
+ }
catch (Exception ex)
{
- throw new ReverseProxyException($"dns({endpoint}):{ex.Message}", ex);
+ throw new FastGithubException($"dns({endpoint}):{ex.Message}", ex);
}
}
}
diff --git a/FastGithub.ReverseProxy/ReverseProxyException.cs b/FastGithub.ReverseProxy/ReverseProxyException.cs
deleted file mode 100644
index 16aa1b7..0000000
--- a/FastGithub.ReverseProxy/ReverseProxyException.cs
+++ /dev/null
@@ -1,20 +0,0 @@
-using System;
-
-namespace FastGithub.ReverseProxy
-{
- ///
- /// 反向代理异常
- ///
- sealed class ReverseProxyException : Exception
- {
- ///
- /// 反向代理异常
- ///
- ///
- ///
- public ReverseProxyException(string message, Exception? inner)
- : base(message, inner)
- {
- }
- }
-}
diff --git a/FastGithub/Program.cs b/FastGithub/Program.cs
index 222b653..3b77699 100644
--- a/FastGithub/Program.cs
+++ b/FastGithub/Program.cs
@@ -39,7 +39,7 @@ namespace FastGithub
.AddDnscryptProxy()
.AddOptions()
.Bind(ctx.Configuration.GetSection(nameof(FastGithub)))
- .Validate(opt => opt.TrustedDns.Validate() && opt.UntrustedDns.Validate(), "无效的Dns配置");
+ .PostConfigure(opt => opt.Validate());
})
.ConfigureWebHostDefaults(web =>
{