package middleware import ( "net/http" "time" "music-server/internal/logging" "github.com/danielgtaylor/huma/v2" echoMiddleware "github.com/labstack/echo/v5/middleware" "go.uber.org/zap" ) // RateLimit allows each client IP limit requests per window, with bursts up to limit. func RateLimit(api huma.API, limit int, window time.Duration) Middleware { store := echoMiddleware.NewRateLimiterMemoryStoreWithConfig(echoMiddleware.RateLimiterMemoryStoreConfig{ Rate: float64(limit) / window.Seconds(), Burst: limit, ExpiresIn: window, }) return func(ctx huma.Context, next func(huma.Context)) { ip := clientIP(ctx) if allowed, _ := store.Allow(ip); !allowed { logging.GetLogger().Warn("Rate limit exceeded", zap.String("ip", ip), zap.String("path", ctx.URL().Path)) _ = huma.WriteErr(api, ctx, http.StatusTooManyRequests, "Rate limit exceeded. Please try again later.") return } next(ctx) } }