From d0152e1f3853d031dd3d3bfba8d71d79c93cc958 Mon Sep 17 00:00:00 2001 From: Viktor Barzin Date: Sun, 26 Apr 2026 09:27:16 +0000 Subject: [PATCH] crowdsec/traefik: stop captchaing legit Immich mobile bursts MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Mobile timeline scrubs prefetch ~100 thumbs in <1s, which exhausted the immich-rate-limit (avg=500, burst=5000) and produced a cascade of HTTP 429s. CrowdSec's local http-429-abuse scenario then fired captcha:1 on the source IP (alert #291, 2026-04-25 — owner's Hyperoptic IPv6). Two changes: - crowdsec: add a second whitelist doc (viktor/immich-asset-paths-whitelist) filtering events by Immich asset paths so they never feed leaky buckets. Auth endpoints intentionally excluded — brute-force protection unchanged. - traefik: raise immich-rate-limit avg=500->1000, burst=5000->20000 so legitimate mobile scrubs don't produce 429s in the first place. --- stacks/crowdsec/modules/crowdsec/main.tf | 15 +++++++++++++++ stacks/traefik/modules/traefik/middleware.tf | 4 ++-- 2 files changed, 17 insertions(+), 2 deletions(-) diff --git a/stacks/crowdsec/modules/crowdsec/main.tf b/stacks/crowdsec/modules/crowdsec/main.tf index cf59ea47..ca7b1998 100644 --- a/stacks/crowdsec/modules/crowdsec/main.tf +++ b/stacks/crowdsec/modules/crowdsec/main.tf @@ -96,6 +96,21 @@ resource "kubernetes_config_map" "crowdsec_whitelist" { reason: "Trusted IP - never block" ip: - "176.12.22.76" + --- + name: viktor/immich-asset-paths-whitelist + description: "Don't penalise legit Immich timeline bursts (mobile scrub, web grid)" + whitelist: + reason: "Immich asset endpoints are auth-gated; mobile scrub legitimately bursts" + expression: + - > + evt.Parsed.target_fqdn == "immich.viktorbarzin.me" && + (evt.Parsed.request startsWith "/api/assets/" || + evt.Parsed.request startsWith "/api/timeline/" || + evt.Parsed.request startsWith "/api/asset/" || + evt.Parsed.request startsWith "/api/search/" || + evt.Parsed.request startsWith "/api/memories" || + evt.Parsed.request startsWith "/api/albums" || + evt.Parsed.request startsWith "/api/activities") YAML } } diff --git a/stacks/traefik/modules/traefik/middleware.tf b/stacks/traefik/modules/traefik/middleware.tf index 9cfac0a3..2c8ae8c4 100644 --- a/stacks/traefik/modules/traefik/middleware.tf +++ b/stacks/traefik/modules/traefik/middleware.tf @@ -244,8 +244,8 @@ resource "kubernetes_manifest" "middleware_immich_rate_limit" { } spec = { rateLimit = { - average = 500 - burst = 5000 + average = 1000 + burst = 20000 } } }