Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 14 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -180,11 +180,22 @@ metricExporter, err := otlpmetricgrpc.New(
otlpmetricgrpc.WithTLSCredentials(insecure.NewCredentials()))
```

And configuring an OTLP compliant logs exporters can be done as follows:

```go
import "go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploggrpc"
// ...
logExporter, err := otlploggrpc.New(
context.Background(),
otlploggrpc.WithEndpoint("localhost:4317"),
otlploggrpc.WithTLSCredentials(insecure.NewCredentials()))
```

These exporters can then be used to configure Clue:

```go
// Configure OpenTelemetry.
cfg := clue.NewConfig(ctx, "service", "1.0.0", metricExporter, spanExporter)
cfg := clue.NewConfig(ctx, "service", "1.0.0", metricExporter, spanExporter, logExporter)
clue.ConfigureOpenTelemetry(ctx, cfg)
```

Expand Down Expand Up @@ -330,7 +341,8 @@ v1.x:
ctx := log.Context(context.Background())
traceExporter := tracestdout.New()
metricsExporter := metricstdout.New()
cfg := clue.NewConfig(ctx, "service", "1.0.0", metricsExporter, traceExporter)
logsExporter = logsstdout.New()
cfg := clue.NewConfig(ctx, "service", "1.0.0", metricsExporter, traceExporter, logsExplorer)
clue.ConfigureOpenTelemetry(ctx, cfg)
```

