package handlers import ( "context" "encoding/json" "errors" "net/http" "net/http/httptest" "testing" "git.threesix.ai/jordan/sp4-v2-1770499323/pkg/auth" "git.threesix.ai/jordan/sp4-v2-1770499323/pkg/logging" ) // mockValidator implements auth.Validator for testing. type mockValidator struct { user *auth.User err error } func (m *mockValidator) Validate(ctx context.Context, token string) (*auth.User, error) { if m.err != nil { return nil, m.err } return m.user, nil } func TestValidate_Check(t *testing.T) { tests := []struct { name string token string validator *mockValidator wantStatus int wantUserID string }{ { name: "valid token", token: "valid-jwt-token", validator: &mockValidator{ user: &auth.User{ ID: "user-123", Email: "user@example.com", Roles: []string{"admin"}, }, }, wantStatus: http.StatusOK, wantUserID: "user-123", }, { name: "missing token", token: "", validator: &mockValidator{}, wantStatus: http.StatusUnauthorized, }, { name: "invalid token", token: "bad-token", validator: &mockValidator{ err: errors.New("token invalid"), }, wantStatus: http.StatusUnauthorized, }, } for _, tt := range tests { t.Run(tt.name, func(t *testing.T) { handler := NewValidate(tt.validator, logging.Nop()) req := httptest.NewRequest(http.MethodPost, "/api/auth-svc/validate", nil) if tt.token != "" { req.Header.Set("Authorization", "Bearer "+tt.token) } w := httptest.NewRecorder() err := handler.Check(w, req) if err != nil { // Handler returns error for app.Wrap to handle if tt.wantStatus == http.StatusOK { t.Fatalf("unexpected error: %v", err) } return } if tt.wantStatus != http.StatusOK { t.Fatalf("expected error but got nil") } if w.Code != http.StatusOK { t.Errorf("expected status %d, got %d", http.StatusOK, w.Code) } var resp map[string]any if err := json.NewDecoder(w.Body).Decode(&resp); err != nil { t.Fatalf("failed to decode response: %v", err) } data, ok := resp["data"].(map[string]any) if !ok { t.Fatal("expected 'data' field in response") } if data["user_id"] != tt.wantUserID { t.Errorf("expected user_id %q, got %q", tt.wantUserID, data["user_id"]) } }) } }