From 1a05a5a951a60f960855cfb29c3982eb20086f1d Mon Sep 17 00:00:00 2001 From: Guillaume Calmettes Date: Wed, 9 Oct 2024 20:28:57 +0200 Subject: [PATCH] feat: can configure min hitsaddend value Signed-off-by: Guillaume Calmettes --- src/limiter/base_limiter.go | 4 +++- src/memcached/cache_impl.go | 7 ++++--- src/redis/cache_impl.go | 1 + src/redis/fixed_cache_impl.go | 6 +++--- src/settings/settings.go | 1 + test/integration/dump.rdb | Bin 981 -> 131 bytes test/limiter/base_limiter_test.go | 24 ++++++++++++------------ test/memcached/cache_impl_test.go | 14 +++++++------- test/redis/bench_test.go | 2 +- test/redis/fixed_cache_impl_test.go | 16 ++++++++-------- 10 files changed, 40 insertions(+), 35 deletions(-) diff --git a/src/limiter/base_limiter.go b/src/limiter/base_limiter.go index 18f0b83d3..f84f7de6f 100644 --- a/src/limiter/base_limiter.go +++ b/src/limiter/base_limiter.go @@ -22,6 +22,7 @@ type BaseRateLimiter struct { localCache *freecache.Cache nearLimitRatio float32 StatsManager stats.Manager + HitsAddendMinValue uint32 } type LimitInfo struct { @@ -143,7 +144,7 @@ func (this *BaseRateLimiter) GetResponseDescriptorStatus(key string, limitInfo * } func NewBaseRateLimit(timeSource utils.TimeSource, jitterRand *rand.Rand, expirationJitterMaxSeconds int64, - localCache *freecache.Cache, nearLimitRatio float32, cacheKeyPrefix string, statsManager stats.Manager, + localCache *freecache.Cache, nearLimitRatio float32, cacheKeyPrefix string, statsManager stats.Manager, hitsAddendMinValue uint32, ) *BaseRateLimiter { return &BaseRateLimiter{ timeSource: timeSource, @@ -153,6 +154,7 @@ func NewBaseRateLimit(timeSource utils.TimeSource, jitterRand *rand.Rand, expira localCache: localCache, nearLimitRatio: nearLimitRatio, StatsManager: statsManager, + HitsAddendMinValue: hitsAddendMinValue, } } diff --git a/src/memcached/cache_impl.go b/src/memcached/cache_impl.go index d4f65f75b..f3fe9a719 100644 --- a/src/memcached/cache_impl.go +++ b/src/memcached/cache_impl.go @@ -71,7 +71,7 @@ func (this *rateLimitMemcacheImpl) DoLimit( logger.Debugf("starting cache lookup") // request.HitsAddend could be 0 (default value) if not specified by the caller in the Ratelimit request. - hitsAddend := utils.Max(1, request.HitsAddend) + hitsAddend := utils.Max(this.baseRateLimiter.HitsAddendMinValue, request.HitsAddend) // First build a list of all cache keys that we are actually going to hit. cacheKeys := this.baseRateLimiter.GenerateCacheKeys(request, limits, hitsAddend) @@ -302,7 +302,7 @@ func runAsync(task func()) { } func NewRateLimitCacheImpl(client Client, timeSource utils.TimeSource, jitterRand *rand.Rand, - expirationJitterMaxSeconds int64, localCache *freecache.Cache, statsManager stats.Manager, nearLimitRatio float32, cacheKeyPrefix string, + expirationJitterMaxSeconds int64, localCache *freecache.Cache, statsManager stats.Manager, nearLimitRatio float32, cacheKeyPrefix string, hitsAddendMinValue uint32, ) limiter.RateLimitCache { return &rateLimitMemcacheImpl{ client: client, @@ -311,7 +311,7 @@ func NewRateLimitCacheImpl(client Client, timeSource utils.TimeSource, jitterRan expirationJitterMaxSeconds: expirationJitterMaxSeconds, localCache: localCache, nearLimitRatio: nearLimitRatio, - baseRateLimiter: limiter.NewBaseRateLimit(timeSource, jitterRand, expirationJitterMaxSeconds, localCache, nearLimitRatio, cacheKeyPrefix, statsManager), + baseRateLimiter: limiter.NewBaseRateLimit(timeSource, jitterRand, expirationJitterMaxSeconds, localCache, nearLimitRatio, cacheKeyPrefix, statsManager, hitsAddendMinValue), } } @@ -327,5 +327,6 @@ func NewRateLimitCacheImplFromSettings(s settings.Settings, timeSource utils.Tim statsManager, s.NearLimitRatio, s.CacheKeyPrefix, + s.HitsAddendMinValue, ) } diff --git a/src/redis/cache_impl.go b/src/redis/cache_impl.go index 30890786a..ff421f2bd 100644 --- a/src/redis/cache_impl.go +++ b/src/redis/cache_impl.go @@ -37,5 +37,6 @@ func NewRateLimiterCacheImplFromSettings(s settings.Settings, localCache *freeca s.CacheKeyPrefix, statsManager, s.StopCacheKeyIncrementWhenOverlimit, + s.HitsAddendMinValue, ), closer } diff --git a/src/redis/fixed_cache_impl.go b/src/redis/fixed_cache_impl.go index 8c551e0ce..f536f85a4 100644 --- a/src/redis/fixed_cache_impl.go +++ b/src/redis/fixed_cache_impl.go @@ -49,7 +49,7 @@ func (this *fixedRateLimitCacheImpl) DoLimit( logger.Debugf("starting cache lookup") // request.HitsAddend could be 0 (default value) if not specified by the caller in the RateLimit request. - hitsAddend := utils.Max(1, request.HitsAddend) + hitsAddend := utils.Max(this.baseRateLimiter.HitsAddendMinValue, request.HitsAddend) // First build a list of all cache keys that we are actually going to hit. cacheKeys := this.baseRateLimiter.GenerateCacheKeys(request, limits, hitsAddend) @@ -218,12 +218,12 @@ func (this *fixedRateLimitCacheImpl) Flush() {} func NewFixedRateLimitCacheImpl(client Client, perSecondClient Client, timeSource utils.TimeSource, jitterRand *rand.Rand, expirationJitterMaxSeconds int64, localCache *freecache.Cache, nearLimitRatio float32, cacheKeyPrefix string, statsManager stats.Manager, - stopCacheKeyIncrementWhenOverlimit bool, + stopCacheKeyIncrementWhenOverlimit bool, hitsAddendMinValue uint32, ) limiter.RateLimitCache { return &fixedRateLimitCacheImpl{ client: client, perSecondClient: perSecondClient, stopCacheKeyIncrementWhenOverlimit: stopCacheKeyIncrementWhenOverlimit, - baseRateLimiter: limiter.NewBaseRateLimit(timeSource, jitterRand, expirationJitterMaxSeconds, localCache, nearLimitRatio, cacheKeyPrefix, statsManager), + baseRateLimiter: limiter.NewBaseRateLimit(timeSource, jitterRand, expirationJitterMaxSeconds, localCache, nearLimitRatio, cacheKeyPrefix, statsManager, hitsAddendMinValue), } } diff --git a/src/settings/settings.go b/src/settings/settings.go index 9febf7d9b..7fd7cec2a 100644 --- a/src/settings/settings.go +++ b/src/settings/settings.go @@ -106,6 +106,7 @@ type Settings struct { CacheKeyPrefix string `envconfig:"CACHE_KEY_PREFIX" default:""` BackendType string `envconfig:"BACKEND_TYPE" default:"redis"` StopCacheKeyIncrementWhenOverlimit bool `envconfig:"STOP_CACHE_KEY_INCREMENT_WHEN_OVERLIMIT" default:"false"` + HitsAddendMinValue uint32 `envconfig:"DEFAULT_HITS_ADDEND_MIN_VALUE" default:"1"` // Settings for optional returning of custom headers RateLimitResponseHeadersEnabled bool `envconfig:"LIMIT_RESPONSE_HEADERS_ENABLED" default:"false"` diff --git a/test/integration/dump.rdb b/test/integration/dump.rdb index b5814b13a8df2f58767f6a6d7f9cf24e20969ff0..6c60e1985b15a58b7c5fc360216269d58ae9ae37 100644 GIT binary patch literal 131 zcmWG?b@2=~FfcUy#aWb^l3A=cL2a-7h^jZCfye{UY6^$ z4%wyRp*Nf)=|;BPpA5(L@cs8kyV-?<#16V+J3id_=zG~}80~eR$2J`IMmF_Myy@DS zd;NLk@yjL8^KORw(d4O(gJ<>?1xlbc97t#;v?Rlb0+c8@69|y{?&|$3bsRHb7$`tM zg;J0toae$XmkX}b3zK30pBe_Es2`4ky(l`J73q>Y`c`V-oVQ|HOASJ30;!DzrE<+v z8q$_~_r$MrC|S-Jt%VXsb2MB+m2115pQ{B|r>c}TLKw=kP%MX$Se5o2-MzI)vvR{` zns}b-ii7k2(dJwcqESL{i6mj6lMi-#abp%VcQRA;-Ts|YwO#3Ct_{fB_`12-yjioi za