ratelimit

package
v0.3.2 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Sep 10, 2026 License: MIT Imports: 14 Imported by: 0

Documentation

Overview

Package ratelimit implements optional atomic GCRA quotas with bounded, expiring state.

Design

Callers choose route families, bucket keys and quotas. Each decision accounts for all buckets or none, using transactional store time. Keys are hashed, capacity is bounded, and typed unavailable errors distinguish storage/capacity failures from quota exhaustion. A decision can carry a retry delay.

The limiter does not choose enrollment admission policy or trust forwarded addresses. The reference server configures peer and aggregate buckets and serializes capacity accounting within its limiter namespace. Do not include raw credentials in bucket keys.

References

Index

Constants

This section is empty.

Variables

View Source
var (
	ErrInvalid     = errors.New("ratelimit: invalid quota")
	ErrUnavailable = errors.New("ratelimit: store unavailable")
	ErrCapacity    = errors.New("ratelimit: state capacity reached")
)

Functions

func Middleware

func Middleware(cfg HTTPConfig, next http.Handler) http.Handler

Middleware enforces configured quotas. Unavailability answers 503 and a denied quota answers 429 with a Retry-After rounded up to whole seconds.

func PeerKey

func PeerKey(r *http.Request, trusted []netip.Prefix) string

PeerKey uses the socket peer unless it is explicitly trusted to set X-Forwarded-For. It walks from the nearest proxy toward the client, stopping at the first untrusted address. Malformed chains fall back to the socket peer.

Types

type Bucket

type Bucket struct {
	Key      string
	Interval time.Duration
	Burst    int
}

Bucket permits one request per Interval, accumulating at most Burst requests. Key is caller-selected; it is hashed before persistence.

func (Bucket) Validate

func (b Bucket) Validate() error

Validate checks that a quota can be represented with shared microsecond precision.

type Checker

type Checker interface {
	Check(context.Context, []Bucket) (Decision, error)
}

Checker is injectable into an HTTP transport or other admission boundary.

type Decision

type Decision struct {
	Allowed    bool
	RetryAfter time.Duration
}

Decision reports the atomic result across all requested buckets.

type HTTPConfig

type HTTPConfig struct {
	Limiter Checker
	Buckets func(*http.Request) []Bucket
	Reject  func(http.ResponseWriter, *http.Request, int)
}

HTTPConfig selects quotas before parsing an inbound request body. A nil bucket list exempts the route. Reject may encode a protocol-specific error such as ACME.

type Limiter

type Limiter struct {
	Store      state.Store
	MaxEntries int
	Namespace  string
}

Limiter accounts over shared state. MaxEntries defaults to 4096 (maximum 10000). Namespace separates independent capacity pools. It is configuration, not user input.

func (*Limiter) Check

func (l *Limiter) Check(ctx context.Context, buckets []Bucket) (Decision, error)

Check consumes every bucket or none. Store failures wrap ErrUnavailable. State capacity exhaustion is unavailable rather than an unaccounted successful request.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL