项目文件夹

文件
2026-07-14 10:24:10 +08:00

95 行
3.3 KiB
Go

此文件含有模棱两可的 Unicode 字符
此文件含有可能会与其他字符混淆的 Unicode 字符。 如果您是想特意这样的,可以安全地忽略该警告。 使用 Escape 按钮显示他们。
package middleware
import "testing"
// 回归 C7a:通配符子域匹配必须锚定真实子域边界,拒绝后缀相同但非子域的域名。
// 旧实现 strings.HasSuffix(origin, domain) 接受 notexample.com / evil-example.com。
func TestMatchOriginWildcardBoundary(t *testing.T) {
cases := []struct {
name string
origin string
ao string
want bool
}{
// 精确匹配
{"exact", "https://example.com", "https://example.com", true},
{"exact with port", "https://example.com:8443", "https://example.com:8443", true},
{"exact mismatch", "https://example.com", "https://other.com", false},
// 通配子域 *.example.com
{"subdomain ok", "https://a.example.com", "*.example.com", true},
{"deep subdomain ok", "https://a.b.example.com", "*.example.com", true},
{"subdomain with port ok", "https://a.example.com:3000", "*.example.com", true},
{"apex not matched by wildcard", "https://example.com", "*.example.com", false},
// C7a 核心:后缀相同但非真实子域必须拒绝
{"notexample.com rejected", "https://notexample.com", "*.example.com", false},
{"evil-example.com rejected", "https://evil-example.com", "*.example.com", false},
{"villainexample.com rejected", "https://villainexample.com", "*.example.com", false},
// 端口/协议不同的 origin host 仍按 host 判断
{"http subdomain ok", "http://a.example.com", "*.example.com", true},
// 通配仅匹配 host,scheme 不同的精确配置不被通配覆盖
{"different scheme exact not wildcard", "http://example.com", "https://example.com", false},
// 边界
{"empty origin", "", "*.example.com", false},
{"empty ao", "https://a.example.com", "", false},
{"malformed origin", "://:bad", "*.example.com", false},
}
for _, c := range cases {
t.Run(c.name, func(t *testing.T) {
got := matchOrigin(c.origin, c.ao)
if got != c.want {
t.Errorf("matchOrigin(%q, %q) = %v, want %v", c.origin, c.ao, got, c.want)
}
})
}
}
// 回归 C7a:通配大小写不敏感(host 归一化为小写比较)。
func TestMatchOriginCaseInsensitive(t *testing.T) {
if !matchOrigin("https://A.Example.COM", "*.example.com") {
t.Error("matchOrigin should be case-insensitive on host")
}
}
// 回归 C7atrailing dot FQDNa.example.com.)应等同 a.example.com 被接受(功能正确性)。
func TestMatchOriginTrailingDot(t *testing.T) {
if !matchOrigin("https://a.example.com.", "*.example.com") {
t.Error("trailing-dot subdomain should match wildcard")
}
if !matchOrigin("https://a.example.com", "*.example.com.") {
t.Error("trailing-dot wildcard should match plain subdomain")
}
}
// 回归 C7bisLocalhostOrigin 仅允许 localhost/127.0.0.1/::1,拒绝任意其他来源。
func TestIsLocalhostOrigin(t *testing.T) {
allowed := []string{
"http://localhost:3000",
"http://localhost",
"http://127.0.0.1:8080",
"http://127.0.0.1",
"http://[::1]:4000",
"http://[::1]",
}
for _, o := range allowed {
if !isLocalhostOrigin(o) {
t.Errorf("isLocalhostOrigin(%q) = false, want true", o)
}
}
denied := []string{
"https://evil.com",
"https://localhost.evil.com", // 后缀含 localhost 但非 localhost host
"https://notlocalhost.com",
"https://example.com",
"",
"://bad",
}
for _, o := range denied {
if isLocalhostOrigin(o) {
t.Errorf("isLocalhostOrigin(%q) = true, want false", o)
}
}
}