Quota Enforcement — Flow Diagram

Audience: scanner operators and engineers who need to understand how free-tier quota limits are enforced at request time.

This guide traces the request path through the quota gate: the key parameters, the Valkey key layout, the enforcement algorithm, and the metrics you can alert on. For the user-facing quota model and how to obtain a free token, see the Free-Tier Quota overview. For policy rationale and legal aspects, see the Quota Legal FAQ.


0 · Key parameters

SymbolValueMeaning
L_anon{{quota_anon}}Daily ceiling for anonymous users
L_jwt{{quota_token}}Daily ceiling for token holders
T_warn200Soft reminder threshold
D_soft5 000 msDelay applied to the first 30 over-quota scans
D_hard60 000 msDelay applied to all scans beyond the soft window

L_active is L_jwt when a valid token is present; otherwise it is L_anon.


1 · Sequence diagram

sequenceDiagram
    participant C as Client
    participant API as Scanner API
    participant VALKEY as Valkey (quota)
    C->>API: /scan
    API->>VALKEY: INCR quota:
    VALKEY-->>API: new_count
    alt new_count ≤ L_active
        API-->>C: 202 Accepted (no delay)
    else new_count ≤ L_active + 30
        API->>C: wait D_soft
        API-->>C: 202 Accepted
    else
        API->>C: wait D_hard
        API-->>C: 202 Accepted
    end

Counters auto-expire 24 h after the first increment (00:00 UTC reset).


2 · Valkey key layout

Key patternTTLDescription
quota:ip:<sha256>24 hAnonymous quota per hashed IP
quota:tid:<sha256>24 hToken quota per hashed token-ID
quota:ip:<sha256>:ts24 hFirst-seen timestamp (ISO 8601)

Keys share a common TTL for efficient mass expiry via valkey-cli --scan.


3 · Pseudocode (Go-style)

func gate(key string, limit int) (delay time.Duration) {
    cnt, _ := rdb.Incr(ctx, key).Result()

    switch {
    case cnt <= limit:
        return 0 // under quota
    case cnt <= limit+30:
        return 5 * time.Second
    default:
        return 60 * time.Second
    }
}

The middleware applies time.Sleep(delay) before processing the scan request; it never returns HTTP 429 under the free tier.


4 · Metrics & monitoring

MetricPromQL sampleAlert on
stella_quota_soft_hits_totalincrease(...[5m]) > 50Many users near the limit
stella_quota_hard_hits_totalrate(...[1h]) > 0.1Potential abuse
Average delay per requesthistogram_quantile(0.95, sum(rate(...)))P95 < 1 s expected

Quota values are pulled from central constants at build time; this document is the authoritative description of enforcement behaviour.