修复:调整游客取号限流策略

问题:移动网络共享出口 IP 会造成游客取号被误限流。

实现:移除公开取号 IP 限制,改用项目总量与手机号 HMAC 限流,并支持 Retry-After 倒计时。
This commit is contained in:
2026-07-31 22:56:33 +08:00
parent 3f4a9bf398
commit c2a5281534
17 changed files with 357 additions and 73 deletions

View File

@@ -101,3 +101,40 @@ func TestPublicPhoneLookupRejectsInvalidPhone(t *testing.T) {
t.Fatalf("invalid phone lookup status = %d, want 422", recorder.Code)
}
}
func TestPublicTicketLimitsUseProjectAndPhoneDigest(t *testing.T) {
now := time.Unix(100, 0)
server := &Server{
publicTicketProjectLimiter: newQueryLimiter(func() time.Time { return now }, 10, time.Minute),
publicTicketPhoneLimiter: newQueryLimiter(func() time.Time { return now }, 1, time.Minute),
}
projectA := "11111111-1111-4111-8111-111111111111"
projectB := "22222222-2222-4222-8222-222222222222"
phoneDigest := strings.Repeat("a", 64)
if allowed, _ := server.allowPublicTicket(projectA, phoneDigest); !allowed {
t.Fatal("first project/phone request should be allowed")
}
if allowed, retry := server.allowPublicTicket(projectA, phoneDigest); allowed || retry <= 0 {
t.Fatalf("second request should be phone-limited, got allowed=%v retry=%s", allowed, retry)
}
if allowed, _ := server.allowPublicTicket(projectB, phoneDigest); !allowed {
t.Fatal("the same phone digest should have an independent limit in another project")
}
}
func TestPublicTicketLimitsEnforceProjectTotalAcrossPhones(t *testing.T) {
now := time.Unix(100, 0)
server := &Server{
publicTicketProjectLimiter: newQueryLimiter(func() time.Time { return now }, 1, time.Minute),
publicTicketPhoneLimiter: newQueryLimiter(func() time.Time { return now }, 10, time.Minute),
}
projectID := "11111111-1111-4111-8111-111111111111"
if allowed, _ := server.allowPublicTicket(projectID, strings.Repeat("a", 64)); !allowed {
t.Fatal("first project request should be allowed")
}
if allowed, retry := server.allowPublicTicket(projectID, strings.Repeat("b", 64)); allowed || retry <= 0 {
t.Fatalf("second phone should be limited by project total, got allowed=%v retry=%s", allowed, retry)
}
}