.NET 7 Rate Limit by real IP from Cloudflare?

AG 521 Reputation points
2022-10-25T06:29:19.207+00:00

Hi,

I can see that .NET 7 now support Rate Limiting and I wounder if it support the real IP address of the consumer that Cloudflare is sending with each request in a Header name CF-Connecting-IP ?

Thanks,
AG

Developer technologies | ASP.NET | ASP.NET Core
0 comments No comments
{count} votes

4 answers

Sort by: Most helpful
  1. Bruce (SqlWork.com) 77,766 Reputation points Volunteer Moderator
    2022-10-25T16:33:30.24+00:00

    rate limit is just an api. your code supplies the implementation.

    0 comments No comments

  2. AG 521 Reputation points
    2022-10-30T12:29:51.373+00:00

    Will be much appreciated for a starting point how to "tell" .NET 7 Rate Limiter to take the real IP from CF-Connecting-IP header on each request.
    I am currently using https://gist.github.com/jjxtra/3b240b31a1ed3ad783a7dcdb6df12c36 Extension in my other code but I have no starting point how to for .NET 7 Rate Limiter.

    Thanks,
    AG


  3. AG 521 Reputation points
    2022-11-10T10:44:49.72+00:00

    Hi @Bruce (SqlWork.com)

    I would like to rate limit based on the real IP of the connected client where Cloudflare sends in a Header "CF-Connecting-IP" based on your code I have tried using httpContext.Request.Headers["CF-Connecting-IP"].ToString() and the Extension method like this httpContext.GetCloudflareIPAddress().ToString() but when trying to connect using my PC and my other PC with VPN so they are two difference IP's rate limiting is acting like I am arriving from one IP so when IP1 is blocked also IP2 is blocked where IP2 should be free to make requests as it doesn't reached the limit yet.

    builder.Services.AddRateLimiter(options =>  
    {  
        options.RejectionStatusCode = 429;  
        options.GlobalLimiter = PartitionedRateLimiter.Create<HttpContext, string>(httpContext =>  
            RateLimitPartition.GetFixedWindowLimiter(  
                //partitionKey: httpContext.Request.Headers["CF-Connecting-IP"].ToString(),  
                partitionKey: httpContext.GetCloudflareIPAddress().ToString(),  
                factory: partition => new FixedWindowRateLimiterOptions  
                {  
                    AutoReplenishment = true,  
                    PermitLimit = 5,  
                    QueueLimit = 0,  
                    Window = TimeSpan.FromSeconds(30)  
                }));  
    });  
    

    I would also like to add policies based rate limiting in order to set them to a specific Controller\Action for example [EnableRateLimitingAttribute("API")] so I have tried the following code but this is not working like the above problem.

    builder.Services.AddRateLimiter(options =>  
    {  
        options.RejectionStatusCode = 429;  
        options.AddPolicy("API", httpContext =>  
        RateLimitPartition.GetFixedWindowLimiter(httpContext.Request.Headers["CF-Connecting-IP"].ToString(),  
        partition => new FixedWindowRateLimiterOptions  
        {  
            AutoReplenishment = true,  
            PermitLimit = 5,  
            Window = TimeSpan.FromSeconds(30)  
        }));  
    });  
    
    
    app.MapControllers().RequireRateLimiting("API");  
    

    Regards,
    AG

    0 comments No comments

  4. AG 521 Reputation points
    2022-11-11T10:44:43.05+00:00

    Some more research leads me to the following code for my API MVC.

    At Program.cs file:

    builder.Services.AddRateLimiter(options =>  
    {  
        options.RejectionStatusCode = 429;  
        options.AddPolicy("API", httpContext =>  
        RateLimitPartition.GetFixedWindowLimiter(httpContext.Request.Headers["CF-Connecting-IP"].ToString(),  
        partition => new FixedWindowRateLimiterOptions  
        {  
            AutoReplenishment = true,  
            PermitLimit = 5,  
            Window = TimeSpan.FromSeconds(10)  
        }));  
    });  
    
     
    app.UseRateLimiter();  
    

    At WeatherForecastController.cs files:

    [HttpGet]  
            [EnableRateLimiting("API")]  
            public IEnumerable<WeatherForecast> Get()  
            {  
                  
                return Enumerable.Range(1, 5).Select(index => new WeatherForecast  
                {  
                    Date = DateTime.Now.AddDays(index),  
                    TemperatureC = Random.Shared.Next(-20, 55),  
                    Summary = Summaries[Random.Shared.Next(Summaries.Length)]  
                })  
                .ToArray();  
            }  
    

    Regards,
    AG

    0 comments No comments

Your answer

Answers can be marked as Accepted Answers by the question author, which helps users to know the answer solved the author's problem.