Files
4566704 45864a61dd feat(rate): 自 go-hua 迁入秒级带宽限速器
- 按秒配额补充令牌, Add 阻塞限速, 配合 conn 使用; 附测试、例程与 README
2026-09-20 12:25:36 +08:00

80 lines
1.7 KiB
Go

package rate
import (
"sync/atomic"
"testing"
"time"
)
func TestNewRateLimitConvert(t *testing.T) {
// 10 Mbps = 10*1024*1024/8 = 1310720 字节/秒
r := NewRate(10)
if r.Limit != 1310720 {
t.Errorf("Limit = %d, want 1310720", r.Limit)
}
if r.Surplus != 1310720 {
t.Errorf("初始 Surplus = %d, want 1310720", r.Surplus)
}
}
func TestSetLimit(t *testing.T) {
r := NewRate(10)
r.SetLimit(0)
if r.Limit != 0 {
t.Errorf("SetLimit(0) 后 Limit = %d, want 0", r.Limit)
}
r.SetLimit(1)
if r.Limit != 1*1024*1024/8 {
t.Errorf("SetLimit(1) 后 Limit = %d, want %d", r.Limit, 1*1024*1024/8)
}
}
func TestAddWithoutLimit(t *testing.T) {
r := NewRate(0) // 不限速
done := make(chan struct{})
go func() {
r.Add(1 << 20)
close(done)
}()
select {
case <-done:
case <-time.After(time.Second):
t.Error("不限速时 Add 阻塞了")
}
}
func TestAddConsumeQuota(t *testing.T) {
r := NewRate(1) // 1 Mbps = 131072 字节/秒
r.Add(1000)
if got := atomic.LoadInt32(&r.Surplus); got != 131072-1000 {
t.Errorf("Add 后 Surplus = %d, want %d", got, 131072-1000)
}
}
func TestStartStopReset(t *testing.T) {
r := NewRate(1)
r.Start()
r.Add(500)
// 等待配额重置(每秒一次)
time.Sleep(1100 * time.Millisecond)
if got := atomic.LoadInt32(&r.Surplus); got != 131072 {
t.Errorf("重置后 Surplus = %d, want 131072", got)
}
// Stop 应正常返回(IsStop 通道已在 NewRate 中初始化)
r.Stop()
// 重复 Stop 不应 panic:第二次发送时 proc 协程已退出,会阻塞,故放入独立协程
done := make(chan struct{})
go func() {
defer close(done)
r.Stop()
}()
select {
case <-done:
case <-time.After(time.Second):
t.Log("proc 协程已退出,第二次 Stop 阻塞(属预期)")
}
}