package middleware import ( "bytes" "net/http" "net/http/httptest" "testing" "time" "github.com/alicebob/miniredis/v2" "github.com/gin-gonic/gin" goredis "github.com/redis/go-redis/v9" "github.com/stretchr/testify/require" "go.uber.org/zap" "go.uber.org/zap/zapcore" sharedauth "github.com/geo-platform/tenant-api/internal/shared/auth" ) func TestLoggerIncludesDetailedAuthFailureContext(t *testing.T) { t.Parallel() gin.SetMode(gin.TestMode) var logBuffer bytes.Buffer encoderConfig := zap.NewProductionEncoderConfig() encoderConfig.TimeKey = "" logger := zap.New(zapcore.NewCore( zapcore.NewJSONEncoder(encoderConfig), zapcore.AddSync(&logBuffer), zapcore.DebugLevel, )) mr := miniredis.RunT(t) rdb := goredis.NewClient(&goredis.Options{Addr: mr.Addr()}) mgr := sharedauth.NewManager("logger-test-secret", -1*time.Minute, 7*24*time.Hour) sessions := sharedauth.NewSessionStore(rdb) pair, err := mgr.Issue(7, 42, "editor") require.NoError(t, err) router := gin.New() router.Use(RequestID()) router.Use(Logger(logger)) router.Use(sharedauth.Middleware(mgr, sessions)) router.GET("/test", func(c *gin.Context) { c.Status(http.StatusOK) }) req := httptest.NewRequest(http.MethodGet, "/test?tab=cards", nil) req.Header.Set("Authorization", "Bearer "+pair.AccessToken) req.Header.Set("User-Agent", "geo-rankly-test/1.0") resp := httptest.NewRecorder() router.ServeHTTP(resp, req) require.Equal(t, http.StatusUnauthorized, resp.Code) logLine := logBuffer.String() t.Log(logLine) require.Contains(t, logLine, `"msg":"request"`) require.Contains(t, logLine, `"status":401`) require.Contains(t, logLine, `"route":"/test"`) require.Contains(t, logLine, `"query":"tab=cards"`) require.Contains(t, logLine, `"user_agent":"geo-rankly-test/1.0"`) require.Contains(t, logLine, `"app_message":"invalid_access_token"`) require.Contains(t, logLine, `"auth_header_present":true`) require.Contains(t, logLine, `"auth_scheme":"Bearer"`) require.Contains(t, logLine, `"auth_failure_stage":"parse_access_token"`) require.Contains(t, logLine, `"auth_failure_reason":"expired"`) require.Contains(t, logLine, `"auth_parse_error":"token has invalid claims: token is expired"`) require.Contains(t, logLine, `"auth_token_fingerprint":"`) }