fxtracing

package
v0.0.0-...-edc4474 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: May 5, 2026 License: Apache-2.0 Imports: 20 Imported by: 3

README

Tracing Module

This module provides opentelemetry tracing support.

Components

The module lazily provides the following components:

  • A trace.TracerProvider
  • A server stats.Handler that traces all incoming requests
  • A client stats.Handler that traces all requests made with the client
  • HttpMiddleware that traces all incoming server requests

At the moment we do not expose any advanced otelgrpc, or samplerprovider options.

Configuration

The module provides the following configuration options:

  • Enabled: Turns tracing support on or off. When turned off, a NopTracerProvider is inserted into the system.
  • InsecureConnection: Disables TLS when connecting to the tracing endpoint
  • CertFile: Path to a pem encoded client TLS certificate
  • KeyFile: Path to the pem encoded private key of the client TLS certificate
  • RootCAFile: Path to a pem encoded CA bundle to validate the server certificate
  • Endpoint: The address + port (without protocol) of the grpc service where spans should be delivered When it is "" and InsecureConnection is set, spans will be printed to stdout

Documentation

Overview

Example
package main

import (
	"context"
	"time"

	sconfig "github.com/exoscale/stelling/config"
	"github.com/exoscale/stelling/fxlogging"
	"github.com/exoscale/stelling/fxtracing"
	"go.opentelemetry.io/otel/trace"
	"go.uber.org/fx"
	"go.uber.org/zap"
)

type Config struct {
	fxlogging.Logging
	fxtracing.Tracing
}

func main() {
	conf := &Config{}
	args := []string{"tracing-test", "--tracing.enabled", "--tracing.insecure-connection", "--logging.mode", "production"}
	if err := sconfig.Load(conf, args); err != nil {
		panic(err)
	}
	opts := fx.Options(
		fxlogging.NewModule(conf),
		fxtracing.NewModule(conf),
		// zapOpts contains options to make the logs determistic so we can test the output
		fx.Supply(fx.Annotate(zapOpts, fx.ResultTags(`group:"zap_opts,flatten"`))),
		fx.Invoke(run),
	)

	if err := fx.ValidateApp(opts); err != nil {
		panic(err)
	}

	fx.New(opts).Run()

	// This does print the span as json to stdout: we're not asserting over it because it can't be made deterministic
	// If we disable the timestamp in the stdouttracer and pass in an ID generator that always returns the same ID, it might work
	// But then I also need to figure out why the example test isn't currently checking the output anyway

}

func run(lc fx.Lifecycle, sd fx.Shutdowner, tp trace.TracerProvider) {
	// Create a tracer for this particular component
	// It is supposed to be persisted and reused
	tracer := tp.Tracer("demoapp")

	lc.Append(fx.Hook{
		OnStart: func(ctx context.Context) error {
			go func() {
				// Create a new span
				// If a span is already present in the given context, the new span
				// will a child of that one, otherwise it will be a root span
				// The resulting context embeds the new span
				ctx, span := tracer.Start(context.Background(), "my-job")
				job(ctx)
				defer span.End()
				sd.Shutdown() //nolint:errcheck
			}()
			return nil
		},
	})
}

func job(_ context.Context) {
	time.Sleep(1 * time.Millisecond)
}

var zapOpts = []zap.Option{
	zap.WithCaller(false),
	zap.WithClock(&fixedClock{ts: 1257894000}),
}

type fixedClock struct {
	ts int64
}

func (c *fixedClock) Now() time.Time {
	return time.Unix(c.ts, 0).UTC()
}

func (c *fixedClock) NewTicker(d time.Duration) *time.Ticker {
	return time.NewTicker(d)
}
Output:
{"level":"info","ts":"2009-11-10T23:00:00.000Z","msg":"Using configuration","conf":{"Mode":"production","Enabled":true,"InsecureConnection":true,"CertFile":"","KeyFile":"","RootCAFile":"","Endpoint":""}}
{"level":"info","ts":"2009-11-10T23:00:00.000Z","msg":"Final configuration","conf":{"Mode":"production","Enabled":true,"InsecureConnection":true,"CertFile":"","KeyFile":"","RootCAFile":"","Endpoint":""}}

Index

Examples

Constants

This section is empty.

Variables

This section is empty.

Functions

func NewModule

func NewModule(conf TracingConfig) fx.Option

NewModule provides an opentelemetry TracingProvider to the system

func NewTracerProvider

func NewTracerProvider(lc fx.Lifecycle, conf TracingConfig, logger *zap.Logger) (trace.TracerProvider, error)

Types

type ClientStatsHandlerResult

type ClientStatsHandlerResult struct {
	fx.Out

	Handler stats.Handler `group:"client_stats_handler"`
}

func NewClientStatsHandler

func NewClientStatsHandler(tracerProvider trace.TracerProvider) ClientStatsHandlerResult

NewClientStatsHandler returns a grpc stats.Handler for use in a client that automatically traces requests

type HttpMiddlewareResult

type HttpMiddlewareResult struct {
	fx.Out

	Middleware *fxhttp.Middleware `group:"http_middleware"`
}

func NewHttpMiddleware

func NewHttpMiddleware(tracerProvider trace.TracerProvider) HttpMiddlewareResult

type ServerStatsHandlerResult

type ServerStatsHandlerResult struct {
	fx.Out

	Handler stats.Handler `group:"server_stats_handler"`
}

func NewServerStatsHandler

func NewServerStatsHandler(tracerProvider trace.TracerProvider) ServerStatsHandlerResult

NewServerStatsHandler returns a grpc stats.Handler for use in a server that automatically traces requests

type Tracing

type Tracing struct {
	// Enabled allows tracing support to be toggled on and off
	Enabled bool
	// InsecureConnection indicates whether TLS needs to be disabled when connecting to the grpc server
	InsecureConnection bool
	// CertFile is the path to the pem encoded TLS certificate
	CertFile string `validate:"required_if=Enabled true InsecureConnection false,omitempty,file"`
	// KeyFile is the path to the pem encoded private key of the TLS certificate
	KeyFile string `validate:"required_if=Enabled true InsecureConnection false,omitempty,file"`
	// RootCAFile is the  path to a pem encoded CA bundle used to validate server connections
	RootCAFile string `validate:"required_if=Enabled true InsecureConnection false,omitempty,file"`
	// Endpoint is the address + port where the collector can be reached
	Endpoint string `validate:"required_if=Enabled true InsecureConnection false,omitempty,hostname_port"`
}

func (*Tracing) GrpcClientConfig

func (t *Tracing) GrpcClientConfig() *fxgrpc.Client

func (*Tracing) MarshalLogObject

func (t *Tracing) MarshalLogObject(enc zapcore.ObjectEncoder) error

func (*Tracing) TracingConfig

func (t *Tracing) TracingConfig() *Tracing

type TracingConfig

type TracingConfig interface {
	TracingConfig() *Tracing
}

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL