Files
sm-sitemap-plugin/routes_test.go
Jakub Zych 4e55939a1f test(17-06): sitemap parity unit tests
- TestURLTo (every Url::to golden case, BackendURL, URLPath),
  TestXMLEscaping (PHP XmlEscapingTest as behaviour), TestTiers (each
  default rule, first match, off, bad pattern fails Boot), TestRewrite,
  TestHooks, TestURLCap, TestManifest (fail-safe reads, key
  normalization, dates), TestFillable (PHP MassAssignmentTest),
  TestDefinitionItemJSON, TestBackendURL (trusted forwarded proto)
- TestImportWinter on Postgres: maps and drops with report, --theme,
  --dry-run, --force, settings upsert, refusals
2026-10-12 19:38:04 +02:00

70 lines
2.6 KiB
Go

package sitemap
import (
"crypto/tls"
"net/http/httptest"
"os"
"path/filepath"
"testing"
"git.golem15.com/golem15/summercms/modules/backpack"
"git.golem15.com/golem15/summercms/modules/compass"
)
// TestBackendURL pins the root URL the sitemap's absolute URLs and the
// frontend_url rewrite start from: app.url when set; else the request's
// Host with https for TLS, or for the last X-Forwarded-Proto hop of a peer
// in http.trusted_proxies, while a client that sends the header directly
// gets http.
func TestBackendURL(t *testing.T) {
app := func(t *testing.T, files map[string]string) *backpack.App {
t.Helper()
dir := t.TempDir()
for name, body := range files {
if err := os.WriteFile(filepath.Join(dir, name), []byte(body), 0o644); err != nil {
t.Fatal(err)
}
}
cfg, err := compass.Open(compass.Options{Dir: dir, Environ: []string{}})
if err != nil {
t.Fatal(err)
}
return backpack.New(cfg)
}
trusted := app(t, map[string]string{"http.yaml": "trusted_proxies:\n - 10.0.0.0/8\n"})
for _, tc := range []struct {
name string
app *backpack.App
remote string
proto []string
tls bool
want string
}{
{"app.url wins", app(t, map[string]string{"app.yaml": "url: https://api.example.test/\n"}), "203.0.113.9:1234", []string{"http"}, false, "https://api.example.test"},
{"plain request", trusted, "203.0.113.9:1234", nil, false, "http://h.test"},
{"TLS", trusted, "203.0.113.9:1234", nil, true, "https://h.test"},
{"trusted proxy says https", trusted, "10.1.2.3:5000", []string{"https"}, false, "https://h.test"},
{"trusted proxy, last hop wins", trusted, "10.1.2.3:5000", []string{"https, http"}, false, "http://h.test"},
{"trusted proxy, last header wins", trusted, "10.1.2.3:5000", []string{"http", "HTTPS"}, false, "https://h.test"},
{"untrusted client says https", trusted, "203.0.113.9:1234", []string{"https"}, false, "http://h.test"},
{"no trusted proxies configured", app(t, nil), "10.1.2.3:5000", []string{"https"}, false, "http://h.test"},
{"nil app", nil, "10.1.2.3:5000", []string{"https"}, false, "http://h.test"},
{"IPv4-mapped trusted peer", trusted, "[::ffff:10.1.2.3]:5000", []string{"https"}, false, "https://h.test"},
{"unparsable peer", trusted, "not-an-address", []string{"https"}, false, "http://h.test"},
} {
t.Run(tc.name, func(t *testing.T) {
r := httptest.NewRequest("GET", "http://h.test/sitemap.xml", nil)
r.RemoteAddr = tc.remote
for _, v := range tc.proto {
r.Header.Add("X-Forwarded-Proto", v)
}
if tc.tls {
r.TLS = &tls.ConnectionState{}
}
if got := backendURL(tc.app, r); got != tc.want {
t.Fatalf("backendURL = %q, want %q", got, tc.want)
}
})
}
}