feat: implement rate limiting across all API endpoints

Add sliding-window in-memory RateLimiter service (Arc<Mutex<HashMap>>)
with per-IP and per-user-id limits on all public endpoint classes:
- POST /api/v1/join: 5/min per IP
- GET /api/v1/feed: configurable per IP (feed_rate_per_min, default 60)
- POST /api/v1/upload: configurable per user (upload_rate_per_hour, default 10)
- GET /api/v1/export/zip|html: configurable per IP (export_rate_per_day, default 3)
Limits are hot-reloadable via the config table. All 429 responses use
German error messages. Client IP is read from X-Forwarded-For (Caddy).

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
MechaCat02
2026-04-02 21:03:59 +02:00
parent 258e2bd84d
commit 989d88022a
7 changed files with 136 additions and 8 deletions

View File

@@ -3,6 +3,7 @@ use tokio::sync::broadcast;
use crate::config::AppConfig;
use crate::services::compression::CompressionWorker;
use crate::services::rate_limiter::RateLimiter;
#[derive(Clone, Debug)]
pub struct SseEvent {
@@ -16,6 +17,7 @@ pub struct AppState {
pub config: AppConfig,
pub sse_tx: broadcast::Sender<SseEvent>,
pub compression: CompressionWorker,
pub rate_limiter: RateLimiter,
}
impl AppState {
@@ -28,6 +30,7 @@ impl AppState {
config,
sse_tx,
compression,
rate_limiter: RateLimiter::new(),
}
}
}