diff --git a/lightstep/sdk/internal/common.go b/lightstep/sdk/internal/common.go index fb44ed34..3e7f71e5 100644 --- a/lightstep/sdk/internal/common.go +++ b/lightstep/sdk/internal/common.go @@ -15,15 +15,14 @@ package internal import ( + "errors" + "strings" + "sync" + + "go.opentelemetry.io/collector/component" "go.opentelemetry.io/collector/config/configtelemetry" - "go.opentelemetry.io/collector/exporter" - "go.opentelemetry.io/otel" - noopmetric "go.opentelemetry.io/otel/metric/noop" "go.opentelemetry.io/otel/trace" - nooptrace "go.opentelemetry.io/otel/trace/noop" "go.uber.org/zap" - "strings" - "sync" "go.opentelemetry.io/collector/pdata/pcommon" "go.opentelemetry.io/otel/attribute" @@ -206,46 +205,26 @@ const ( func ConfigureSelfTelemetry( name string, - selfSpans bool, - selfMetrics bool, - exporterSettings *exporter.Settings, - tracer *trace.Tracer, - telemetryItemsCounter *metricapi.Int64Counter, -) error { + tp trace.TracerProvider, + mp metric.MeterProvider, +) (component.TelemetrySettings, trace.Tracer, metricapi.Int64Counter, error) { + var settings component.TelemetrySettings // setup logs - logger, err := zap.NewProduction() - if err != nil { - return err - } - - exporterSettings.TelemetrySettings.Logger = logger + logger, logErr := zap.NewProduction() - // setup traces - tracerProvider := trace.TracerProvider(nooptrace.NewTracerProvider()) - if selfSpans { - tracerProvider = otel.GetTracerProvider() - } - - exporterSettings.TelemetrySettings.TracerProvider = tracerProvider - *tracer = exporterSettings.TelemetrySettings.TracerProvider.Tracer(name) - - // setup metrics - meterProvider := metricapi.MeterProvider(noopmetric.NewMeterProvider()) - if selfMetrics { - meterProvider = NOTelColMeterProvider(otel.GetMeterProvider()) - } - - exporterSettings.TelemetrySettings.MetricsLevel = configtelemetry.LevelNormal - exporterSettings.TelemetrySettings.MeterProvider = meterProvider - exporterSettings.TelemetrySettings.LeveledMeterProvider = func(level configtelemetry.Level) metricapi.MeterProvider { - return meterProvider - } + // this replaces otelcol_ w/ otelsdk_ + mp = NOTelColMeterProvider(mp) - // setup the telemetry item counter metric - if telemetryItemsCounter != nil { - meter := exporterSettings.TelemetrySettings.LeveledMeterProvider(configtelemetry.LevelNormal).Meter(name) - *telemetryItemsCounter, err = meter.Int64Counter(selfTelemetryItemsCounterName) + settings.Logger = logger + settings.TracerProvider = tp + settings.MeterProvider = mp + settings.MetricsLevel = configtelemetry.LevelNormal + settings.LeveledMeterProvider = func(level configtelemetry.Level) metricapi.MeterProvider { + return mp } - return err + tracer := tp.Tracer(name) + meter := mp.Meter(name) + counter, metErr := meter.Int64Counter(selfTelemetryItemsCounterName) + return settings, tracer, counter, errors.Join(logErr, metErr) } diff --git a/lightstep/sdk/internal/go.mod b/lightstep/sdk/internal/go.mod index 77ae409c..7ed5d167 100644 --- a/lightstep/sdk/internal/go.mod +++ b/lightstep/sdk/internal/go.mod @@ -6,8 +6,8 @@ toolchain go1.22.5 require ( github.com/stretchr/testify v1.9.0 + go.opentelemetry.io/collector/component v0.111.0 go.opentelemetry.io/collector/config/configtelemetry v0.111.0 - go.opentelemetry.io/collector/exporter v0.111.0 go.opentelemetry.io/collector/pdata v1.17.0 go.opentelemetry.io/otel v1.30.0 go.opentelemetry.io/otel/metric v1.30.0 @@ -22,15 +22,8 @@ require ( github.com/go-logr/stdr v1.2.2 // indirect github.com/gogo/protobuf v1.3.2 // indirect github.com/google/uuid v1.6.0 // indirect - github.com/json-iterator/go v1.1.12 // indirect - github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect - github.com/modern-go/reflect2 v1.0.2 // indirect github.com/pmezard/go-difflib v1.0.0 // indirect github.com/rogpeppe/go-internal v1.11.0 // indirect - go.opentelemetry.io/collector/component v0.111.0 // indirect - go.opentelemetry.io/collector/consumer v0.111.0 // indirect - go.opentelemetry.io/collector/internal/globalsignal v0.111.0 // indirect - go.opentelemetry.io/collector/pipeline v0.111.0 // indirect go.uber.org/multierr v1.11.0 // indirect golang.org/x/net v0.28.0 // indirect golang.org/x/sys v0.25.0 // indirect diff --git a/lightstep/sdk/internal/go.sum b/lightstep/sdk/internal/go.sum index 5bc5446c..23e45f71 100644 --- a/lightstep/sdk/internal/go.sum +++ b/lightstep/sdk/internal/go.sum @@ -1,4 +1,3 @@ -github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/go-logr/logr v1.2.2/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A= @@ -10,28 +9,18 @@ github.com/gogo/protobuf v1.3.2 h1:Ov1cvc58UF3b5XjBnZv7+opcTcQFZebYjWzi34vdm4Q= github.com/gogo/protobuf v1.3.2/go.mod h1:P1XiOD3dCwIKUDQYPy72D8LYyHL2YPYrpS2s69NZV8Q= github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI= github.com/google/go-cmp v0.6.0/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= -github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0= github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= -github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM= -github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo= github.com/kisielk/errcheck v1.5.0/go.mod h1:pFxgyoBC7bSaBwPgfKdkLd5X25qrDl4LWUI2bnpBCr8= github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck= github.com/kr/pretty v0.3.1 h1:flRD4NNwYAUpkphVc1HcthR4KEIFJ65n8Mw5qdRn3LE= github.com/kr/pretty v0.3.1/go.mod h1:hoEshYVHaxMs3cyo3Yncou5ZscifuDolrwPKZanG3xk= github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= -github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= -github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd h1:TRLaZ9cD/w8PVh93nsPXa1VrQ6jlwL5oN8l14QlcNfg= -github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= -github.com/modern-go/reflect2 v1.0.2 h1:xBagoLtFs94CBntxluKeaWgTMpvLxC4ur3nMaC9Gz0M= -github.com/modern-go/reflect2 v1.0.2/go.mod h1:yWuevngMOJpCy52FWWMvUC8ws7m/LJsjYzDa0/r8luk= github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/rogpeppe/go-internal v1.11.0 h1:cWPaGQEPrBb5/AsnsZesgZZ9yb1OQ+GOISoDNXVBh4M= github.com/rogpeppe/go-internal v1.11.0/go.mod h1:ddIwULY96R17DhadqLgMfk9H9tvdUzkipdSkR5nkCZA= -github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= -github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg= github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= @@ -40,22 +29,8 @@ go.opentelemetry.io/collector/component v0.111.0 h1:AiDIrhkq6sbHnU9Rhq6t4DC4Gal4 go.opentelemetry.io/collector/component v0.111.0/go.mod h1:wYwbRuhzK5bm5x1bX+ukm1tT50QXYLs4MKwzyfiVGoE= go.opentelemetry.io/collector/config/configtelemetry v0.111.0 h1:Q3TJRM2A3FIDjIvzWa3uFArsdFN0I/0GzcWynHjC+oY= go.opentelemetry.io/collector/config/configtelemetry v0.111.0/go.mod h1:R0MBUxjSMVMIhljuDHWIygzzJWQyZHXXWIgQNxcFwhc= -go.opentelemetry.io/collector/consumer v0.111.0 h1:d2kRTDnu+p0q4D5fTU+Pk59KRm5F2JRYrk30Ep5j0xI= -go.opentelemetry.io/collector/consumer v0.111.0/go.mod h1:FjY9bPbVkFZLKKxnNbGsIqaz3lcFDKGf+7wxA1uCugs= -go.opentelemetry.io/collector/consumer/consumerprofiles v0.111.0 h1:w9kGdTaXdwD/ZtbxVOvuYQEFKBX3THQgEz/enQnMt9s= -go.opentelemetry.io/collector/consumer/consumerprofiles v0.111.0/go.mod h1:Ebt1jDdrQb3G2sNHrWHNr5wS3UJ9k3h8LHCqUPTbxLY= -go.opentelemetry.io/collector/consumer/consumertest v0.111.0 h1:ZEikGRPdrhVAq7xhJVc8WapRBVN/CdPnMEnXgpRGu1U= -go.opentelemetry.io/collector/consumer/consumertest v0.111.0/go.mod h1:EHPrn8ovcTGdTDlCEi1grOXSP3jUUYU0zvl92uA5L+4= -go.opentelemetry.io/collector/exporter v0.111.0 h1:NpiP6xXGOmSi59RlB5gGTB+PtCLldVeK3vCQBJPW0sU= -go.opentelemetry.io/collector/exporter v0.111.0/go.mod h1:FjO80zGWZjqXil8vM1MS8gyxxzZ29WmChTNV2y9xjHo= -go.opentelemetry.io/collector/internal/globalsignal v0.111.0 h1:oq0nSD+7K2Q1Fx5d3s6lPRdKZeTL0FEg4sIaR7ZJzIc= -go.opentelemetry.io/collector/internal/globalsignal v0.111.0/go.mod h1:GqMXodPWOxK5uqpX8MaMXC2389y2XJTa5nPwf8FYDK8= go.opentelemetry.io/collector/pdata v1.17.0 h1:z8cjjT2FThAehWu5fbF48OnZyK5q8xd1UhC4XszDo0w= go.opentelemetry.io/collector/pdata v1.17.0/go.mod h1:yZaQ9KZAm/qie96LTygRKxOXMq0/54h8OW7330ycuvQ= -go.opentelemetry.io/collector/pdata/pprofile v0.111.0 h1:4if6rItcX8a6X4bIh6lwQnlE+ncKXQaIim7F5O7ZA58= -go.opentelemetry.io/collector/pdata/pprofile v0.111.0/go.mod h1:iBwrNFB6za1qspy46ZE41H3MmcxUogn2AuYbrWdoMd8= -go.opentelemetry.io/collector/pipeline v0.111.0 h1:qENDGvWWnDXguEfmj8eO+5kr8Y6XFKytU5SuMinz3Ls= -go.opentelemetry.io/collector/pipeline v0.111.0/go.mod h1:ZZMU3019geEU283rTW5M/LkcqLqHp/YI2Nl6/Vp68PQ= go.opentelemetry.io/otel v1.30.0 h1:F2t8sK4qf1fAmY9ua4ohFS/K+FUuOPemHUIXHtktrts= go.opentelemetry.io/otel v1.30.0/go.mod h1:tFw4Br9b7fOS+uEao81PJjVMjW/5fvNCbpsDIXqP0pc= go.opentelemetry.io/otel/metric v1.30.0 h1:4xNulvn9gjzo4hjg+wzIKG7iNFEaBMX00Qd4QIZs7+w= diff --git a/lightstep/sdk/metric/exporters/otlp/otelcol/client.go b/lightstep/sdk/metric/exporters/otlp/otelcol/client.go index 46cd18c8..edb06972 100644 --- a/lightstep/sdk/metric/exporters/otlp/otelcol/client.go +++ b/lightstep/sdk/metric/exporters/otlp/otelcol/client.go @@ -34,8 +34,11 @@ import ( "go.opentelemetry.io/collector/exporter" "go.opentelemetry.io/collector/exporter/exporterhelper" "go.opentelemetry.io/collector/processor" + "go.opentelemetry.io/otel" metricapi "go.opentelemetry.io/otel/metric" + metricnoop "go.opentelemetry.io/otel/metric/noop" traceapi "go.opentelemetry.io/otel/trace" + tracenoop "go.opentelemetry.io/otel/trace/noop" "go.uber.org/multierr" ) @@ -147,16 +150,23 @@ func NewExporter(ctx context.Context, cfg Config) (metric.PushExporter, error) { c.settings.ID = component.NewID(component.MustNewType("otel_sdk_metric_otlp")) } - err := internal.ConfigureSelfTelemetry( - "lightstep-go/sdk/metric", - cfg.SelfSpans, - cfg.SelfMetrics, - &c.settings, - &c.tracer, - &c.counter, - ) - if err != nil { + var mp metricapi.MeterProvider = metricnoop.NewMeterProvider() + var tp traceapi.TracerProvider = tracenoop.NewTracerProvider() + + if cfg.SelfSpans { + tp = otel.GetTracerProvider() + } + if cfg.SelfMetrics { + mp = otel.GetMeterProvider() + } + + if settings, tracer, counter, err := + internal.ConfigureSelfTelemetry("lightstep-go/sdk/metric", tp, mp); err != nil { return nil, err + } else { + c.settings.TelemetrySettings = settings + c.tracer = tracer + c.counter = counter } exp, err := otelarrowexporter.NewFactory().CreateMetricsExporter(ctx, c.settings, &cfg.Exporter) diff --git a/lightstep/sdk/metric/exporters/prom/client.go b/lightstep/sdk/metric/exporters/prom/client.go index e760ce85..af1eedfb 100644 --- a/lightstep/sdk/metric/exporters/prom/client.go +++ b/lightstep/sdk/metric/exporters/prom/client.go @@ -17,6 +17,8 @@ package prom import ( "context" "fmt" + "time" + "github.com/lightstep/otel-launcher-go/lightstep/sdk/internal" "github.com/lightstep/otel-launcher-go/lightstep/sdk/metric" "github.com/lightstep/otel-launcher-go/lightstep/sdk/metric/data" @@ -26,10 +28,12 @@ import ( "go.opentelemetry.io/collector/component" "go.opentelemetry.io/collector/config/confighttp" "go.opentelemetry.io/collector/exporter" + "go.opentelemetry.io/otel" metricapi "go.opentelemetry.io/otel/metric" + metricnoop "go.opentelemetry.io/otel/metric/noop" traceapi "go.opentelemetry.io/otel/trace" + tracenoop "go.opentelemetry.io/otel/trace/noop" "go.uber.org/multierr" - "time" ) // TODO: Config, Option, and the option impls are duplicated between @@ -97,16 +101,23 @@ func NewExporter(ctx context.Context, cfg Config) (metric.PushExporter, error) { c.settings.ID = component.NewID(component.MustNewType("otel_sdk_metric_prom")) - err := internal.ConfigureSelfTelemetry( - "lightstep-go/sdk/metric", - cfg.SelfSpans, - cfg.SelfMetrics, - &c.settings, - &c.tracer, - &c.counter, - ) - if err != nil { + var mp metricapi.MeterProvider = metricnoop.NewMeterProvider() + var tp traceapi.TracerProvider = tracenoop.NewTracerProvider() + + if cfg.SelfSpans { + tp = otel.GetTracerProvider() + } + if cfg.SelfMetrics { + mp = otel.GetMeterProvider() + } + + if settings, tracer, counter, err := + internal.ConfigureSelfTelemetry("lightstep-go/sdk/metric", tp, mp); err != nil { return nil, err + } else { + c.settings.TelemetrySettings = settings + c.tracer = tracer + c.counter = counter } exp, err := prometheusexporter.NewFactory().CreateMetricsExporter(ctx, c.settings, &cfg.Exporter) diff --git a/lightstep/sdk/metric/internal/export/export.go b/lightstep/sdk/metric/internal/export/export.go index f1a9ae7b..a2262284 100644 --- a/lightstep/sdk/metric/internal/export/export.go +++ b/lightstep/sdk/metric/internal/export/export.go @@ -356,7 +356,7 @@ func ExportMetrics( if err == nil { span.SetStatus(otelcodes.Ok, state) } else { - span.SetStatus(otelcodes.Error, state) + span.SetStatus(otelcodes.Error, err.Error()) } return err } diff --git a/lightstep/sdk/trace/exporters/otlp/otelcol/client.go b/lightstep/sdk/trace/exporters/otlp/otelcol/client.go index 181377cb..76c70973 100644 --- a/lightstep/sdk/trace/exporters/otlp/otelcol/client.go +++ b/lightstep/sdk/trace/exporters/otlp/otelcol/client.go @@ -30,11 +30,14 @@ import ( "go.opentelemetry.io/collector/exporter" "go.opentelemetry.io/collector/exporter/exporterhelper" "go.opentelemetry.io/collector/processor" + "go.opentelemetry.io/otel" "go.opentelemetry.io/otel/attribute" otelcodes "go.opentelemetry.io/otel/codes" - "go.opentelemetry.io/otel/metric" + metricapi "go.opentelemetry.io/otel/metric" + metricnoop "go.opentelemetry.io/otel/metric/noop" "go.opentelemetry.io/otel/sdk/trace" traceapi "go.opentelemetry.io/otel/trace" + tracenoop "go.opentelemetry.io/otel/trace/noop" "go.uber.org/multierr" "github.com/lightstep/otel-launcher-go/lightstep/sdk/internal" @@ -53,7 +56,7 @@ type Config struct { type ExporterOptions struct { TracerProvider traceapi.TracerProvider - MeterProvider metric.MeterProvider + MeterProvider metricapi.MeterProvider } func WithTracerProvider(tp traceapi.TracerProvider) func(*ExporterOptions) { @@ -62,7 +65,7 @@ func WithTracerProvider(tp traceapi.TracerProvider) func(*ExporterOptions) { } } -func WithMeterProvider(mp metric.MeterProvider) func(*ExporterOptions) { +func WithMeterProvider(mp metricapi.MeterProvider) func(*ExporterOptions) { return func(opts *ExporterOptions) { opts.MeterProvider = mp } @@ -75,6 +78,7 @@ type client struct { batcher processor.Traces settings exporter.Settings tracer traceapi.Tracer + counter metricapi.Int64Counter } func (c *client) ExportSpans(ctx context.Context, spans []trace.ReadOnlySpan) error { @@ -104,11 +108,12 @@ func (c *client) ExportSpans(ctx context.Context, spans []trace.ReadOnlySpan) er attribute.Bool("success", success), attribute.String("state", state), } + c.counter.Add(ctx, int64(count), metricapi.WithAttributes(attrs...)) span.SetAttributes(append(attrs, attribute.Int("num_spans", count))...) if err == nil { span.SetStatus(otelcodes.Ok, state) } else { - span.SetStatus(otelcodes.Error, state) + span.SetStatus(otelcodes.Error, err.Error()) } return err } @@ -201,7 +206,10 @@ func WithTLSSetting(tlss configtls.ClientConfig) Option { } func NewExporter(ctx context.Context, cfg Config, opts ...func(options *ExporterOptions)) (trace.SpanExporter, error) { - options := ExporterOptions{} + options := ExporterOptions{ + MeterProvider: nil, + TracerProvider: nil, + } for _, opt := range opts { opt(&options) } @@ -214,16 +222,31 @@ func NewExporter(ctx context.Context, cfg Config, opts ...func(options *Exporter c.settings.ID = component.NewID(component.MustNewType("otel_sdk_trace_otlp")) } - err := internal.ConfigureSelfTelemetry( - "lightstep-go/sdk/trace", - cfg.SelfSpans, - cfg.SelfMetrics, - &c.settings, - &c.tracer, - nil, - ) - if err != nil { + if options.MeterProvider == nil { + if cfg.SelfMetrics { + options.MeterProvider = otel.GetMeterProvider() + } else { + options.MeterProvider = metricnoop.NewMeterProvider() + } + } + if options.TracerProvider == nil { + if cfg.SelfSpans { + options.TracerProvider = otel.GetTracerProvider() + } else { + options.TracerProvider = tracenoop.NewTracerProvider() + } + } + + if settings, tracer, counter, err := + internal.ConfigureSelfTelemetry( + "lightstep-go/sdk/trace", + options.TracerProvider, + options.MeterProvider); err != nil { return nil, err + } else { + c.settings.TelemetrySettings = settings + c.tracer = tracer + c.counter = counter } exp, err := otelarrowexporter.NewFactory().CreateTracesExporter(ctx, c.settings, &cfg.Exporter)