|
@@ -10,11 +10,13 @@ import (
|
|
|
"github.com/go-nunu/nunu-layout-advanced/pkg/rabbitmq"
|
|
|
amqp "github.com/rabbitmq/amqp091-go"
|
|
|
"go.uber.org/zap"
|
|
|
+ "golang.org/x/net/idna"
|
|
|
"golang.org/x/net/publicsuffix"
|
|
|
"golang.org/x/sync/errgroup"
|
|
|
"net"
|
|
|
"slices"
|
|
|
"strconv"
|
|
|
+ "strings"
|
|
|
)
|
|
|
|
|
|
type WafFormatterService interface {
|
|
@@ -33,6 +35,8 @@ type WafFormatterService interface {
|
|
|
AddOrigin(ctx context.Context, req v1.WebJson) (int64, error)
|
|
|
// 获取ip数量等于1的源站过白ip
|
|
|
WashDelIps(ctx context.Context, ips []string) ([]string, error)
|
|
|
+ // 判断域名是否是IDN,如果是,转换为 Punycode
|
|
|
+ ConvertToPunycodeIfIDN(ctx context.Context,domain string) (isIDN bool, punycodeDomain string, err error)
|
|
|
}
|
|
|
func NewWafFormatterService(
|
|
|
service *Service,
|
|
@@ -471,4 +475,22 @@ func (s *wafFormatterService) WashDelIps(ctx context.Context, ips []string) ([]s
|
|
|
}
|
|
|
|
|
|
return ipsToDelist, nil
|
|
|
+}
|
|
|
+
|
|
|
+// 判断域名是否为 中文域名,如果是,转换为 Punycode
|
|
|
+func (s *wafFormatterService) ConvertToPunycodeIfIDN(ctx context.Context,domain string) (isIDN bool, punycodeDomain string, err error) {
|
|
|
+ // 使用 idna.ToASCII 将域名转换为 Punycode。
|
|
|
+ // 这个函数同时会根据 IDNA 规范验证域名的合法性。
|
|
|
+ punycodeDomain, err = idna.ToASCII(domain)
|
|
|
+ if err != nil {
|
|
|
+ // 如果转换出错,说明域名格式不符合 IDNA 标准。
|
|
|
+ return false, "", fmt.Errorf("域名 '%s' 格式无效: %v", domain, err)
|
|
|
+ }
|
|
|
+
|
|
|
+ // 判断是否为 IDN 的关键:
|
|
|
+ // 比较转换后的 Punycode 域名和原始域名(忽略大小写)。
|
|
|
+ // 如果不相等,说明原始域名包含非 ASCII 字符,即为 IDN。
|
|
|
+ isIDN = !strings.EqualFold(domain, punycodeDomain)
|
|
|
+
|
|
|
+ return isIDN, punycodeDomain, nil
|
|
|
}
|