From 3094117d9496ca49e21cdd950add94313b6f0c37 Mon Sep 17 00:00:00 2001 From: Marcin Tojek Date: Tue, 18 Apr 2023 13:45:59 +0200 Subject: [PATCH 1/2] feat: Expose magicsock metrics --- cli/agent.go | 25 +++++++++++++++++++++++++ 1 file changed, 25 insertions(+) diff --git a/cli/agent.go b/cli/agent.go index 8fc2f3f6e3042..bcc18b5bb331d 100644 --- a/cli/agent.go +++ b/cli/agent.go @@ -18,6 +18,7 @@ import ( "cloud.google.com/go/compute/metadata" "golang.org/x/xerrors" "gopkg.in/natefinch/lumberjack.v2" + "tailscale.com/util/clientmetric" "cdr.dev/slog" "cdr.dev/slog/sloggers/sloghuman" @@ -36,6 +37,7 @@ func (r *RootCmd) workspaceAgent() *clibase.Cmd { noReap bool sshMaxTimeout time.Duration tailnetListenPort int64 + prometheusAddress string ) cmd := &clibase.Cmd{ Use: "agent", @@ -126,6 +128,13 @@ func (r *RootCmd) workspaceAgent() *clibase.Cmd { agentPorts[port] = "pprof" } + prometheusSrvClose := ServeHandler(ctx, logger, prometheusMetricsHandler(), prometheusAddress, "prometheus") + defer prometheusSrvClose() + // Do a best effort here. If this fails, it's not a big deal. + if port, err := urlPort(prometheusAddress); err == nil { + agentPorts[port] = "prometheus" + } + // exchangeToken returns a session token. // This is abstracted to allow for the same looping condition // regardless of instance identity auth type. @@ -257,6 +266,13 @@ func (r *RootCmd) workspaceAgent() *clibase.Cmd { Description: "Specify a static port for Tailscale to use for listening.", Value: clibase.Int64Of(&tailnetListenPort), }, + { + Flag: "prometheus-address", + Default: "127.0.0.1:2112", + Env: "CODER_AGENT_PROMETHEUS_ADDRESS", + Value: clibase.StringOf(&prometheusAddress), + Description: "The bind address to serve Prometheus metrics.", + }, } return cmd @@ -343,3 +359,12 @@ func urlPort(u string) (int, error) { } return -1, xerrors.Errorf("invalid port: %s", u) } + +func prometheusMetricsHandler() http.Handler { + // We don't have any other internal metrics so far, so it's safe to expose metrics this way. + // Based on: https://github.com/tailscale/tailscale/blob/280255acae604796a1113861f5a84e6fa2dc6121/ipn/localapi/localapi.go#L489 + return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { + w.Header().Set("Content-Type", "text/plain") + clientmetric.WritePrometheusExpositionFormat(w) + }) +} From a629d447b1d464a2ed6ee5590abe2ebf2cadc002 Mon Sep 17 00:00:00 2001 From: Marcin Tojek Date: Tue, 18 Apr 2023 22:35:06 +0200 Subject: [PATCH 2/2] golden-files --- cli/testdata/coder_agent_--help.golden | 3 +++ 1 file changed, 3 insertions(+) diff --git a/cli/testdata/coder_agent_--help.golden b/cli/testdata/coder_agent_--help.golden index ae15c96c71579..7b6d05ecb9602 100644 --- a/cli/testdata/coder_agent_--help.golden +++ b/cli/testdata/coder_agent_--help.golden @@ -15,6 +15,9 @@ Starts the Coder workspace agent. --pprof-address string, $CODER_AGENT_PPROF_ADDRESS (default: 127.0.0.1:6060) The address to serve pprof. + --prometheus-address string, $CODER_AGENT_PROMETHEUS_ADDRESS (default: 127.0.0.1:2112) + The bind address to serve Prometheus metrics. + --ssh-max-timeout duration, $CODER_AGENT_SSH_MAX_TIMEOUT (default: 0) Specify the max timeout for a SSH connection.