{"record":{"id":"7ee764e1859a0a1d","repo":"App-vNext/Polly","slug":"maxburst-must-be-an-integer-greater-than-or-equal","errorCode":null,"errorMessage":"maxBurst must be an integer greater than or equal to 1.","messagePattern":"maxBurst must be an integer greater than or equal to 1\\.","errorType":"exception","errorClass":"ArgumentOutOfRangeException","httpStatus":null,"severity":"error","filePath":"src/Polly/RateLimit/AsyncRateLimitSyntax.cs","lineNumber":42,"sourceCode":"    /// <returns>The policy instance.</returns>\n    public static AsyncRateLimitPolicy RateLimitAsync(\n        int numberOfExecutions,\n        TimeSpan perTimeSpan,\n        int maxBurst)\n    {\n        if (numberOfExecutions < 1)\n        {\n            throw new ArgumentOutOfRangeException(nameof(numberOfExecutions), numberOfExecutions, $\"{nameof(numberOfExecutions)} per timespan must be an integer greater than or equal to 1.\");\n        }\n\n        if (perTimeSpan <= TimeSpan.Zero)\n        {\n            throw new ArgumentOutOfRangeException(nameof(perTimeSpan), perTimeSpan, $\"{nameof(perTimeSpan)} must be a positive timespan.\");\n        }\n\n        if (maxBurst < 1)\n        {\n            throw new ArgumentOutOfRangeException(nameof(maxBurst), maxBurst, $\"{nameof(maxBurst)} must be an integer greater than or equal to 1.\");\n        }\n\n        var onePer = TimeSpan.FromTicks(perTimeSpan.Ticks / numberOfExecutions);\n\n        if (onePer <= TimeSpan.Zero)\n        {\n            throw new ArgumentOutOfRangeException(nameof(perTimeSpan), perTimeSpan, \"The number of executions per timespan must be positive.\");\n        }\n\n        IRateLimiter rateLimiter = new LockFreeTokenBucketRateLimiter(onePer, maxBurst);\n\n        return new AsyncRateLimitPolicy(rateLimiter);\n    }\n}\n","sourceCodeStart":24,"sourceCodeEnd":57,"githubUrl":"https://github.com/App-vNext/Polly/blob/d0e46bdb1ee11ea50d0e4b6846d2633d6bc09bac/src/Polly/RateLimit/AsyncRateLimitSyntax.cs#L24-L57","documentation":"Thrown by RateLimitAsync when maxBurst is less than 1. maxBurst is the bucket capacity (maximum executions permitted in a single burst after idle); zero or negative capacity makes the limiter unable to ever permit execution. This is the third sequential config guard.","triggerScenarios":"Calling Policy.RateLimitAsync(n, ts, 0) or with a negative maxBurst. Typically the value is derived from configuration without a lower bound.","commonSituations":"maxBurst sourced from an optional config key that defaults to 0; intentional 'disable burst' set to 0 not realizing it fully blocks execution; copying a config template that omitted the value.","solutions":["Set maxBurst to a positive integer (often equal to or greater than numberOfExecutions).","Clamp the config value: Math.Max(1, parsedBurst).","If you want to forbid bursts, set maxBurst = numberOfExecutions rather than 0.","Validate the full (numberOfExecutions, perTimeSpan, maxBurst) triple before constructing the policy."],"exampleFix":"// before\nvar p = Policy.RateLimitAsync(10, TimeSpan.FromSeconds(1), 0);\n\n// after\nvar p = Policy.RateLimitAsync(10, TimeSpan.FromSeconds(1), 10);","handlingStrategy":"validation","validationCode":"int burst = Math.Max(1, parsedMaxBurst);\nvar p = Policy.RateLimitAsync(n, perTimeSpan, burst);","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Set maxBurst >= numberOfExecutions unless you intentionally want to cap bursts (still >= 1).","Clamp config values: Math.Max(1, parsed).","Validate the triple at startup."],"tags":["argumentoutofrange","ratelimit","config","validation","legacy-api"],"backgroundTag":null,"analyzedSha":"d0e46bdb1ee11ea50d0e4b6846d2633d6bc09bac","analyzedAt":"2026-08-13T16:36:01.959Z","schemaVersion":2},"datasetVersion":"2026-08-13T19:17:28.613Z"}