Before you can view the trace data of your application, you must use a client to report the trace data to Managed Service for OpenTelemetry. This topic describes how to use OpenTelemetry SDK for Go to submit the trace data of a Go application.
Prerequisites
Background information
OpenTelemetry SDK for Go provides distributed tracing analysis capabilities for the Go programming language. You can use OpenTelemetry Protocol (OTLP) over gRPC or HTTP to submit data to the Managed Service for OpenTelemetry server.
OpenTelemetry provides several semi-automatic instrumentation plug-ins. You do not need to manually create a span. You only need to call the API operations provided by these plug-ins in the code. Spans can be automatically created for common frameworks. For more information about the supported frameworks, see OpenTelemetry documentation.
Sample code
Submit data over gRPC
Add the OpenTelemetry Go dependency.
go get go.opentelemetry.io/otel go get go.opentelemetry.io/otel/trace go get go.opentelemetry.io/otel/sdk go get go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc // otlp grpc
Initialize OpenTelemetry SDK for Go.
You can submit data by using OpenTelemetry SDK for Go or forward data by using the open source OpenTelemetry Collector.
If you submit data by using OpenTelemetry SDK for Go, replace otelAgentAddr and xtraceToken with the endpoint and authentication token obtained in the Prerequisites section.
If you forward data by using the open source OpenTelemetry Collector, replace otelAgentAddr with the IP address of your on-premises service and delete the headers:
func initProvider() func() { ctx := context.Background() otelAgentAddr, xtraceToken, ok := common.ObtainXTraceInfo() if !ok { log.Fatalf("Cannot init OpenTelemetry, exit") os.Exit(-1) } headers := map[string]string{"Authentication": xtraceToken} // Replace xtraceToken with the authentication token obtained in the Prerequisites section. traceClient := otlptracegrpc.NewClient( otlptracegrpc.WithInsecure(), otlptracegrpc.WithEndpoint(otelAgentAddr), // Replace otelAgentAddr with the endpoint obtained in the Prerequisites section. otlptracegrpc.WithHeaders(headers), otlptracegrpc.WithDialOption(grpc.WithBlock())) log.Println("start to connect to server") traceExp, err := otlptrace.New(ctx, traceClient) handleErr(err, "Failed to create the collector trace exporter") res, err := resource.New(ctx, resource.WithFromEnv(), resource.WithProcess(), resource.WithTelemetrySDK(), resource.WithHost(), resource.WithAttributes( // Specify the service name displayed on the backend of Managed Service for OpenTelemetry. semconv.ServiceNameKey.String(common.ServerServiceName), semconv.HostNameKey.String(common.ServerServiceHostName), ), ) handleErr(err, "failed to create resource") bsp := sdktrace.NewBatchSpanProcessor(traceExp) tracerProvider := sdktrace.NewTracerProvider( sdktrace.WithSampler(sdktrace.AlwaysSample()), sdktrace.WithResource(res), sdktrace.WithSpanProcessor(bsp), ) // Set the global propagator to tracecontext. The global propagator is not specified by default. otel.SetTextMapPropagator(propagation.TraceContext{}) otel.SetTracerProvider(tracerProvider) return func() { cxt, cancel := context.WithTimeout(ctx, time.Second) defer cancel() if err := traceExp.Shutdown(cxt); err != nil { otel.Handle(err) } } }
Instrument the application.
shutdown := initProvider() defer shutdown() //meter := global.Meter("demo-server-meter") serverAttribute := attribute.String("server-attribute", "foo") fmt.Println("start to gen chars for trace data") initTraceDemoData() fmt.Println("gen trace data done") tracer := otel.Tracer(common.TraceInstrumentationName) // Create a handler in OpenTelemetry. handler := http.HandlerFunc(func(w http.ResponseWriter, req *http.Request) { // Simulate a delay. var sleep int64 switch modulus := time.Now().Unix() % 5; modulus { case 0: sleep = rng.Int63n(2000) case 1: sleep = rng.Int63n(15) case 2: sleep = rng.Int63n(917) case 3: sleep = rng.Int63n(87) case 4: sleep = rng.Int63n(1173) } ctx := req.Context() span := trace.SpanFromContext(ctx) span.SetAttributes(serverAttribute) actionChild(tracer, ctx, sleep) w.Write([]byte("Hello World")) }) wrappedHandler := otelhttp.NewHandler(handler, "/hello") http.Handle("/hello", wrappedHandler) http.ListenAndServe(":7080", nil)
Start the application.
go run main.go
Log on to the ARMS console. In the left-side navigation pane, choose . On the Application List page, click the name of the application. On the page that appears, view the trace data.
NoteIf the icon is displayed in the Language column, the application is connected to Application Monitoring. If a hyphen (-) is displayed, the application is connected to Managed Service for OpenTelemetry.
Submit data over HTTP
Add the OpenTelemetry Go dependency.
go get go.opentelemetry.io/otel go get go.opentelemetry.io/otel/trace go get go.opentelemetry.io/otel/sdk go get go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp // otlp http
Initialize OpenTelemetry SDK for Go. Replace Endpoint and URLPath with the endpoint obtained in the Prerequisites section.
You can submit data by using OpenTelemetry SDK for Go or forward data by using the open source OpenTelemetry Collector.
If you submit data by using OpenTelemetry SDK for Go, replace Endpoint and URLPath with the endpoint obtained in the Prerequisites section.
If you forward data by using the open source OpenTelemetry Collector, replace Endpoint with the IP address of your on-premises service and delete the headers:
func initProvider() func() { ctx := context.Background() traceClientHttp := otlptracehttp.NewClient( otlptracehttp.WithEndpoint("127.0.XX.XX:8080"), //Replace Endpoint with the endpoint obtained in the Prerequisites section. otlptracehttp.WithURLPath("/adapt_xxxxx/api/otlp/traces"), //Replace URLPath with the endpoint obtained in the Prerequisites section. otlptracehttp.WithInsecure()) otlptracehttp.WithCompression(1) traceExp, err := otlptrace.New(ctx, traceClientHttp) handleErr(err, "Failed to create the collector trace exporter") res, err := resource.New(ctx, resource.WithFromEnv(), resource.WithProcess(), resource.WithTelemetrySDK(), resource.WithHost(), resource.WithAttributes( // Specify the service name displayed on the backend of Managed Service for OpenTelemetry. semconv.ServiceNameKey.String(common.ClientServiceName), semconv.HostNameKey.String(common.ClientServiceHostName), ), ) handleErr(err, "failed to create resource") bsp := sdktrace.NewBatchSpanProcessor(traceExp) tracerProvider := sdktrace.NewTracerProvider( sdktrace.WithSampler(sdktrace.AlwaysSample()), sdktrace.WithResource(res), sdktrace.WithSpanProcessor(bsp), ) // Set the global propagator to tracecontext. The global propagator is not specified by default. otel.SetTextMapPropagator(propagation.TraceContext{}) otel.SetTracerProvider(tracerProvider) log.Println("OTEL init success") return func() { cxt, cancel := context.WithTimeout(ctx, time.Second) defer cancel() if err := traceExp.Shutdown(cxt); err != nil { otel.Handle(err) } } }
Instrument the application.
tracer := otel.Tracer(common.TraceInstrumentationName) method, _ := baggage.NewMember("method", "repl") client, _ := baggage.NewMember("client", "cli") bag, _ := baggage.New(method, client) defaultCtx := baggage.ContextWithBaggage(context.Background(), bag) for { ctx, span := tracer.Start(defaultCtx, "ExecuteRequest") makeRequest(ctx) span.End() time.Sleep(time.Duration(1) * time.Second) }
Start the application.
go run main.go
Log on to the ARMS console. In the left-side navigation pane, choose . On the Application List page, click the name of the application. On the page that appears, view the trace data.
NoteIf the icon is displayed in the Language column, the application is connected to Application Monitoring. If a hyphen (-) is displayed, the application is connected to Managed Service for OpenTelemetry.