Rate Limiter Strategy
The rate limiter proactive resilience strategy controls the number of operations that can pass through it. This strategy is built on top of theSystem.Threading.RateLimiting API.
The rate limiter strategy resides in the Polly.RateLimiting package, not in Polly.Core like other strategies.
When to Use Rate Limiter
Use the rate limiter strategy when:- Protecting your API from being overwhelmed by too many requests
- Implementing fair usage policies across multiple clients
- Controlling outbound calls to rate-limited external APIs
- Preventing resource exhaustion from excessive concurrent operations
- Implementing token bucket, sliding window, or fixed window rate limiting
Installation
Rate Limiter Types
Polly supports several rate limiter types:- Concurrency Limiter: Limits the number of concurrent operations
- Fixed Window: Allows a fixed number of operations per time window
- Sliding Window: Smooths rate limiting across overlapping time segments
- Token Bucket: Uses tokens that regenerate over time
- Partitioned: Different rate limits per key (e.g., per user)
Usage
Basic Concurrency Limiter
Sliding Window Rate Limiter
Fixed Window Rate Limiter
Token Bucket Rate Limiter
With OnRejected Event
Configuration Options
Func<OnRateLimiterArguments, ValueTask<RateLimitLease>>
default:"null"
Dynamically creates a
RateLimitLease for executions. Allows for custom rate limiting logic.ConcurrencyLimiterOptions
default:"PermitLimit: 1000, QueueLimit: 0"
If
RateLimiter is not provided, uses these options for the default concurrency limiter.Func<OnRateLimiterRejectedArguments, ValueTask>
default:"null"
Invoked after the limiter rejected an execution, before throwing
RateLimiterRejectedException.Advanced Scenarios
Partitioned Rate Limiter (Per-User)
Chained Rate Limiters
Combine multiple rate limiters for complex scenarios:Custom Rate Limiter Logic
Proper Disposal
When using dynamic reloads or manual rate limiter creation, ensure proper disposal:Best Practices
Choose the right limiter type
Choose the right limiter type
- Concurrency Limiter: Limit simultaneous operations (database connections, API calls)
- Fixed Window: Simple rate limiting with defined time windows
- Sliding Window: Smoother rate limiting, prevents burst at window edges
- Token Bucket: Allows bursts while maintaining average rate
- Partitioned: Different limits per user/tenant/key
Configure queue limits appropriately
Configure queue limits appropriately
Set
QueueLimit based on acceptable latency:- 0: Reject immediately when limit reached
- Small value: Low latency, but more rejections
- Large value: Fewer rejections, but higher latency
Use partitioned limiters for multi-tenant scenarios
Use partitioned limiters for multi-tenant scenarios
Prevent one user/tenant from consuming all resources:
Handle RetryAfter in responses
Handle RetryAfter in responses
When catching
RateLimiterRejectedException, check for RetryAfter and respect it:Monitor rate limiter metrics
Monitor rate limiter metrics
Use
OnRejected to track rejections and adjust limits:Don't use rate limiter for retry delay
Don't use rate limiter for retry delay
Rate limiter is for controlling load, not for implementing retry delays. Use the Retry strategy for that.
Examples
API Rate Limiting Middleware
External API Client with Rate Limiting
Database Connection Pool Management
What's the difference between Concurrency Limiter and Rate Limiter?
What's the difference between Concurrency Limiter and Rate Limiter?
- Concurrency Limiter: Limits simultaneous operations (e.g., max 10 concurrent requests)
- Rate Limiter: Limits operations over time (e.g., max 100 requests per minute)
Can I use multiple rate limiters in one pipeline?
Can I use multiple rate limiters in one pipeline?
Yes! You can either:
- Chain multiple
AddRateLimitercalls (they’ll be applied in sequence) - Use
PartitionedRateLimiter.CreateChainedto combine multiple limiters
How do I implement per-user rate limiting?
How do I implement per-user rate limiting?
Use
PartitionedRateLimiter with the user ID as the partition key. Store the user ID in the ResilienceContext.Properties and extract it in the partition selector.Should I use rate limiting for retry delays?
Should I use rate limiting for retry delays?
No. Rate limiter is for controlling load and preventing overuse. Use the Retry strategy’s delay configuration for retry timing.