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:
@@ -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(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user