推荐使用.NET 7+内置Microsoft.AspNetCore.RateLimiting包,通过AddRateLimiter注册策略、UseRateLimiter启用中间件,并用[EnableRateLimiting]特性应用到控制器或方法,支持Fixed Window、Sliding Window等算法及自定义限流键。

ASP.NET Core 中实现速率限制(Rate Limiting)推荐使用官方内置的 Microsoft.AspNetCore.RateLimiting 包(.NET 7+ 原生支持),它比第三方库更轻量、更集成、更易配置。
启用 Rate Limiting 中间件
在 Program.cs 中注册并启用中间件:
- 调用
AddRateLimiter()添加服务,可配置多种策略 - 调用
UseRateLimiter()启用中间件(必须放在UseAuthorization()之后、UseEndpoints()之前)
示例:
// Program.cs
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddRateLimiter(options =>
{
options.AddFixedWindowLimiter("fixed", opt =>
{
opt.Window = TimeSpan.FromSeconds(60);
opt.PermitLimit = 10;
opt.QueueProcessingOrder = QueueProcessingOrder.OldestFirst;
opt.QueueLimit = 5;
});
});
// ... 其他服务注册
var app = builder.Build();
app.UseRateLimiter(); // ⚠️ 位置很重要
app.UseAuthentication();
app.UseAuthorization();
app.MapControllers();
app.Run();
为控制器或方法应用限流策略
使用 [EnableRateLimiting("policy-name")] 特性标记端点:
- 可加在 Controller 类上(全局生效),也可加在单个 Action 方法上(更精细)
- 策略名必须与
AddRateLimiter中注册的名称一致 - 未标记的端点默认不受限
示例:
[ApiController]
[Route("api/[controller]")]
[EnableRateLimiting("fixed")] // 整个控制器启用
public class ValuesController : ControllerBase
{
[HttpGet]
public IActionResult Get() => Ok(new[] { "a", "b" });
[HttpPost]
[DisableRateLimiting] // 可对个别方法禁用
public IActionResult Post() => Ok();
}
支持的限流算法及配置要点
内置策略包括 Fixed Window、Sliding Window、Token Bucket,常用的是前两种:
- Fixed Window:简单高效,但存在窗口边界突增问题(如每分钟10次,0:59和1:00各来10次 → 实际20次)
- Sliding Window:更精准(如每60秒最多10次),适合高一致性要求场景,但需存储支持(如 Redis)
- 策略可指定
KeyGenerator自定义限流键,例如按 IP、用户 ID 或请求头区分
Sliding Window 示例:
options.AddSlidingWindowLimiter("sliding", opt =>
{
opt.Window = TimeSpan.FromMinutes(1);
opt.SegmentsPerWindow = 12; // 拆成12段(每5秒一段)
opt.PermitLimit = 10;
opt.QueueLimit = 3;
});
自定义限流键(按用户/IP/租户区分)
默认按客户端 IP 限流,可通过 KeyGenerator 改为按用户身份、请求头等维度:
- 返回字符串作为唯一键,相同键共享配额
- 例如:登录用户用
HttpContext.User.FindFirst(ClaimTypes.NameIdentifier)?.Value - 注意空值处理,避免 null 引发异常
示例(按用户 ID):
options.AddFixedWindowLimiter("per-user", opt =>
{
opt.Window = TimeSpan.FromMinutes(1);
opt.PermitLimit = 5;
opt.KeyGenerator = async context =>
{
var userId = context.User?.FindFirst(ClaimTypes.NameIdentifier)?.Value ?? "anonymous";
return userId;
};
});
基本上就这些。官方 Rate Limiting 中间件开箱即用,无需额外存储(Fixed Window 内存即可),配合策略配置和特性标注,就能快速落地生产级限流能力。