Expand Down
25 changes: 24 additions & 1 deletion clue/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,15 +5,19 @@ import (

"github.com/go-logr/logr"
"go.opentelemetry.io/otel"
otellog "go.opentelemetry.io/otel/log"
"go.opentelemetry.io/otel/log/global"
"go.opentelemetry.io/otel/metric"
metricnoop "go.opentelemetry.io/otel/metric/noop"
"go.opentelemetry.io/otel/propagation"
sdklog "go.opentelemetry.io/otel/sdk/log"
sdkmetric "go.opentelemetry.io/otel/sdk/metric"
"go.opentelemetry.io/otel/sdk/resource"
sdktrace "go.opentelemetry.io/otel/sdk/trace"
semconv "go.opentelemetry.io/otel/semconv/v1.34.0"
"go.opentelemetry.io/otel/trace"
tracenoop "go.opentelemetry.io/otel/trace/noop"
lognoop "go.opentelemetry.io/otel/log/noop"

"goa.design/clue/log"

Expand All @@ -30,6 +34,8 @@ type (
MeterProvider metric.MeterProvider
// TracerProvider is the OpenTelemetry tracer provider used clue
TracerProvider trace.TracerProvider
// LoggerProvider is the OpenTelemetry logger provider used by clue
LoggerProvider otellog.LoggerProvider
// Propagators is the OpenTelemetry propagator used by clue
Propagators propagation.TextMapPropagator
// ErrorHandler is the error handler used by OpenTelemetry
Expand All @@ -42,6 +48,7 @@ type (
func ConfigureOpenTelemetry(ctx context.Context, cfg *Config) {
otel.SetMeterProvider(cfg.MeterProvider)
otel.SetTracerProvider(cfg.TracerProvider)
global.SetLoggerProvider(cfg.LoggerProvider)
otel.SetTextMapPropagator(cfg.Propagators)
otel.SetLogger(logr.New(log.ToLogrSink(ctx)))
otel.SetErrorHandler(cfg.ErrorHandler)
Expand All @@ -67,13 +74,18 @@ func ConfigureOpenTelemetry(ctx context.Context, cfg *Config) {
// if err != nil {
// return err
// }
// cfg := clue.NewConfig(ctx, "mysvc", "1.0.0", metricExporter, spanExporter)
// logExporter, err := stdoutlog.New()
// if err != nil {
// return err
// }
// cfg := clue.NewConfig(ctx, "mysvc", "1.0.0", metricExporter, spanExporter, logExporter)
func NewConfig(
ctx context.Context,
svcName string,
svcVersion string,
metricExporter sdkmetric.Exporter,
spanExporter sdktrace.SpanExporter,
logExporter sdklog.Exporter,
opts ...Option,
) (*Config, error) {
options := defaultOptions(ctx)
Expand Down Expand Up @@ -125,9 +137,20 @@ func NewConfig(
sdktrace.WithBatcher(spanExporter),
)
}
var loggerProvider otellog.LoggerProvider
if logExporter == nil {
loggerProvider = lognoop.NewLoggerProvider()
} else {
loggerProvider = sdklog.NewLoggerProvider(
sdklog.WithResource(res),
sdklog.WithProcessor(sdklog.NewBatchProcessor(logExporter)),
)
}

return &Config{
MeterProvider: meterProvider,
TracerProvider: tracerProvider,
LoggerProvider: loggerProvider,
Propagators: options.propagators,
ErrorHandler: options.errorHandler,
}, nil
Expand Down
21 changes: 21 additions & 0 deletions clue/config_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,11 +8,16 @@ import (
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
"go.opentelemetry.io/otel"
"go.opentelemetry.io/otel/exporters/stdout/stdoutlog"
"go.opentelemetry.io/otel/exporters/stdout/stdoutmetric"
"go.opentelemetry.io/otel/exporters/stdout/stdouttrace"
otellog "go.opentelemetry.io/otel/log"
"go.opentelemetry.io/otel/log/global"
lognoop "go.opentelemetry.io/otel/log/noop"
"go.opentelemetry.io/otel/metric"
metricnoop "go.opentelemetry.io/otel/metric/noop"
"go.opentelemetry.io/otel/propagation"
sdklog "go.opentelemetry.io/otel/sdk/log"
sdkmetric "go.opentelemetry.io/otel/sdk/metric"
sdktrace "go.opentelemetry.io/otel/sdk/trace"
"go.opentelemetry.io/otel/trace"
Expand All @@ -29,17 +34,20 @@ func TestConfigureOpenTelemetry(t *testing.T) {
ctx := log.Context(context.Background())
noopMeterProvider := metricnoop.NewMeterProvider()
noopTracerProvider := tracenoop.NewTracerProvider()
noopLoggerProvider := lognoop.NewLoggerProvider()
noopErrorHandler := dummyErrorHandler{}

cases := []struct {
name string
meterProvider metric.MeterProvider
tracerProvider trace.TracerProvider
loggerProvider otellog.LoggerProvider
propagators propagation.TextMapPropagator
errorHandler otel.ErrorHandler

wantMeterProvider metric.MeterProvider
wantTracerProvider trace.TracerProvider
wantLoggerProvider otellog.LoggerProvider
wantPropagators propagation.TextMapPropagator
wantErrorHandler bool
}{
Expand All @@ -53,6 +61,10 @@ func TestConfigureOpenTelemetry(t *testing.T) {
name: "tracer provider",
tracerProvider: noopTracerProvider,
wantTracerProvider: noopTracerProvider,
}, {
name: "logger provider",
loggerProvider: noopLoggerProvider,
wantLoggerProvider: noopLoggerProvider,
}, {
name: "propagators",
propagators: propagation.Baggage{},
Expand All @@ -68,12 +80,14 @@ func TestConfigureOpenTelemetry(t *testing.T) {
cfg := &Config{
MeterProvider: c.meterProvider,
TracerProvider: c.tracerProvider,
LoggerProvider: c.loggerProvider,
Propagators: c.propagators,
ErrorHandler: c.errorHandler,
}
ConfigureOpenTelemetry(ctx, cfg)
assert.Equal(t, c.wantMeterProvider, otel.GetMeterProvider())
assert.Equal(t, c.wantTracerProvider, otel.GetTracerProvider())
assert.Equal(t, c.wantLoggerProvider, global.GetLoggerProvider())
assert.Equal(t, c.wantPropagators, otel.GetTextMapPropagator())
})
}
Expand All @@ -87,12 +101,15 @@ func TestNewConfig(t *testing.T) {
require.NoError(t, err)
metricsExporter, err := stdoutmetric.New()
require.NoError(t, err)
logExporter, err := stdoutlog.New()
require.NoError(t, err)
noopErrorHandler := dummyErrorHandler{}

cases := []struct {
name string
metricsExporter sdkmetric.Exporter
spanExporter sdktrace.SpanExporter
logExporter sdklog.Exporter
propagators propagation.TextMapPropagator
errorHandler otel.ErrorHandler

Expand All @@ -107,6 +124,9 @@ func TestNewConfig(t *testing.T) {
}, {
name: "tracer provider",
spanExporter: spanExporter,
}, {
name: "log exporter",
logExporter: logExporter,
}, {
name: "propagators",
propagators: propagation.Baggage{},
Expand All @@ -124,6 +144,7 @@ func TestNewConfig(t *testing.T) {
svcVersion,
c.metricsExporter,
c.spanExporter,
c.logExporter,
WithPropagators(c.propagators),
WithErrorHandler(c.errorHandler))
require.NoError(t, err)
Expand Down
39 changes: 39 additions & 0 deletions clue/exporters.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,13 @@ package clue
import (
"context"

"go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploggrpc"
"go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploghttp"
"go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetricgrpc"
"go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetrichttp"
"go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc"
"go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp"
otellog "go.opentelemetry.io/otel/sdk/log"
"go.opentelemetry.io/otel/sdk/metric"
"go.opentelemetry.io/otel/sdk/trace"

Expand All @@ -15,12 +18,31 @@ import (

// Allow mocking
var (
otlploggrpcNew = otlploggrpc.New
otlploghttpNew = otlploghttp.New
otlpmetricgrpcNew = otlpmetricgrpc.New
otlpmetrichttpNew = otlpmetrichttp.New
otlptracegrpcNew = otlptracegrpc.New
otlptracehttpNew = otlptracehttp.New
)

// NewGRPCLogExporter returns an OpenTelementry Protocol logs exporter that
// report logs to a gRPC collector.
func NewGRPCLogExporter(ctx context.Context, options ...otlploggrpc.Option) (exporter otellog.Exporter, shutdown func(), err error) {
exporter, err = otlploggrpcNew(ctx, options...)
if err != nil {
return
}
shutdown = func() {
// Create new context in case the parent context has been canceled.
ctx := log.WithContext(context.Background(), ctx)
if err := exporter.Shutdown(ctx); err != nil {
log.Errorf(ctx, err, "failed to shutdown log exporter")
}
}
return
}

// NewGRPCMetricExporter returns an OpenTelementry Protocol metric exporter that
// report metrics to a gRPC collector.
func NewGRPCMetricExporter(ctx context.Context, options ...otlpmetricgrpc.Option) (exporter metric.Exporter, shutdown func(), err error) {
Expand Down Expand Up @@ -55,6 +77,23 @@ func NewGRPCSpanExporter(ctx context.Context, options ...otlptracegrpc.Option) (
return
}

// NewHTTPLogExporter returns an OpenTelementry Protocol logs exporter that
// report logs to a HTTP collector.
func NewHTTPLogExporter(ctx context.Context, options ...otlploghttp.Option) (exporter otellog.Exporter, shutdown func(), err error) {
exporter, err = otlploghttpNew(ctx, options...)
if err != nil {
return
}
shutdown = func() {
// Create new context in case the parent context has been canceled.
ctx := log.WithContext(context.Background(), ctx)
if err := exporter.Shutdown(ctx); err != nil {
log.Errorf(ctx, err, "failed to shutdown log exporter")
}
}
return
}

// NewHTTPMetricExporter returns an OpenTelementry Protocol metric exporter that
// report metrics to a HTTP collector.
func NewHTTPMetricExporter(ctx context.Context, options ...otlpmetrichttp.Option) (exporter metric.Exporter, shutdown func(), err error) {
Expand Down
15 changes: 15 additions & 0 deletions example/weather/services/forecaster/cmd/forecaster/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import (
"go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc"
"go.opentelemetry.io/contrib/instrumentation/net/http/httptrace/otelhttptrace"
"go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp"
"go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploggrpc"
"go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetricgrpc"
"go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc"
"goa.design/clue/clue"
Expand Down Expand Up @@ -82,11 +83,25 @@ func main() {
log.Errorf(ctx, err, "failed to shutdown metrics")
}
}()
logExporter, err := otlploggrpc.New(ctx,
otlploggrpc.WithEndpoint(*coladdr),
otlploggrpc.WithInsecure())
if err != nil {
log.Errorf(ctx, err, "failed to initialize logging")
}
defer func() {
ctx := log.Context(context.Background())
if err := logExporter.Shutdown(ctx); err != nil {
log.Errorf(ctx, err, "failed to shutdown logging")
}
}()

cfg, err := clue.NewConfig(ctx,
genforecaster.ServiceName,
genforecaster.APIVersion,
metricExporter,
spanExporter,
logExporter,
)
if err != nil {
log.Fatalf(ctx, err, "failed to initialize instrumentation")
Expand Down
15 changes: 15 additions & 0 deletions example/weather/services/front/cmd/front/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ import (

"go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc"
"go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp"
"go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploggrpc"
"go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetricgrpc"
"go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc"
"goa.design/clue/clue"
Expand Down Expand Up @@ -85,11 +86,25 @@ func main() {
log.Errorf(ctx, err, "failed to shutdown metrics")
}
}()
logExporter, err := otlploggrpc.New(ctx,
otlploggrpc.WithEndpoint(*coladdr),
otlploggrpc.WithInsecure())
if err != nil {
log.Errorf(ctx, err, "failed to initialize logging")
}
defer func() {
// Create new context in case the parent context has been canceled.
ctx := log.Context(context.Background(), log.WithFormat(format))
if err := logExporter.Shutdown(ctx); err != nil {
log.Errorf(ctx, err, "failed to shutdown logging")
}
}()
cfg, err := clue.NewConfig(ctx,
genfront.ServiceName,
genfront.APIVersion,
metricExporter,
spanExporter,
logExporter,
)
if err != nil {
log.Fatalf(ctx, err, "failed to initialize instrumentation")
Expand Down
15 changes: 15 additions & 0 deletions example/weather/services/locator/cmd/locator/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import (
"go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc"
"go.opentelemetry.io/contrib/instrumentation/net/http/httptrace/otelhttptrace"
"go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp"
"go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploggrpc"
"go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetricgrpc"
"go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc"
"goa.design/clue/clue"
Expand Down Expand Up @@ -84,11 +85,25 @@ func main() {
log.Errorf(ctx, err, "failed to shutdown metrics")
}
}()
logExporter, err := otlploggrpc.New(ctx,
otlploggrpc.WithEndpoint(*oteladdr),
otlploggrpc.WithInsecure())
if err != nil {
log.Errorf(ctx, err, "failed to initialize logging")
}
defer func() {
// Create new context in case the parent context has been canceled.
ctx := log.Context(context.Background(), log.WithFormat(format))
if err := logExporter.Shutdown(ctx); err != nil {
log.Errorf(ctx, err, "failed to shutdown logging")
}
}()
cfg, err := clue.NewConfig(ctx,
genlocator.ServiceName,
genlocator.APIVersion,
metricExporter,
spanExporter,
logExporter,
)
if err != nil {
log.Fatalf(ctx, err, "failed to initialize instrumentation")
Expand Down
Loading