Spring REST API: Handling Rate Limiting with Redis and Spring Boot
I need some guidance on I've encountered a strange issue with I'm learning this framework and I'm working on a project and hit a roadblock. I'm working on a Spring Boot REST API and I want to implement rate limiting to prevent abuse of my endpoints. I'm using Redis as my backend for storing the rate limit counters. I followed a tutorial and set up a simple filter to check the number of requests per user. However, I'm encountering a couple of issues. When testing, I find that the rate limit is not applied consistently; sometimes it allows more requests than specified. Here's the approach I'm using: ```java import org.springframework.stereotype.Component; import org.springframework.web.filter.OncePerRequestFilter; import javax.servlet.FilterChain; import javax.servlet.ServletException; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.io.IOException; import redis.clients.jedis.Jedis; @Component public class RateLimitFilter extends OncePerRequestFilter { private final Jedis jedis; public RateLimitFilter(Jedis jedis) { this.jedis = jedis; } @Override protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain) throws ServletException, IOException { String ipAddress = request.getRemoteAddr(); String key = "rate_limit:" + ipAddress; int limit = 100; long currentRequests = jedis.incr(key); if (currentRequests == 1) { jedis.expire(key, 60); // Set expiration time of 60 seconds } if (currentRequests > limit) { response.setStatus(HttpServletResponse.SC_TOO_MANY_REQUESTS); return; } filterChain.doFilter(request, response); } } ``` I've also configured Jedis in my Spring configuration: ```java import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import redis.clients.jedis.Jedis; @Configuration public class RedisConfig { @Bean public Jedis jedis() { return new Jedis("localhost", 6379); } } ``` When I run the application and make requests rapidly from the same IP, it seems to allow more than 100 requests within the 60-second window. I also see that sometimes the key in Redis doesnβt expire as expected. I've tried adding logging to see the values being set in Redis, and they seem to increment correctly, but the expiration doesn't appear to trigger. Is there something I'm missing in the configuration or implementation? Should I be using a different method to handle expiration or rate limiting? Any advice on best practices would be greatly appreciated! This is part of a larger CLI tool I'm building. Thanks in advance! The stack includes Java and several other technologies. I'm working in a CentOS environment. I've been using Java for about a year now. Hoping someone can shed some light on this.