“This article has participated in the good article call order activity, click to see: back end, big front end double track submission, 20,000 yuan prize pool for you to challenge!”
The introduction
Traffic limiting is a requirement that is often encountered in the use of external Api services.
Limiting the frequency of client access can effectively prevent the risk that the client will use scripts or other destructive methods to affect the normal operation of the service.
There are many ways to limit traffic. The simplest way is to restrict Ip access. Ip access records can be stored in memory or other high-speed data storage services.
Of course, we will certainly not build any wheel in the development, both a waste of time, error probability is large, not comprehensive consideration. So choosing the right wheel is very important, and today I recommend AspNetCoreRateLimit, an ASP.NET Core rate limiting solution
AspNetCoreRateLimit introduction
AspNetCoreRateLimit is an ASP.NET Core rate limiting solution designed to control the rate at which clients make requests to Web API or MVC applications based on IP address or client ID. AspNetCoreRateLimit contains a IpRateLimitMiddleware and ClientRateLimitMiddleware, every middleware can according to the different scenarios with limit allows IP or client, custom these limit the strategy, You can also apply a restriction policy to each API URL or specific HTTP Method.
Nuget package
Nuget package reference, AspNetCoreRateLimit version 3.2.2 at the time of article use.
Install-Package AspNetCoreRateLimit
Copy the code
Configuration instructions
General Ip configuration rules
IpRateLimiting
The name of the | type | instructions |
---|---|---|
EnableEndpointRateLimiting | bool | False applies the restriction globally, and only rules that have an endpoint * are applied. For example, if you set a limit of five calls per second, then any HTTP calls to any endpoint will count toward that limit true and the limit will apply to each endpoint, such as {HTTP_Verb}{PATH}. For example, if you set a limit of 5 calls per second for the *:/ API /values client |
StackBlockedRequests | bool | False Rejected API calls are not added to the call count; If the client makes three requests per second and you set a limit of one call per second, other limits such as a per-minute or per-day counter will only record the first call, the successful API call |
RealIpHeader | string | The back of the server is a reverse proxy, if your proxy server uses a different header then extract the client IP x-real-IP use this option to set it |
ClientIdHeader | string | Obtains the ID of the whitelist client. If there is a client ID in this header and it matches the value specified in the ClientWhitelist, no rate limit is applied. |
HttpStatusCode | string | Restricted status code |
IpWhitelist | string | IP whitelist: Supports IP V4 and V6 |
EndpointWhitelist | string | Endpoint whitelist |
ClientWhitelist | string | White Client whitelist |
GeneralRules | json | General rules |
QuotaExceededResponse | json | “QuotaExceededResponse”: {” Content”: “{{“code”:429,” MSG “:” too often, please try again later “,”data”:null}}”, “ContentType”: “application/json”, “StatusCode”: 200 } |
For details, see the following configuration files: The IP address restriction applies to all global Settings. The rule is three access times every five seconds
{ "IpRateLimiting": { "EnableEndpointRateLimiting": false, "StackBlockedRequests": false, "RealIpHeader": "X-real-ip ", "ClientIdHeader":" X-Clientid ", "HttpStatusCode": 429, ////IP whitelist: support IP V4 and V6 "IpWhitelist": [" 127.0.0.1 "], "GeneralRules" : [{" Endpoint ":" * ", "Period" : "5 s", "Limit" : 3}]}}Copy the code
GeneralRules
The name of the | type | instructions |
---|---|---|
Endpoint | string | The endpoint path |
Period | string | Period, format: {number}{unit}; Available units: S, m, H, d |
Limit | string | Call limit |
EndPoint
Endpoint format :{HTTP_Verb}:{PATH}, you can use asterix symbols to locate any HTTP predicate.
Period
Period format: {INT}{PERIOD_TYPE}, you can use one of the following period types: s, m, h, d.
Limit
Restricted format: {LONG}
Configuration Rule Reference
"GeneralRules" : [/ / 1 seconds can only access 2 times {" Endpoint ":" * ", "Period" : "1 s", / / limits "Limit", 2}, {/ / 15 minutes can only call 100 times "Endpoint" : "*", "Period", "15 m", "Limit" : 100}, 12 h can call 1000 / / {" Endpoint ":" * ", "Period" : "12 h", "Limit" : 1000}, can call 10000 times 7 days / / {" Endpoint ":" * ", "Period" : "7 d", "Limit" : 10000}, / / API/rateLimit/GetDateTime interface rules for 5 seconds at most visit three {" Endpoint ":" * : / API/rateLimit GetDateTime ", "Period" : "5s", "Limit": 3 } ]Copy the code
Special Ip restriction rules
"IpRateLimitPolicies": {//IP Rules" IpRules": [{//IP "IP ": "84.247.85.224", // Rule content "Rules": [//1s requests 10 times {"Endpoint": "*", "Period" : "1 s", "Limit" : 10}, / / 15 minutes request 200 {" Endpoint ":" * ", "Period" : "15 m", "Limit" : 200}}, {/ / IP support set up multiple "IP" : "192.168.3.22/25", "Rules" : [/ / 1 second request 5 times {" Endpoint ":" * ", "Period" : "1 s", "Limit" : 5}, / / 15 minutes request {150 times "Endpoint" : "*", "Period", "15 m", "Limit" : 150}, 12 hours / / request 500 {" Endpoint ":" * ", "Period" : "12 h", "Limit" : 500}]]}}Copy the code
I believe that after reading the general Ip configuration rules of the small partners to see this section of the configuration should not have any pressure, I will not do much explanation here.
This code is enabled in the ConfigureService to use special Ip restriction rules
// Load the IP limit custom policy, that is, for a specific IP limit, //services.Configure<IpRateLimitPolicies>(configuration.getSection ("IpRateLimitPolicies"));Copy the code
Encoding to use
With the ground rules in mind, we start coding
1. Inject services
Because of the large amount of injected content involved, we use an extension method to identify the content that the Ip limiting service needs to inject.
public static class RateLimitedConfigureService { public static void RateLimitedConfig(this IServiceCollection services, {// configuration of IConfiguration mode services.addOptions (); // Memory rate limit calculator and IP rule services.addMemoryCache (); // Configure<IpRateLimitOptions>(configuration.getSection ("IpRateLimiting")); // Configure<IpRateLimitOptions>(configuration. // Load the IP limit custom policy, that is, for a specific IP limit, //services.Configure<IpRateLimitPolicies>(configuration.getSection ("IpRateLimitPolicies")); AddSingleton<IIpPolicyStore, MemoryCacheIpPolicyStore>(); services.AddSingleton<IRateLimitCounterStore, MemoryCacheRateLimitCounterStore>(); AddSingleton<IHttpContextAccessor, HttpContextAccessor>(); AddSingleton<IRateLimitConfiguration, RateLimitConfiguration>(); }}Copy the code
1.1 Configuring Services
Public void ConfigureServices (IServiceCollection services) {/ / Ip restrictions configuration services. RateLimitedConfig (_configuration); services.AddControllers(); }Copy the code
1.2 Enabling Pipes
public void Configure(IApplicationBuilder app, IWebHostEnvironment env) { if (env.IsDevelopment()) { app.UseDeveloperExceptionPage(); } app.UseRouting(); // Pipeline events enable client IP limiting rate app.useipratelimiting (); }Copy the code
2. Write an Api
/// </summary> [Route(" API /rateLimit")] [ApiController] public class RateLimitController: Controller { [HttpGet("GetDateTime")] public string GetDateTime() { return DateTime.Now.ToString("d"); }}Copy the code
3, test,
Normal request
Call http://localhost:5000/api/ratelimit/getdatetime request interface, returns the current date.
If we look at the ResponseHeaders at F12, we can see that we have three more parameters
X-rate-limit-limit Specifies the time Limit
X-rate-limit-remaining Indicates the number of Remaining requests
X-rate-limit-reset Indicates the request Reset time
Every time x-rate-limit-remaining is called, subtract 1. When no number of requests can be called, an error is returned.
API calls quota exceeded! maximum admitted 3 per 5s.
Copy the code
Bad request
The page returns an error message when the number of requests falls outside the time limit. The returned content can also be customized. For details, see configuration rules
reference
Asp.NET Core flow limiting control -AspNetCoreRateLimit
NetCore combined with AspNetCoreRateLimit implements traffic limiting