package server import ( "html/template" "io/fs" "log/slog" "net/http/httptest" "strings" "testing" "git.coopcloud.tech/wiki-cafe/member-console/internal/config" "git.coopcloud.tech/wiki-cafe/member-console/internal/embeds" ) func errorPageTemplates(t *testing.T) *SafeTemplates { t.Helper() sub, err := fs.Sub(embeds.Templates, "templates") if err != nil { t.Fatalf("sub templates FS: %v", err) } tmpl, err := template.New("root").Funcs(template.FuncMap{ "deploymentName": config.DeploymentName, }).ParseFS(sub, "error.html") if err != nil { t.Fatalf("parse error.html: %v", err) } return NewSafeTemplates(tmpl, slog.Default()) } func TestRenderErrorPageNavigation404(t *testing.T) { st := errorPageTemplates(t) rec := httptest.NewRecorder() req := httptest.NewRequest("GET", "/no-such-page", nil) st.RenderErrorPage(rec, req, 404, "The page you requested does not exist.") if rec.Code != 404 { t.Fatalf("status = %d, want 404", rec.Code) } body := rec.Body.String() for _, want := range []string{"404", "Not Found", "The page you requested does not exist.", "navbar-brand"} { if !strings.Contains(body, want) { t.Errorf("styled 404 body missing %q", want) } } if ct := rec.Header().Get("Content-Type"); !strings.HasPrefix(ct, "text/html") { t.Errorf("Content-Type = %q, want text/html", ct) } } func TestRenderErrorPagePanicBodyNeverLeaksInternals(t *testing.T) { st := errorPageTemplates(t) rec := httptest.NewRecorder() req := httptest.NewRequest("GET", "/", nil) // The recovery middleware passes only a fixed message; assert the page // carries exactly that and no request-derived or internal detail slot. st.RenderErrorPage(rec, req, 500, "An unexpected error occurred. Please try again.") if rec.Code != 500 { t.Fatalf("status = %d, want 500", rec.Code) } body := rec.Body.String() if !strings.Contains(body, "Internal Server Error") { t.Errorf("styled 500 body missing status text") } for _, banned := range []string{"goroutine", "runtime error", ".go:"} { if strings.Contains(body, banned) { t.Errorf("styled 500 body leaks internals: %q", banned) } } } func TestRenderErrorPageHTMXKeepsPlainText(t *testing.T) { st := errorPageTemplates(t) rec := httptest.NewRecorder() req := httptest.NewRequest("GET", "/partials/whatever", nil) req.Header.Set("HX-Request", "true") st.RenderErrorPage(rec, req, 404, "not found") if rec.Code != 404 { t.Fatalf("status = %d, want 404", rec.Code) } body := rec.Body.String() if strings.Contains(body, "