-
Notifications
You must be signed in to change notification settings - Fork 0
/
limiter.go
95 lines (74 loc) · 1.39 KB
/
limiter.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
package limiter
import "time"
type Limiter interface {
Init(limit int) Limiter
Acquire()
Release()
Stop()
}
type NoLimiter struct {
}
func (n *NoLimiter) Init(limit int) Limiter {
return n
}
func (n *NoLimiter) Acquire() {
return
}
func (n *NoLimiter) Release() {
}
func (n *NoLimiter) Stop() {
}
func NewNoLimiter() Limiter {
return &NoLimiter{}
}
type PoolLimit struct {
poolSize int
bufferChan chan struct{}
}
func (p *PoolLimit) Init(limit int) Limiter {
p.poolSize = limit
p.bufferChan = make(chan struct{}, limit)
return p
}
func (p *PoolLimit) Acquire() {
p.bufferChan <- struct{}{}
}
func (p *PoolLimit) Release() {
<-p.bufferChan
}
func (p *PoolLimit) Stop() {
p.poolSize = 0
close(p.bufferChan)
}
func NewPoolLimit(limit int) Limiter {
return (&PoolLimit{}).Init(limit)
}
type TimeLimiter struct {
StartTime time.Time
Tick *time.Ticker
LimitChan chan struct{}
}
func NewTimeLimiter(limit int) Limiter {
return (&TimeLimiter{}).Init(limit)
}
func (t *TimeLimiter) Init(limit int) Limiter {
t.Tick = time.NewTicker(time.Second / time.Duration(limit))
t.StartTime = time.Now()
t.LimitChan = make(chan struct{}, 1)
go func() {
for _ = range t.Tick.C {
t.LimitChan <- struct{}{}
}
}()
return t
}
func (t *TimeLimiter) Acquire() {
<-t.LimitChan
}
func (t *TimeLimiter) Release() {
return
}
func (t *TimeLimiter) Stop() {
close(t.LimitChan)
t.Tick.Stop()
}