Rate Limits e controllo del carico
TL; DR
Un tracciato affidabile è una combinazione di limiti e quote su più livelli (edge→BFF→servis), una distribuzione equa delle risorse (per-tenant/chiave/rout), trottling adattivo SLO e backprescher invece di timeout silenziosi. Utilizzare token/leaky bucket per «velocità», una finestra slittante per le quote contabili, limiti competitivi per le operazioni pesanti, dynamic throttling per il degrado e circuito-breaker per gli upstream fragili. Tutti sotto osservazione e playbook.
1) Perché i limiti nel iGaming/fintech
SLO e resilienza: protezione da valanga di retrai, picchi di tornei/event, picchi di pagamento.
Giusto, un tenente o un socio non «succhia» tutto il budget.
Antiabuse/bot - Controllo login/registrazione, spam, screeping cataloghi.
Costo: contenimento di chiamate costose (KYC, report, aggregazioni).
Compagine/uso leale: quote formali «fair use» nei contratti.
2) Tassonomia dei limiti
3) Algoritmi e dove applicare
3. 1 Token Bucket (impostazione predefinita)
Le opzioni sono «rated» (token/secondi), «burst» (scorta max).
Ottimo per API read, pagamento/stato, BFF.
Con il serbatoio vuoto → 429 + «Retry-After».
3. 2 Leaky Bucket (media)
«Demolizione» RPS garantita, utile per i webhoot per evitare di colpire i worker.
3. 3 Fixed Window vs Sliding Window
Fissed - semplice ma «limite» Sliding è un registro onesto nella finestra (min/h/24).
Utilizzare Sliding per le quote contrattuali.
3. 4 Concurrent Limits
Limite attività attive contemporaneamente. Ideale per esportazioni/ricambi, pacchetti KYC, ricambi.
In caso di carenza, 429/503 + coda/polling.
3. 5 Cost/Complexity Limiter
GraphQL/Ricerca: consideriamo il «costo» in profondità/radicalità/estensione.
Ritaglia/degrado le query «costose», risposta con suggerimento.
4) Chiavi di limitazione (dimensioning)
per-tenant (multiparenda, giustizia),
per-api _ key/client _ id (partner),
per-route (mutazioni critiche più rigide),
per-user/device/IP/ASN/geo (antibot/anticrave),
per-BIN/country (metodi di pagamento, protezione di emittenti e provider),
per-method (GET più morbido, POST/PUT più rigido).
Composizione: chiave principale + «moltiplicatore di rischio» (nuovo account, TOR/proxy, alto rischio changeback).
5) trottling adattivo SLO
Abilita throttling dynamic quando lo SLO è in pericolo:- Trigger: «p95», « », «queue», «CPU/IO saturation».
- Azioni: abbassare rate/burst, attivare outlier-ejection, tagliare i router «costosi», degrade temporaneo (senza campi o aggregazioni pesanti).
- Ritorno: graduale (25→50→100%) quando i segnali N sono normalizzati.
6) Integrazione con l'architettura
API Gateway (edge): rate/quote primarie, geo/ASN, HMAC/JWT-Validation, 429/' Retry-After '.
BFF/Service Mesh: limiti sottili per-route/per-tenant, concurrent-limits, circuiti-breakers agli upstream.
All'interno del servizio: semafori per operazioni pesanti, backprescher per code, pool di lavoro con dimensioni bound.
Webhookie - endpoint separato con leaky bucket e buffer retraes.
7) Configurazioni (sezioni)
Kong / NGINX-style (rate + burst):yaml plugins:
- name: rate-limiting config:
policy: local minute: 600 # 10 rps limit_by: consumer fault_tolerant: true
- name: response-ratelimiting config:
limits:
heavy: { minute: 60 }
Envoy (circuit + outlier + rate):
yaml circuit_breakers:
thresholds: { max_connections: 1000, max_requests: 800 }
outlier_detection:
consecutive_5xx: 5 interval: 5s base_ejection_time: 30s http_filters:
- name: envoy. filters. http. local_ratelimit typed_config:
token_bucket: { max_tokens: 100, tokens_per_fill: 100, fill_interval: 1s }
filter_enabled: { default_value: 100% }
filter_enforced: { default_value: 100% }
Concept-limits (pseudo):
pseudo sema = Semaphore(MAX_ACTIVE_EXPORTS_PER_TENANT)
if! sema. tryAcquire(timeout=100ms) then return 429 with retry_after=rand(1..5)s process()
sema. release()
GraphQL cost guard (idea):
pseudo cost = sum(weight(field) cardinality(arg))
if cost > tenant. budget then reject(429,"query too expensive")
8) Criteri per canali diversi
REST
GET più morbido, POST/PATCH/DELETE più rigoroso; è possibile ritrarre gli stati/verifiche «idipotenti».
Per i pagamenti: limiti di «auth/capture/refund» per-user/tenant/BIN/paese.
GraphQL
Depth/complexity caps, persisted/whitelisted queries, limiti per «alias».
WebSocket/SSE
Il limite di frequenza dì subscribe/unsubscribe «, la cappa per numero di topic, il controllo della dimensione degli eventi e la send-queue si → in caso di sovraccarico dì policy _ disconnect».
Webhook
Leaky bucket in ricezione, per-sender quote, dead-letter coda, determinati 2xx/429.
9) Feedback clienti
Restituisci sempre un chiaro 429 con i titoli:- `Retry-After:
` - `X-RateLimit-Limit/Remaining/Reset`
- Per le quote, 403 con il codice «queta _ exceeded» e il riferimento all'upgrade del piano.
- La documentazione è limitata alla pagina «Fair Use» +.
10) Monitoraggio e dashboard
Metriche:- I successi dei limiti sono «rate». limit. hit per chiavi/rots/tenanti.
- 429/503 доля, latency p50/p95/p99, error rate, queue length, open circuits.
- Fair-share: top tenant per consumo, «bully detector».
- Webhook: ricezione/retrai, drop-rate, lega media.
- 429 non più dell '1-3% del totale RPS (senza bot).
- p95 5-10 ms per edge.
- Tempo di recupero dal degrado di 10 minuti
sql
SELECT ts::date d, tenant, route,
SUM(hits) AS limit_hits,
SUM(total) AS total_calls,
SUM(hits)::decimal/NULLIF(SUM(total),0) AS hit_rate
FROM ratelimit_stats
GROUP BY 1,2,3
ORDER BY d DESC, hit_rate DESC;
11) Playbook incidenti
Tempesta di retroscena (la caduta di upstream) - Attivare il global throttling, sollevare backoff, aprire il circuito-breaker, restituire «errori rapidi» al posto dei time-out.
Bot-attacco/screaping: cap rigido IP/ASN/geo, abilitare WAF/JS challenge, limitare directory/ricerca.
Il picco del torneo/eventa è quello di alzare preventivamente i limiti di lettura, abbassare i «campi costosi», includere cash/denormalizzazione.
I siti Web di PSP sono stati disattivati: leaky bucket temporaneo, priorità dei tipi critici, espansione dead-letter e retrai.
12) Test e UAT
Carica: RPS scala, burst x 10 da normale.
Equità: emulazione 1 tenente avido - non più del X% del budget globale.
Degrado: l'adattamento SLO riduce i limiti e tiene p95 nel corridoio.
Valigie limite: cambio finestra (min→chas), tremore orologio (clock skew), ridimensionamento Redis/charding chiavi.
Contratto: titoli 429 e Retry-After presenti, SDK correttamente back-off.
13) Storage per limiti
In-memory per i limiti locali (piccoli cluster).
Redis/Memcached per distribuiti (script Lua per l'atomatologia).
Charding delle chiavi per hash; TTL sotto le finestre; Becap metrico per la perdita della cache.
Idempotency - Il limitatore non deve interrompere le ripetute idipotenti (contabilità della chiave di richiesta).
14) Gestione regole (Governance)
Elenco dei limiti: chi è il proprietario, quali chiavi/soglia/razionalizzazione.
Feature-flags per i pulsanti di scelta rapida (crisi mode).
Versioning delle regole e processo RFC per modificare le quote contrattuali.
A/B esperimenti per la selezione delle soglie ottimali.
15) Anti-pattern
Un limite globale per tutte le API.
Solo finestre fisse per le corse di bordo.
Limite senza feedback (nessun Retry-After/headers).
Timeout silenziosi invece di veloce 429/503.
Assenza per-tenant fair-share - un cliente soffoca gli altri.
Nessuna protezione GrafQL/Ricerca per complessità.
Zero in concurrent-guard → aspirapolvere BD/PSP.
16) Mini scorciatoia di selezione
Il valore predefinito è token bucket (rate + burst) per-tenant + route.
Quote di denaro/report: sliding window giorno/mese.
Operazioni pesanti: concurrent-limits + coda.
GraphQL/поиск: complexity-budgets + persisted queries.
WS/webhook: leaky bucket + backpressure.
Кризис: dynamic throttling + circuit-breaker + degrade.
Riepilogo
Il controllo del carico è una disciplina su più livelli: algoritmi corretti (bucket/finestre/competitività), chiavi di limitazione equo, adattamento SLO e feedback trasparente. Inserendo i limiti in gateway/mesh/servizi, armando GrafQL/WS/webhoop con le polizze di profilo e collegando l'osservabilità con i playbook, si trasformano eventi di punta e guasti altrui in situazioni gestite - senza crac, rimborsi e errori di conversione.