Monitor Go net/http performance with OpenTelemetry
Package net/http provides HTTP client and server implementations. It allows you to make and serve HTTP requests in Golang.
This article will teach you how to monitor net/http performance using OpenTelemetry observability framework.
What is OpenTelemetry?
OpenTelemetry is an open-source observability framework for distributed tracing (including logs and errors) and OpenTelemetry metrics.
Otel allows developers to collect and export telemetry data in a vendor agnostic way. With OpenTelemetry, you can instrument your application once and then add or change vendors without changing the instrumentation, for example, here is a list popular DataDog alternatives that support OpenTelemetry.
OpenTelemetry is available for most programming languages and provides interoperability across different languages and environments.
net/http instrumentation
To install net/http OpenTelemetry instrumentation:
go get go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp
Instrumenting http.Server
You can instrument HTTP server by wrapping all your handlers:
handler := http.Handler(http.DefaultServeMux) // or use your router
handler = otelhttp.NewHandler(handler, "")
httpServer := &http.Server{
Addr: ":8888",
ReadTimeout: 5 * time.Second,
WriteTimeout: 10 * time.Second,
IdleTimeout: 60 * time.Second,
Handler: handler,
}
err := httpServer.ListenAndServe()
Filtering requests
You can exclude some requests from being traced using otelhttp.WithFilter:
handler = otelhttp.NewHandler(handler, "", otelhttp.WithFilter(otelReqFilter))
func otelReqFilter(req *http.Request) bool {
return req.URL.Path != "/ping"
}
Span name
You can customize span name formatting using otelhttp.WithSpanNameFormatter:
handler = otelhttp.NewHandler(handler, "", otelhttp.WithSpanNameFormatter(httpSpanName))
func spanName(operation string, req *http.Request) string {
return operation
}
Route attribute
If you are instrumenting individual handlers (not all handlers at once), you can annotate handler spans with http.route
attribute. This can be useful when you can't find an instrumentation for your router.
handler = otelhttp.WithRouteTag("/hello/:username", handler)
Instrumenting http.Client
otelhttp provides a HTTP transport to instrument http.Client
:
client := http.Client{
Transport: otelhttp.NewTransport(http.DefaultTransport),
}
You can also use the following shortcuts to make HTTP requets:
import "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp"
resp, err := otelhttp.Get(ctx, "https://google.com/")
What is Uptrace?
Uptrace is an open source APM for OpenTelemetry with an intuitive query builder, rich dashboards, automatic alerts, and integrations for most languages and frameworks.
You can get started with Uptrace by downloading a DEB/RPM package or a pre-compiled Go binary.
What's next?
Next, instrument more operations, for example, database queries, errors, and logs. You can also learn about OpenTelemetry Go Tracing API to create your own instrumentations.
Popular instrumentations: