Mastering Redis Rate Limiting: 3 Practical Techniques for High‑Concurrency Backends
This article explains three Redis‑based rate‑limiting techniques—setnx with expiration, a sliding‑window implementation using sorted sets, and a token‑bucket algorithm with lists—complete with Java code examples and discussion of their advantages and limitations for high‑concurrency backend services.
Rate Limiting with Redis: setnx Approach
Using Redis' SETNX command together with an expiration time provides a simple distributed lock that can enforce a limit of N requests within a given time window. For example, setting an expiration of 10 seconds and allowing 20 successful SETNX calls achieves a 20‑request‑per‑10‑seconds limit. The main drawback is that it cannot easily produce a sliding window; implementing a sliding window would require maintaining multiple keys.
Sliding Window Using Redis ZSet
A sliding‑window algorithm can be built with Redis sorted sets ( ZSET). Each incoming request is added as a member with a unique UUID as the value and the current timestamp as the score. By querying the range of scores between now‑interval and now, we can count how many requests occurred in the last N seconds.
public Response limitFlow() {
Long currentTime = new Date().getTime();
System.out.println(currentTime);
if (redisTemplate.hasKey("limit")) {
Integer count = redisTemplate.opsForZSet()
.rangeByScore("limit", currentTime - intervalTime, currentTime)
.size(); // intervalTime is the rate‑limit period
System.out.println(count);
if (count != null && count > 5) {
return Response.ok("每分钟最多只能访问5次");
}
}
redisTemplate.opsForZSet().add("limit", UUID.randomUUID().toString(), currentTime);
return Response.ok("访问成功");
}This code achieves the sliding‑window effect, guaranteeing at most M requests per N seconds, but the sorted set can grow indefinitely as timestamps accumulate.
Token Bucket with Redis List
The token‑bucket algorithm can be implemented using a Redis list. Tokens are stored as unique identifiers (e.g., UUIDs). When a request arrives, LEFTPOP retrieves a token; if none is available, the request is rejected. A scheduled Java task periodically pushes new tokens into the list to replenish the bucket.
public Response limitFlow2(Long id) {
Object result = redisTemplate.opsForList().leftPop("limit_list");
if (result == null) {
return Response.ok("当前令牌桶中无令牌");
}
return Response.ok(articleDescription2);
} @Scheduled(fixedDelay = 10_000, initialDelay = 0)
public void setIntervalTimeTask() {
redisTemplate.opsForList().rightPush("limit_list", UUID.randomUUID().toString());
}These implementations are straightforward and can be integrated into an AOP interceptor or servlet filter to protect APIs. Beyond rate limiting, Redis offers many other data structures (e.g., GeoHash, BitMap, HyperLogLog, Bloom filters) that are useful for various backend scenarios.
Signed-in readers can open the original source through BestHub's protected redirect.
This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactand we will review it promptly.
Programmer DD
A tinkering programmer and author of "Spring Cloud Microservices in Action"
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.
