Docs / Reference / Security
RateLimitRule
RateLimitRule manages one rate limiting rule in a zone, in its http_ratelimit phase: the rule counts the requests its expression matches, and once a client sends more than requestsPerPeriod of them in a period, the action applies to the client's matching requests for the mitigation timeout. A Free plan allows one rate limiting rule, counted per IP address over 10 seconds, with the block action.
- API version
- kflare.dev/v1alpha1
- Scope
- Namespaced
- Short name
- cfratelimit
- Token permission
- Zone · Zone WAF · Edit
Example
Every field, with the sample's values. The live lines are the repository's sample, which applies as it is; the commented ones are the other fields, filled from other samples where one sets them. Some exclude each other, so check the rules before you uncomment several.
apiVersion: kflare.dev/v1alpha1
kind: RateLimitRule
metadata:
name: example-ratelimitrule
namespace: default
spec:
zoneRef:
name: example-zone
expression: starts_with(http.request.uri.path, "/api/")
description: Limit each client to 100 API requests every 10 seconds
action: block
response:
content: '{"error":"rate limited, try again in 10 seconds"}'
contentType: application/json
statusCode: 429
ratelimit:
characteristics:
- cf.colo.id
- ip.src
period: 10
mitigationTimeout: 10
requestsPerPeriod: 100
# countingExpression: <countingExpression>
# requestsToOrigin: true
# enabled: true
# priority: 1Spec
What you set, with the limits the API server enforces.
| Field | Description |
|---|---|
actionstringrequired | Action is what Cloudflare does with a client's matching requests once it is over the rate. Free plans can only block. - block: blocks them, with Cloudflare's response or the rule's. - challenge: issues an interactive challenge. - js_challenge: issues a JavaScript challenge. - managed_challenge: issues the challenge Cloudflare picks for the visitor. - log: only logs them (Enterprise plans). One of: |
descriptionstring | Description is shown with the rule in the Cloudflare dashboard. Limits: at most 4096 characters |
enabledboolean | Enabled turns the rule on or off without deleting it. Default: |
expressionstringrequired | Expression selects the requests the rule applies to, in Cloudflare's Rules language, for example Limits: 1 to 4096 characters |
priorityinteger | Priority orders the rules kflare manages in a zone and phase: lower runs first, and rules with the same priority run in order of namespace and name. Rules created outside kflare keep their place. Limits: format |
ratelimitobject | Ratelimit is the rule's rate limit: what requests are counted by, over what period, how many a client may send, and for how long the action applies once the client sends more. Rule: requestsPerPeriod is required Rule: mitigationTimeout is required Rule: mitigationTimeout must be 0 or at least the period Rule: characteristics must list cf.colo.id Rule: characteristics must list a field besides cf.colo.id |
ratelimit.characteristics[]stringrequired | Characteristics are what requests are counted by: requests that share all of them share a counter. Cloudflare counts per data center, so they list cf.colo.id, and at least one other field: ip.src counts per client IP address, the only choice on Free plans; higher plans can count by other fields, such as http.request.headers["x-api-key"]. Limits: at least 1 item; at least 1 character |
ratelimit.countingExpressionstring | CountingExpression counts other requests than those the rule matches, for example only the failed logins among the login requests. It defaults to the rule's expression. Free plans cannot set it. Limits: at least 1 character |
ratelimit.mitigationTimeoutinteger | MitigationTimeout is how long, in seconds, the action applies once a client is over the rate. It must be at least the period, or 0 to throttle instead: apply the action only to the requests over the rate (Enterprise plans). Free plans can only use 10. Limits: format |
ratelimit.periodintegerrequired | Period is how long, in seconds, requests are counted for. Cloudflare accepts set periods between 10 seconds and an hour, and the zone's plan narrows them: Free plans can only count for 10 seconds. Limits: at least 0; format |
ratelimit.requestsPerPeriodinteger | RequestsPerPeriod is how many matching requests a client can send in a period before the action applies. Limits: at least 1 and at most 1000000; format |
ratelimit.requestsToOriginboolean | RequestsToOrigin counts only the requests that reach the origin, leaving out those served from Cloudflare's cache. |
responseobject | Response replaces Cloudflare's response to the requests a block rule blocks. |
response.contentstringrequired | Content is the response body. Limits: 1 to 30720 characters |
response.contentTypestringrequired | ContentType is the response's content type. One of: |
response.statusCodeintegerrequired | StatusCode is the response's HTTP status code. Limits: at least 400 and at most 499; format |
zoneRefobjectrequiredimmutable | ZoneRef references the Zone, in the same namespace, the rule belongs to. Immutable after creation. |
zoneRef.namestring | Name of the referent. This field is effectively required, but due to backwards compatibility is allowed to be empty. Instances of this type with an empty value here are almost certainly wrong. More info: https://kubernetes.io/docs/concepts/overview/working-with-objects/names/#names Default: |
Rules
Checked across fields when the resource is applied.
- response is allowed only with action block
- ratelimit is required
Status
What kflare reports. conditions holds the Ready condition, whose reason says why a resource isn't ready.
| Field | Description |
|---|---|
cloudflareMetadataobject | CloudflareMetadata identifies the rule in Cloudflare. |
cloudflareMetadata.refstring | Ref is the rule's ref, which kflare derives from the resource's kind, namespace and name. kflare finds the rule it manages by its ref. |
cloudflareMetadata.ruleIDstring | RuleID is the rule's Cloudflare ID. |
cloudflareMetadata.rulesetIDstring | RulesetID is the zone's entry point ruleset for the rule's phase. |
cloudflareMetadata.versionstring | Version is the rule's version, which Cloudflare increments whenever the rule changes. |
cloudflareMetadata.zoneIDstring | ZoneID is the Cloudflare zone the rule is in. |
conditions[]object | Conditions represent the latest available observations of the rule's state. |
kubectl get
The columns kubectl get ratelimitrules prints.
| Column | Source |
|---|---|
| PERIOD | .spec.ratelimit.period |
| REQUESTS | .spec.ratelimit.requestsPerPeriod |
| ACTION | .spec.action |
| PRIORITY | .spec.priority |
| RULE ID | .status.cloudflareMetadata.ruleID |
| READY | .status.conditions[?(@.type=="Ready")].status |
| AGE | .metadata.creationTimestamp |
Samples
From the repository's config/samples, comments included.
# Generated by kflare-gen from generator/generator.yaml. DO NOT EDIT.
#
# RateLimitRule is the Schema for the ratelimitrules API.
# It manages one rate limiting rule in a zone, in its http_ratelimit phase:
# the rule counts the requests its expression matches, and once a client
# sends more than requestsPerPeriod of them in a period, the action applies
# to the client's matching requests for the mitigation timeout. A Free plan
# allows one rate limiting rule, counted per IP address over 10 seconds,
# with the block action.
apiVersion: kflare.dev/v1alpha1
kind: RateLimitRule
metadata:
name: example-ratelimitrule
namespace: default
spec:
zoneRef:
name: example-zone
expression: starts_with(http.request.uri.path, "/api/")
description: Limit each client to 100 API requests every 10 seconds
action: block
response:
content: '{"error":"rate limited, try again in 10 seconds"}'
contentType: application/json
statusCode: 429
ratelimit:
characteristics:
- cf.colo.id
- ip.src
period: 10
mitigationTimeout: 10
requestsPerPeriod: 100