Files
MyClub/internal/middleware/recovery.go
T
Tomas Dvorak dfc079288f hot fix #1
2026-01-26 08:13:18 +01:00

84 lines
1.8 KiB
Go

package middleware
import (
"fmt"
"net/http"
"runtime/debug"
"fotbal-club/internal/services"
"fotbal-club/pkg/logger"
"github.com/gin-gonic/gin"
)
// CustomRecovery returns a middleware that recovers from panics and logs them
func CustomRecovery() gin.HandlerFunc {
return func(c *gin.Context) {
defer func() {
if err := recover(); err != nil {
// Get stack trace
stack := string(debug.Stack())
// Log the panic
requestID := GetRequestID(c)
logger.Error(fmt.Sprintf(
"Panic recovered: request_id=%s error=%v path=%s method=%s stack=%s",
requestID,
err,
c.Request.URL.Path,
c.Request.Method,
stack,
))
// Return error response
c.JSON(http.StatusInternalServerError, gin.H{
"error": "Internal server error",
"request_id": requestID,
})
c.Abort()
}
}()
c.Next()
}
}
func CustomRecoveryWithReporter(reporter *services.ErrorReporter) gin.HandlerFunc {
if reporter == nil {
return CustomRecovery()
}
return func(c *gin.Context) {
defer func() {
if err := recover(); err != nil {
stack := string(debug.Stack())
requestID := GetRequestID(c)
logger.Error(fmt.Sprintf(
"Panic recovered: request_id=%s error=%v path=%s method=%s stack=%s",
requestID,
err,
c.Request.URL.Path,
c.Request.Method,
stack,
))
reporter.Report(c.Request.Context(), &services.ErrorEvent{
Origin: "backend",
Language: "go",
Severity: "fatal",
Message: fmt.Sprintf("%v", err),
Stack: stack,
URL: c.Request.URL.Path,
Method: c.Request.Method,
RequestID: requestID,
})
c.JSON(http.StatusInternalServerError, gin.H{
"error": "Internal server error",
"request_id": requestID,
})
c.Abort()
}
}()
c.Next()
}
}