Instrumenting gRPC with OpenTelemetry

Installation

To install otelgrpc:

go get go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc

Usage

To instrument gRPC client:

import "go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc"

conn, err := grpc.Dial(target,
	grpc.WithInsecure(),
	grpc.WithUnaryInterceptor(otelgrpc.UnaryClientInterceptor()),
	grpc.WithStreamInterceptor(otelgrpc.StreamClientInterceptor()),
)

To instrument gRPC server:

import "go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc"

server := grpc.NewServer(
	grpc.UnaryInterceptor(otelgrpc.UnaryServerInterceptor()),
	grpc.StreamInterceptor(otelgrpc.StreamServerInterceptor()),
)

Metadata and baggage

On the client side, you can use gRPC metadata as a baggage:

import "google.golang.org/grpc/metadata"

md := metadata.Pairs(
	"key1", "value1",
	"key2", "value2",
)
ctx := metadata.NewOutgoingContext(context.Background(), md)

On the server side, you can use gRPC metadata from an incoming request:

import "google.golang.org/grpc/metadata"

md, ok := metadata.FromIncomingContext(ctx); ok {
    fmt.Println(md)
}

Or use baggage API:

import "go.opentelemetry.io/otel/baggage"

baggage := baggage.FromContext(ctx)

What's next?

Next, instrument more operations, for example, database queries, errors, and logs. You can also learn about OpenTelemetry API to create your own instrumentations.