chanfitness: cool down flap count for rate limiting
Since we store all-time flap count for a peer, we add a cooldown factor which will discount poor flap counts in the past. This is only applied to peers that have not flapped for at least a cooldown period, so that we do not downgrade our rate limiting for badly behaved peers.
This commit is contained in:
4 files changed
+155
-5
No files matched your search
@@ -1,11 +1,25 @@
|
||||
package chanfitness
|
||||
|
||||
import "time"
|
||||
import (
|
||||
"math"
|
||||
"time"
|
||||
)
|
||||
|
||||
// rateLimitScale is the number of events we allow per rate limited tier.
|
||||
// Increasing this value makes our rate limiting more lenient, decreasing it
|
||||
// makes us less lenient.
|
||||
const rateLimitScale = 200
|
||||
const (
|
||||
// rateLimitScale is the number of events we allow per rate limited
|
||||
// tier. Increasing this value makes our rate limiting more lenient,
|
||||
// decreasing it makes us less lenient.
|
||||
rateLimitScale = 200
|
||||
|
||||
// flapCountCooldownFactor is the factor by which we decrease a peer's
|
||||
// flap count if they have not flapped for the cooldown period.
|
||||
flapCountCooldownFactor = 0.95
|
||||
|
||||
// flapCountCooldownPeriod is the amount of time that we require a peer
|
||||
// has not flapped for before we reduce their all time flap count using
|
||||
// our cooldown factor.
|
||||
flapCountCooldownPeriod = time.Hour * 8
|
||||
)
|
||||
|
||||
// rateLimits is the set of rate limit tiers we apply to our peers based on
|
||||
// their flap count. A peer can be placed in their tier by dividing their flap
|
||||
@@ -35,3 +49,34 @@ func getRateLimit(flapCount int) time.Duration {
|
||||
|
||||
return rateLimits[tier]
|
||||
}
|
||||
|
||||
// cooldownFlapCount takes a timestamped flap count, and returns its value
|
||||
// scaled down by our cooldown factor if at least our cooldown period has
|
||||
// elapsed since the peer last flapped. We do this because we store all-time
|
||||
// flap count for peers, and want to allow downgrading of peers that have not
|
||||
// flapped for a long time.
|
||||
func cooldownFlapCount(now time.Time, flapCount int,
|
||||
lastFlap time.Time) int {
|
||||
|
||||
// Calculate time since our last flap, and the number of times we need
|
||||
// to apply our cooldown factor.
|
||||
timeSinceFlap := now.Sub(lastFlap)
|
||||
|
||||
// If our cooldown period has not elapsed yet, we just return our flap
|
||||
// count. We allow fractional cooldown periods once this period has
|
||||
// elapsed, so we do not want to apply a fractional cooldown before the
|
||||
// full cooldown period has elapsed.
|
||||
if timeSinceFlap < flapCountCooldownPeriod {
|
||||
return flapCount
|
||||
}
|
||||
|
||||
// Get the factor by which we need to cooldown our flap count. If
|
||||
// insufficient time has passed to cooldown our flap count. Use use a
|
||||
// float so that we allow fractional cooldown periods.
|
||||
cooldownPeriods := float64(timeSinceFlap) /
|
||||
float64(flapCountCooldownPeriod)
|
||||
|
||||
effectiveFactor := math.Pow(flapCountCooldownFactor, cooldownPeriods)
|
||||
|
||||
return int(float64(flapCount) * effectiveFactor)
|
||||
}
|
||||
Reference in new issue
Block a user