Class RateLimiter
java.lang.Object
com.loomcache.server.network.RateLimiter
- All Implemented Interfaces:
AutoCloseable
Production-quality rate limiter supporting multiple policies and per-client limiting.
Implements configurable rate limiting with:
- Token bucket algorithm (primary implementation)
- Per-client isolation with automatic stale entry cleanup
- Global rate limiting across all clients
- Multiple rate limit policies: FIXED_WINDOW, SLIDING_WINDOW, TOKEN_BUCKET
- Comprehensive metrics tracking (total, allowed, denied, per-client stats)
- Virtual thread compatible using ReentrantLock (not synchronized)
- AutoCloseable for clean resource management
Token bucket algorithm:
- Tokens accumulate at a configurable rate (requests/second)
- Each request consumes 1 token (configurable)
- Burst capacity allows temporary exceeding of steady-state rate
- Full bucket never exceeds burst capacity
Per-client limiting:
- Each client maintains independent token bucket
- Clients identified by string ID (e.g., IP address, client UUID)
- Stale entries auto-cleaned after a configurable inactivity threshold
- Memory-efficient with lazy initialization
Thread safety:
- All operations thread-safe using ReentrantLock
- Compatible with Java 25 virtual threads
- Atomic operations for metrics (no lock contention)
Usage example:
var limiter = new RateLimiter.Builder()
.globalRate(1000) // 1000 requests/sec globally
.globalBurst(2000) // Allow 2000 burst
.perClientRate(100) // 100 requests/sec per client
.perClientBurst(200) // Allow 200 burst per client
.cleanupIntervalSeconds(300) // Cleanup every 5 minutes
.build();
if (limiter.allowRequest("client-id")) {
processRequest();
} else {
rejectRequest("rate limited");
}
- Since:
- 1.0
-
Nested Class Summary
Nested ClassesModifier and TypeClassDescriptionstatic classBuilder for fluent RateLimiter construction.static final recordPer-client metrics snapshot.static final recordImmutable snapshot of rate limiter metrics.static interfaceSealed interface for rate limit policies. -
Method Summary
Modifier and TypeMethodDescriptionbooleanallowRequest(String clientId) Check if a request from a client is allowed under rate limits.booleanallowRequests(String clientId, int requestCount) Check if multiple requests are allowed (batched check).voidclose()Shutdown the rate limiter and clean up resources.intGet the number of actively tracked clients.@Nullable RateLimiter.ClientStatsgetClientStats(String clientId) Get per-client statistics.getStats()Get current rate limiter statistics snapshot.longGet global request allowed count.longGet global request denied count.longGet global request count.voidreset()Reset all metrics and client buckets.
-
Method Details
-
allowRequest
Check if a request from a client is allowed under rate limits.Checks both global and per-client rate limits. Request is allowed only if both limits permit it. Automatically creates per-client bucket on first request.
- Parameters:
clientId- unique client identifier (non-null)- Returns:
- true if request is allowed, false if rate limited
- Throws:
NullPointerException- if clientId is nullIllegalStateException- if limiter is closed
-
allowRequests
Check if multiple requests are allowed (batched check).- Parameters:
clientId- unique client identifier (non-null)requestCount- number of requests to check- Returns:
- true if all requests are allowed, false if any rate limited
-
getStats
Get current rate limiter statistics snapshot.- Returns:
- immutable statistics snapshot
-
getClientStats
Get per-client statistics.- Parameters:
clientId- unique client identifier (non-null)- Returns:
- client statistics, or null if client unknown
-
reset
public void reset()Reset all metrics and client buckets. -
getActiveClientCount
public int getActiveClientCount()Get the number of actively tracked clients.- Returns:
- client count
-
getTotalAllowed
public long getTotalAllowed()Get global request allowed count.- Returns:
- total requests allowed
-
getTotalDenied
public long getTotalDenied()Get global request denied count.- Returns:
- total requests denied
-
getTotalRequests
public long getTotalRequests()Get global request count.- Returns:
- total requests
-
close
public void close()Shutdown the rate limiter and clean up resources.Stops the background cleanup task. After close(), allowRequest() will throw.
- Specified by:
closein interfaceAutoCloseable
-