tsweb: update ServeMux matching to 1.22.0 syntax (#11090)

* tsweb: update ServeMux matching to 1.22.0 syntax

Updates #cleanup

Go 1.22.0 introduced the ability to use more expressive routing patterns
that include HTTP method when constructing ServeMux entries.
Applications that attempted to use these patterns in combination with
the old `tsweb.Debugger` would experience a panic as Go would not permit
the use of matching rules with mixed level of specificity. We now
specify the method for each `/debug` handler to prevent
incompatibilities.

Signed-off-by: Patrick O'Doherty <patrick@tailscale.com>
pull/11125/head
Patrick O'Doherty 10 months ago committed by GitHub
parent 5bd19fd3e3
commit 30c9189ed3
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194

@ -39,20 +39,20 @@ type DebugHandler struct {
// Debugger returns the DebugHandler registered on mux at /debug/, // Debugger returns the DebugHandler registered on mux at /debug/,
// creating it if necessary. // creating it if necessary.
func Debugger(mux *http.ServeMux) *DebugHandler { func Debugger(mux *http.ServeMux) *DebugHandler {
h, pat := mux.Handler(&http.Request{URL: &url.URL{Path: "/debug/"}}) h, pattern := mux.Handler(&http.Request{Method: "GET", URL: &url.URL{Path: "/debug/"}})
if d, ok := h.(*DebugHandler); ok && pat == "/debug/" { if d, ok := h.(*DebugHandler); ok && pattern == "GET /debug/" {
return d return d
} }
ret := &DebugHandler{ ret := &DebugHandler{
mux: mux, mux: mux,
} }
mux.Handle("/debug/", ret) mux.Handle("GET /debug/", ret)
ret.KVFunc("Uptime", func() any { return varz.Uptime() }) ret.KVFunc("Uptime", func() any { return varz.Uptime() })
ret.KV("Version", version.Long()) ret.KV("Version", version.Long())
ret.Handle("vars", "Metrics (Go)", expvar.Handler()) ret.Handle("GET vars", "Metrics (Go)", expvar.Handler())
ret.Handle("varz", "Metrics (Prometheus)", http.HandlerFunc(promvarz.Handler)) ret.Handle("GET varz", "Metrics (Prometheus)", http.HandlerFunc(promvarz.Handler))
ret.Handle("pprof/", "pprof (index)", http.HandlerFunc(pprof.Index)) ret.Handle("GET pprof/", "pprof (index)", http.HandlerFunc(pprof.Index))
// the CPU profile handler is special because it responds // the CPU profile handler is special because it responds
// streamily, unlike every other pprof handler. This means it's // streamily, unlike every other pprof handler. This means it's
// not made available through pprof.Index the way all the other // not made available through pprof.Index the way all the other
@ -63,7 +63,7 @@ func Debugger(mux *http.ServeMux) *DebugHandler {
ret.HandleSilent("pprof/profile", http.HandlerFunc(pprof.Profile)) ret.HandleSilent("pprof/profile", http.HandlerFunc(pprof.Profile))
ret.URL("/debug/pprof/goroutine?debug=1", "Goroutines (collapsed)") ret.URL("/debug/pprof/goroutine?debug=1", "Goroutines (collapsed)")
ret.URL("/debug/pprof/goroutine?debug=2", "Goroutines (full)") ret.URL("/debug/pprof/goroutine?debug=2", "Goroutines (full)")
ret.Handle("gc", "force GC", http.HandlerFunc(gcHandler)) ret.Handle("GET gc", "force GC", http.HandlerFunc(gcHandler))
hostname, err := os.Hostname() hostname, err := os.Hostname()
if err == nil { if err == nil {
ret.KV("Machine", hostname) ret.KV("Machine", hostname)
@ -98,7 +98,7 @@ func (d *DebugHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
} }
func (d *DebugHandler) handle(slug string, handler http.Handler) string { func (d *DebugHandler) handle(slug string, handler http.Handler) string {
href := "/debug/" + slug href := "GET /debug/" + slug
d.mux.Handle(href, Protected(debugBrowserHeaderHandler(handler))) d.mux.Handle(href, Protected(debugBrowserHeaderHandler(handler)))
return href return href
} }

Loading…
Cancel
Save