From 4883cb119d59de101dba898fd02604b989734089 Mon Sep 17 00:00:00 2001 From: Tyler Yahn Date: Thu, 10 Jun 2021 16:22:47 +0000 Subject: [PATCH] Refactor exporter creation functions (#1985) * Remove InstallNewPipeline/NewExportPipeline funcs * Rename stdout NewExporter to New * Rename prometheus NewExporter func to New * Rename Jaeger exporter NewRawExporter func to New * Rename zipkin exporter NewRawExporter func to New * Rename otlp exporter creation funcs * Rename processortest exporter creation funcs * Update PR number in changelog * Fix spelling error * Rename remaining NewUnstartedExporter in otlp * Remove unused testing file --- CHANGELOG.md | 8 ++ bridge/opencensus/README.md | 2 +- example/jaeger/main.go | 2 +- example/namedtracer/main.go | 2 +- example/opencensus/main.go | 2 +- example/otel-collector/main.go | 2 +- example/passthrough/README.md | 2 +- example/passthrough/main.go | 2 +- example/prom-collector/main.go | 4 +- example/prometheus/go.mod | 2 + example/prometheus/main.go | 19 ++- example/zipkin/main.go | 2 +- exporters/metric/prometheus/example_test.go | 114 ------------------ exporters/metric/prometheus/prometheus.go | 41 +------ .../metric/prometheus/prometheus_test.go | 22 +++- exporters/otlp/README.md | 2 +- exporters/otlp/example_test.go | 4 +- exporters/otlp/otlp.go | 58 +-------- exporters/otlp/otlp_test.go | 48 +------- exporters/otlp/otlpgrpc/example_test.go | 6 +- .../otlp/otlpgrpc/otlp_integration_test.go | 26 ++-- exporters/otlp/otlphttp/driver_test.go | 24 ++-- exporters/otlp/otlptrace/exporter.go | 38 +----- exporters/otlp/otlptrace/exporter_test.go | 66 ---------- .../internal/otlptracetest/client.go | 2 +- .../otlptrace/otlptracegrpc/client_test.go | 24 ++-- .../otlp/otlptrace/otlptracegrpc/exporter.go | 25 +--- .../otlptrace/otlptracehttp/client_test.go | 22 ++-- .../otlp/otlptrace/otlptracehttp/exporter.go | 25 +--- exporters/otlp/otlptrace/otlptracehttp/go.mod | 1 - exporters/stdout/example_test.go | 65 +++++++--- exporters/stdout/exporter.go | 58 +-------- exporters/stdout/metric_test.go | 4 +- exporters/stdout/trace_test.go | 8 +- exporters/trace/jaeger/agent_test.go | 6 +- exporters/trace/jaeger/env_test.go | 6 +- exporters/trace/jaeger/jaeger.go | 31 +---- .../trace/jaeger/jaeger_benchmark_test.go | 2 +- exporters/trace/jaeger/jaeger_test.go | 64 ++-------- exporters/trace/zipkin/zipkin.go | 31 +---- exporters/trace/zipkin/zipkin_test.go | 100 ++------------- .../controller/basic/controller_test.go | 4 +- sdk/metric/controller/basic/push_test.go | 2 +- sdk/metric/processor/basic/basic_test.go | 2 +- sdk/metric/processor/processortest/test.go | 4 +- .../processor/processortest/test_test.go | 2 +- sdk/metric/processor/reducer/reducer_test.go | 2 +- website_docs/getting-started.md | 6 +- 48 files changed, 238 insertions(+), 756 deletions(-) delete mode 100644 exporters/metric/prometheus/example_test.go delete mode 100644 exporters/otlp/otlptrace/exporter_test.go diff --git a/CHANGELOG.md b/CHANGELOG.md index ae0eccd125e..38602b4362d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -74,6 +74,12 @@ This project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.htm - The `Get` method of the `TraceState` type from the `go.opentelemetry.io/otel/trace` package has been updated to accept a `string` instead of an `attribute.Key` type. (#1931) - The `Insert` method of the `TraceState` type from the `go.opentelemetry.io/otel/trace` package has been updated to accept a pair of `string`s instead of an `attribute.KeyValue` type. (#1931) - The `Delete` method of the `TraceState` type from the `go.opentelemetry.io/otel/trace` package has been updated to accept a `string` instead of an `attribute.Key` type. (#1931) +- Rename `NewExporter` to `New` in the `go.opentelemetry.io/otel/exporters/stdout` package. (#1985) +- Rename `NewExporter` to `New` in the `go.opentelemetry.io/otel/exporters/metric/prometheus` package. (#1985) +- Rename `NewExporter` to `New` in the `go.opentelemetry.io/otel/exporters/trace/jaeger` package. (#1985) +- Rename `NewExporter` to `New` in the `go.opentelemetry.io/otel/exporters/trace/zipkin` package. (#1985) +- Rename `NewExporter` to `New` in the `go.opentelemetry.io/otel/exporters/otlp` package. (#1985) +- Rename `NewUnstartedExporter` to `NewUnstarted` in the `go.opentelemetry.io/otel/exporters/otlp` package. (#1985) ### Deprecated @@ -96,6 +102,8 @@ This project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.htm - The `IsEmpty` method of the `TraceState` type in the `go.opentelemetry.io/otel/trace` package is removed in favor of using the added `TraceState.Len` method. (#1931) - The `Set`, `Value`, `ContextWithValue`, `ContextWithoutValue`, and `ContextWithEmpty` functions in the `go.opentelemetry.io/otel/baggage` package are removed. Handling of baggage is now done using the added `Baggage` type and related context functions (`ContextWithBaggage`, `ContextWithoutBaggage`, and `FromContext`) in that package. (TBD) +- The `InstallNewPipeline` and `NewExportPipeline` creation functions in all the exporters (prometheus, otlp, stdout, jaeger, and zipkin) have been removed. + These functions were deemed premature attempts to provide convenience that did not achieve this aim. (#1985) ### Fixed diff --git a/bridge/opencensus/README.md b/bridge/opencensus/README.md index 5e5f3dacb71..07dc57380b3 100644 --- a/bridge/opencensus/README.md +++ b/bridge/opencensus/README.md @@ -119,7 +119,7 @@ import ( // import logexporter "go.opencensus.io/examples/exporter" // exporter, _ := logexporter.NewLogExporter(logexporter.Options{}) // Instead, we can create an equivalent using the OpenTelemetry stdout exporter: -openTelemetryExporter, _ := stdout.NewExporter(stdout.WithPrettyPrint()) +openTelemetryExporter, _ := stdout.New(stdout.WithPrettyPrint()) exporter := opencensus.NewMetricExporter(openTelemetryExporter) // Use the wrapped OpenTelemetry exporter like you normally would with OpenCensus diff --git a/example/jaeger/main.go b/example/jaeger/main.go index 8afb2aa3ec7..1c9e5917cf6 100644 --- a/example/jaeger/main.go +++ b/example/jaeger/main.go @@ -42,7 +42,7 @@ const ( // about the application. func tracerProvider(url string) (*tracesdk.TracerProvider, error) { // Create the Jaeger exporter - exp, err := jaeger.NewRawExporter(jaeger.WithCollectorEndpoint(jaeger.WithEndpoint(url))) + exp, err := jaeger.New(jaeger.WithCollectorEndpoint(jaeger.WithEndpoint(url))) if err != nil { return nil, err } diff --git a/example/namedtracer/main.go b/example/namedtracer/main.go index 37063a4e550..830835904d9 100644 --- a/example/namedtracer/main.go +++ b/example/namedtracer/main.go @@ -38,7 +38,7 @@ var tp *sdktrace.TracerProvider // initTracer creates and registers trace provider instance. func initTracer() { var err error - exp, err := stdout.NewExporter(stdout.WithPrettyPrint()) + exp, err := stdout.New(stdout.WithPrettyPrint()) if err != nil { log.Panicf("failed to initialize stdout exporter %v\n", err) return diff --git a/example/opencensus/main.go b/example/opencensus/main.go index 32173bf4f3b..4ea5c68ef76 100644 --- a/example/opencensus/main.go +++ b/example/opencensus/main.go @@ -52,7 +52,7 @@ var ( func main() { log.Println("Using OpenTelemetry stdout exporter.") - otExporter, err := stdout.NewExporter(stdout.WithPrettyPrint()) + otExporter, err := stdout.New(stdout.WithPrettyPrint()) if err != nil { log.Fatal(err) } diff --git a/example/otel-collector/main.go b/example/otel-collector/main.go index 2560c04ac2c..932a96ec63b 100644 --- a/example/otel-collector/main.go +++ b/example/otel-collector/main.go @@ -56,7 +56,7 @@ func initProvider() func() { otlpgrpc.WithEndpoint("localhost:30080"), otlpgrpc.WithDialOption(grpc.WithBlock()), // useful for testing ) - exp, err := otlp.NewExporter(ctx, driver) + exp, err := otlp.New(ctx, driver) handleErr(err, "failed to create exporter") res, err := resource.New(ctx, diff --git a/example/passthrough/README.md b/example/passthrough/README.md index 282ae4f3512..9fd54cd4927 100644 --- a/example/passthrough/README.md +++ b/example/passthrough/README.md @@ -13,7 +13,7 @@ But the following will propagate context _and_ create new, potentially recorded ```golang // Setup SDK -exp, _ := stdout.NewExporter(stdout.WithPrettyPrint()) +exp, _ := stdout.New(stdout.WithPrettyPrint()) tp = sdktrace.NewTracerProvider( sdktrace.WithBatcher(exp), ) diff --git a/example/passthrough/main.go b/example/passthrough/main.go index 0974096ad68..69a6cae2526 100644 --- a/example/passthrough/main.go +++ b/example/passthrough/main.go @@ -76,7 +76,7 @@ func initPassthroughGlobals() { // set it as the global tracer provider func nonGlobalTracer() *sdktrace.TracerProvider { var err error - exp, err := stdout.NewExporter(stdout.WithPrettyPrint()) + exp, err := stdout.New(stdout.WithPrettyPrint()) if err != nil { log.Panicf("failed to initialize stdout exporter %v\n", err) } diff --git a/example/prom-collector/main.go b/example/prom-collector/main.go index 4300845a2c1..570f4b50f68 100644 --- a/example/prom-collector/main.go +++ b/example/prom-collector/main.go @@ -52,7 +52,7 @@ func initMeter() { otlpgrpc.WithEndpoint("localhost:30080"), otlpgrpc.WithDialOption(grpc.WithBlock()), // useful for testing ) - otlpExporter, err := otlp.NewExporter(ctx, driver) + otlpExporter, err := otlp.New(ctx, driver) if err != nil { log.Fatal("could not initialize OTLP:", err) @@ -76,7 +76,7 @@ func initMeter() { log.Fatal("could not start controller:", err) } - promExporter, err := prometheus.NewExporter(prometheus.Config{}, cont) + promExporter, err := prometheus.New(prometheus.Config{}, cont) if err != nil { log.Fatal("could not initialize prometheus:", err) } diff --git a/example/prometheus/go.mod b/example/prometheus/go.mod index 7fcf5ccc33d..a841cd7ec6d 100644 --- a/example/prometheus/go.mod +++ b/example/prometheus/go.mod @@ -12,6 +12,8 @@ require ( go.opentelemetry.io/otel v0.20.0 go.opentelemetry.io/otel/exporters/metric/prometheus v0.20.0 go.opentelemetry.io/otel/metric v0.20.0 + go.opentelemetry.io/otel/sdk/export/metric v0.20.0 + go.opentelemetry.io/otel/sdk/metric v0.20.0 ) replace go.opentelemetry.io/otel/bridge/opencensus => ../../bridge/opencensus diff --git a/example/prometheus/main.go b/example/prometheus/main.go index 874dc09a666..6241b92ec8d 100644 --- a/example/prometheus/main.go +++ b/example/prometheus/main.go @@ -26,6 +26,11 @@ import ( "go.opentelemetry.io/otel/exporters/metric/prometheus" "go.opentelemetry.io/otel/metric" "go.opentelemetry.io/otel/metric/global" + export "go.opentelemetry.io/otel/sdk/export/metric" + "go.opentelemetry.io/otel/sdk/metric/aggregator/histogram" + controller "go.opentelemetry.io/otel/sdk/metric/controller/basic" + processor "go.opentelemetry.io/otel/sdk/metric/processor/basic" + selector "go.opentelemetry.io/otel/sdk/metric/selector/simple" ) var ( @@ -33,10 +38,22 @@ var ( ) func initMeter() { - exporter, err := prometheus.InstallNewPipeline(prometheus.Config{}) + config := prometheus.Config{} + c := controller.New( + processor.New( + selector.NewWithHistogramDistribution( + histogram.WithExplicitBoundaries(config.DefaultHistogramBoundaries), + ), + export.CumulativeExportKindSelector(), + processor.WithMemory(true), + ), + ) + exporter, err := prometheus.New(config, c) if err != nil { log.Panicf("failed to initialize prometheus exporter %v", err) } + global.SetMeterProvider(exporter.MeterProvider()) + http.HandleFunc("/", exporter.ServeHTTP) go func() { _ = http.ListenAndServe(":2222", nil) diff --git a/example/zipkin/main.go b/example/zipkin/main.go index fef6c44aca3..720e37652f5 100644 --- a/example/zipkin/main.go +++ b/example/zipkin/main.go @@ -40,7 +40,7 @@ func initTracer(url string) func() { // For demoing purposes, always sample. In a production application, you should // configure the sampler to a trace.ParentBased(trace.TraceIDRatioBased) set at the desired // ratio. - exporter, err := zipkin.NewRawExporter( + exporter, err := zipkin.New( url, zipkin.WithLogger(logger), zipkin.WithSDKOptions(sdktrace.WithSampler(sdktrace.AlwaysSample())), diff --git a/exporters/metric/prometheus/example_test.go b/exporters/metric/prometheus/example_test.go deleted file mode 100644 index e34de6a2c1e..00000000000 --- a/exporters/metric/prometheus/example_test.go +++ /dev/null @@ -1,114 +0,0 @@ -// Copyright The OpenTelemetry Authors -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -package prometheus_test - -import ( - "bytes" - "context" - "fmt" - "io/ioutil" - "net/http" - "net/http/httptest" - - "go.opentelemetry.io/otel/attribute" - "go.opentelemetry.io/otel/exporters/metric/prometheus" - "go.opentelemetry.io/otel/metric" - controller "go.opentelemetry.io/otel/sdk/metric/controller/basic" - "go.opentelemetry.io/otel/sdk/resource" -) - -// This test demonstrates that it is relatively difficult to setup a -// Prometheus export pipeline: -// -// 1. The default boundaries are difficult to pass, should be []float instead of []number.Number -// -// TODO: Address this issue. - -func ExampleNewExportPipeline() { - // Create a resource, with builtin attributes plus R=V. - res, err := resource.New( - context.Background(), - resource.WithAttributes(attribute.String("R", "V")), - ) - if err != nil { - panic(err) - } - - // Create a meter - exporter, err := prometheus.NewExportPipeline( - prometheus.Config{}, - controller.WithResource(res), - ) - if err != nil { - panic(err) - } - meter := exporter.MeterProvider().Meter("example") - ctx := context.Background() - - // Use two instruments - counter := metric.Must(meter).NewInt64Counter( - "a.counter", - metric.WithDescription("Counts things"), - ) - recorder := metric.Must(meter).NewInt64ValueRecorder( - "a.valuerecorder", - metric.WithDescription("Records values"), - ) - - counter.Add(ctx, 100, attribute.String("key", "value")) - recorder.Record(ctx, 100, attribute.String("key", "value")) - - // GET the HTTP endpoint - var input bytes.Buffer - resp := httptest.NewRecorder() - req, err := http.NewRequest("GET", "/", &input) - if err != nil { - panic(err) - } - exporter.ServeHTTP(resp, req) - data, err := ioutil.ReadAll(resp.Result().Body) - if err != nil { - panic(err) - } - fmt.Print(string(data)) - - // Output: - // # HELP a_counter Counts things - // # TYPE a_counter counter - // a_counter{R="V",key="value"} 100 - // # HELP a_valuerecorder Records values - // # TYPE a_valuerecorder histogram - // a_valuerecorder_bucket{R="V",key="value",le="+Inf"} 1 - // a_valuerecorder_sum{R="V",key="value"} 100 - // a_valuerecorder_count{R="V",key="value"} 1 -} - -func ExampleInstallNewPipeline() { - exporter, err := prometheus.InstallNewPipeline(prometheus.Config{}) - if err != nil { - panic(err) - } - - // Expose metrics via HTTP in your handler/muxer - http.Handle("/metrics", exporter) - - // When exiting from your process, call Stop for last collection cycle. - defer func() { - err := exporter.Controller().Stop(context.TODO()) - if err != nil { - panic(err) - } - }() -} diff --git a/exporters/metric/prometheus/prometheus.go b/exporters/metric/prometheus/prometheus.go index 1ab4f181c55..a1b3ec4d1a9 100644 --- a/exporters/metric/prometheus/prometheus.go +++ b/exporters/metric/prometheus/prometheus.go @@ -29,14 +29,10 @@ import ( "go.opentelemetry.io/otel" "go.opentelemetry.io/otel/attribute" "go.opentelemetry.io/otel/metric" - "go.opentelemetry.io/otel/metric/global" "go.opentelemetry.io/otel/metric/number" export "go.opentelemetry.io/otel/sdk/export/metric" "go.opentelemetry.io/otel/sdk/export/metric/aggregation" - "go.opentelemetry.io/otel/sdk/metric/aggregator/histogram" controller "go.opentelemetry.io/otel/sdk/metric/controller/basic" - processor "go.opentelemetry.io/otel/sdk/metric/processor/basic" - selector "go.opentelemetry.io/otel/sdk/metric/selector/simple" ) // Exporter supports Prometheus pulls. It does not implement the @@ -89,9 +85,9 @@ type Config struct { DefaultHistogramBoundaries []float64 } -// NewExporter returns a new Prometheus exporter using the configured -// metric controller. See controller.New(). -func NewExporter(config Config, controller *controller.Controller) (*Exporter, error) { +// New returns a new Prometheus exporter using the configured metric +// controller. See controller.New(). +func New(config Config, controller *controller.Controller) (*Exporter, error) { if config.Registry == nil { config.Registry = prometheus.NewRegistry() } @@ -121,37 +117,6 @@ func NewExporter(config Config, controller *controller.Controller) (*Exporter, e return e, nil } -// NewExportPipeline sets up a complete export pipeline with the recommended setup, -// using the recommended selector and standard processor. See the controller.Options. -func NewExportPipeline(config Config, options ...controller.Option) (*Exporter, error) { - return NewExporter(config, defaultController(config, options...)) -} - -// InstallNewPipeline instantiates a NewExportPipeline and registers it globally. -func InstallNewPipeline(config Config, options ...controller.Option) (*Exporter, error) { - exp, err := NewExportPipeline(config, options...) - if err != nil { - return nil, err - } - global.SetMeterProvider(exp.MeterProvider()) - return exp, nil -} - -// defaultController returns a standard *controller.Controller for use -// with Prometheus. -func defaultController(config Config, options ...controller.Option) *controller.Controller { - return controller.New( - processor.New( - selector.NewWithHistogramDistribution( - histogram.WithExplicitBoundaries(config.DefaultHistogramBoundaries), - ), - export.CumulativeExportKindSelector(), - processor.WithMemory(true), - ), - options..., - ) -} - // MeterProvider returns the MeterProvider of this exporter. func (e *Exporter) MeterProvider() metric.MeterProvider { return e.controller.MeterProvider() diff --git a/exporters/metric/prometheus/prometheus_test.go b/exporters/metric/prometheus/prometheus_test.go index 95f55f7083d..1245cd2582a 100644 --- a/exporters/metric/prometheus/prometheus_test.go +++ b/exporters/metric/prometheus/prometheus_test.go @@ -27,7 +27,11 @@ import ( "go.opentelemetry.io/otel/attribute" "go.opentelemetry.io/otel/exporters/metric/prometheus" "go.opentelemetry.io/otel/metric" + export "go.opentelemetry.io/otel/sdk/export/metric" + "go.opentelemetry.io/otel/sdk/metric/aggregator/histogram" controller "go.opentelemetry.io/otel/sdk/metric/controller/basic" + processor "go.opentelemetry.io/otel/sdk/metric/processor/basic" + selector "go.opentelemetry.io/otel/sdk/metric/selector/simple" "go.opentelemetry.io/otel/sdk/resource" ) @@ -78,8 +82,22 @@ func expectHistogram(name string, values ...string) expectedMetric { } } +func newPipeline(config prometheus.Config, options ...controller.Option) (*prometheus.Exporter, error) { + c := controller.New( + processor.New( + selector.NewWithHistogramDistribution( + histogram.WithExplicitBoundaries(config.DefaultHistogramBoundaries), + ), + export.CumulativeExportKindSelector(), + processor.WithMemory(true), + ), + options..., + ) + return prometheus.New(config, c) +} + func TestPrometheusExporter(t *testing.T) { - exporter, err := prometheus.NewExportPipeline( + exporter, err := newPipeline( prometheus.Config{ DefaultHistogramBoundaries: []float64{-0.5, 1}, }, @@ -155,7 +173,7 @@ func compareExport(t *testing.T, exporter *prometheus.Exporter, expected []expec func TestPrometheusStatefulness(t *testing.T) { // Create a meter - exporter, err := prometheus.NewExportPipeline( + exporter, err := newPipeline( prometheus.Config{}, controller.WithCollectPeriod(0), controller.WithResource(resource.Empty()), diff --git a/exporters/otlp/README.md b/exporters/otlp/README.md index 5c66b93bb67..4895e19b60a 100644 --- a/exporters/otlp/README.md +++ b/exporters/otlp/README.md @@ -12,4 +12,4 @@ The exporter can be installed using standard `go` functionality. go get -u go.opentelemetry.io/otel/exporters/otlp ``` -A new exporter can be created using the `NewExporter` function. +A new exporter can be created using the `New` function. diff --git a/exporters/otlp/example_test.go b/exporters/otlp/example_test.go index 4b4c06297f8..e4f3e998eaf 100644 --- a/exporters/otlp/example_test.go +++ b/exporters/otlp/example_test.go @@ -25,7 +25,7 @@ import ( sdktrace "go.opentelemetry.io/otel/sdk/trace" ) -func ExampleNewExporter() { +func ExampleNew() { ctx := context.Background() // Set different endpoints for the metrics and traces collectors @@ -36,7 +36,7 @@ func ExampleNewExporter() { // Configure traces driver here ) driver := otlp.NewSplitDriver(otlp.WithMetricDriver(metricsDriver), otlp.WithTraceDriver(tracesDriver)) - exporter, err := otlp.NewExporter(ctx, driver) // Configure as needed. + exporter, err := otlp.New(ctx, driver) // Configure as needed. if err != nil { log.Fatalf("failed to create exporter: %v", err) } diff --git a/exporters/otlp/otlp.go b/exporters/otlp/otlp.go index d2ba236456a..f6c3ce72e40 100644 --- a/exporters/otlp/otlp.go +++ b/exporters/otlp/otlp.go @@ -19,15 +19,10 @@ import ( "errors" "sync" - "go.opentelemetry.io/otel" "go.opentelemetry.io/otel/metric" metricsdk "go.opentelemetry.io/otel/sdk/export/metric" "go.opentelemetry.io/otel/sdk/export/metric/aggregation" - "go.opentelemetry.io/otel/sdk/metric/selector/simple" - sdktrace "go.opentelemetry.io/otel/sdk/trace" - "go.opentelemetry.io/otel/sdk/metric/controller/basic" - processor "go.opentelemetry.io/otel/sdk/metric/processor/basic" tracesdk "go.opentelemetry.io/otel/sdk/trace" ) @@ -48,17 +43,17 @@ type Exporter struct { var _ tracesdk.SpanExporter = (*Exporter)(nil) var _ metricsdk.Exporter = (*Exporter)(nil) -// NewExporter constructs a new Exporter and starts it. -func NewExporter(ctx context.Context, driver ProtocolDriver, opts ...ExporterOption) (*Exporter, error) { - exp := NewUnstartedExporter(driver, opts...) +// New constructs a new Exporter and starts it. +func New(ctx context.Context, driver ProtocolDriver, opts ...ExporterOption) (*Exporter, error) { + exp := NewUnstarted(driver, opts...) if err := exp.Start(ctx); err != nil { return nil, err } return exp, nil } -// NewUnstartedExporter constructs a new Exporter and does not start it. -func NewUnstartedExporter(driver ProtocolDriver, opts ...ExporterOption) *Exporter { +// NewUnstarted constructs a new Exporter and does not start it. +func NewUnstarted(driver ProtocolDriver, opts ...ExporterOption) *Exporter { cfg := config{ // Note: the default ExportKindSelector is specified // as Cumulative: @@ -134,46 +129,3 @@ func (e *Exporter) ExportKindFor(desc *metric.Descriptor, kind aggregation.Kind) func (e *Exporter) ExportSpans(ctx context.Context, spans []tracesdk.ReadOnlySpan) error { return e.driver.ExportTraces(ctx, spans) } - -// NewExportPipeline sets up a complete export pipeline -// with the recommended TracerProvider setup. -func NewExportPipeline(ctx context.Context, driver ProtocolDriver, exporterOpts ...ExporterOption) (*Exporter, - *sdktrace.TracerProvider, *basic.Controller, error) { - - exp, err := NewExporter(ctx, driver, exporterOpts...) - if err != nil { - return nil, nil, nil, err - } - - tracerProvider := sdktrace.NewTracerProvider( - sdktrace.WithBatcher(exp), - ) - - cntr := basic.New( - processor.New( - simple.NewWithInexpensiveDistribution(), - exp, - ), - ) - - return exp, tracerProvider, cntr, nil -} - -// InstallNewPipeline instantiates a NewExportPipeline with the -// recommended configuration and registers it globally. -func InstallNewPipeline(ctx context.Context, driver ProtocolDriver, exporterOpts ...ExporterOption) (*Exporter, - *sdktrace.TracerProvider, *basic.Controller, error) { - - exp, tp, cntr, err := NewExportPipeline(ctx, driver, exporterOpts...) - if err != nil { - return nil, nil, nil, err - } - - otel.SetTracerProvider(tp) - err = cntr.Start(ctx) - if err != nil { - return nil, nil, nil, err - } - - return exp, tp, cntr, err -} diff --git a/exporters/otlp/otlp_test.go b/exporters/otlp/otlp_test.go index eee609522b6..801ac1eed25 100644 --- a/exporters/otlp/otlp_test.go +++ b/exporters/otlp/otlp_test.go @@ -24,7 +24,6 @@ import ( "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" - "go.opentelemetry.io/otel" "go.opentelemetry.io/otel/exporters/otlp" "go.opentelemetry.io/otel/exporters/otlp/internal/transform" metricsdk "go.opentelemetry.io/otel/sdk/export/metric" @@ -162,7 +161,7 @@ func (m *stubTransformingProtocolDriver) Reset() { func newExporter(t *testing.T, opts ...otlp.ExporterOption) (*otlp.Exporter, *stubTransformingProtocolDriver) { driver := &stubTransformingProtocolDriver{} - exp, err := otlp.NewExporter(context.Background(), driver, opts...) + exp, err := otlp.New(context.Background(), driver, opts...) require.NoError(t, err) return exp, driver } @@ -171,7 +170,7 @@ func TestExporterShutdownHonorsTimeout(t *testing.T) { ctx, cancel := context.WithTimeout(context.Background(), 1*time.Minute) defer cancel() - e := otlp.NewUnstartedExporter(&stubProtocolDriver{}) + e := otlp.NewUnstarted(&stubProtocolDriver{}) if err := e.Start(ctx); err != nil { t.Fatalf("failed to start exporter: %v", err) } @@ -190,7 +189,7 @@ func TestExporterShutdownHonorsCancel(t *testing.T) { ctx, cancel := context.WithTimeout(context.Background(), 1*time.Minute) defer cancel() - e := otlp.NewUnstartedExporter(&stubProtocolDriver{}) + e := otlp.NewUnstarted(&stubProtocolDriver{}) if err := e.Start(ctx); err != nil { t.Fatalf("failed to start exporter: %v", err) } @@ -209,7 +208,7 @@ func TestExporterShutdownNoError(t *testing.T) { ctx, cancel := context.WithTimeout(context.Background(), 1*time.Minute) defer cancel() - e := otlp.NewUnstartedExporter(&stubProtocolDriver{}) + e := otlp.NewUnstarted(&stubProtocolDriver{}) if err := e.Start(ctx); err != nil { t.Fatalf("failed to start exporter: %v", err) } @@ -221,7 +220,7 @@ func TestExporterShutdownNoError(t *testing.T) { func TestExporterShutdownManyTimes(t *testing.T) { ctx := context.Background() - e, err := otlp.NewExporter(ctx, &stubProtocolDriver{}) + e, err := otlp.New(ctx, &stubProtocolDriver{}) if err != nil { t.Fatalf("failed to start an exporter: %v", err) } @@ -246,43 +245,6 @@ func TestExporterShutdownManyTimes(t *testing.T) { } } -func TestInstallNewPipeline(t *testing.T) { - ctx := context.Background() - _, _, _, err := otlp.InstallNewPipeline(ctx, &stubProtocolDriver{}) - assert.NoError(t, err) - assert.IsType(t, &tracesdk.TracerProvider{}, otel.GetTracerProvider()) -} - -func TestNewExportPipeline(t *testing.T) { - testCases := []struct { - name string - expOpts []otlp.ExporterOption - testSpanSampling bool - }{ - { - name: "simple pipeline", - }, - } - - for _, tc := range testCases { - t.Run(tc.name, func(t *testing.T) { - _, tp, _, err := otlp.NewExportPipeline( - context.Background(), - &stubProtocolDriver{}, - tc.expOpts..., - ) - - assert.NoError(t, err) - assert.NotEqual(t, tp, otel.GetTracerProvider()) - - _, span := tp.Tracer("otlp test").Start(context.Background(), tc.name) - spanCtx := span.SpanContext() - assert.Equal(t, true, spanCtx.IsSampled()) - span.End() - }) - } -} - func TestSplitDriver(t *testing.T) { recordCount := 5 diff --git a/exporters/otlp/otlpgrpc/example_test.go b/exporters/otlp/otlpgrpc/example_test.go index 35f241d728f..a247a684487 100644 --- a/exporters/otlp/otlpgrpc/example_test.go +++ b/exporters/otlp/otlpgrpc/example_test.go @@ -36,7 +36,7 @@ import ( func Example_insecure() { ctx := context.Background() driver := otlpgrpc.NewDriver(otlpgrpc.WithInsecure()) - exp, err := otlp.NewExporter(ctx, driver) + exp, err := otlp.New(ctx, driver) if err != nil { log.Fatalf("Failed to create the collector exporter: %v", err) } @@ -89,7 +89,7 @@ func Example_withTLS() { ctx := context.Background() driver := otlpgrpc.NewDriver(otlpgrpc.WithTLSCredentials(creds)) - exp, err := otlp.NewExporter(ctx, driver) + exp, err := otlp.New(ctx, driver) if err != nil { log.Fatalf("failed to create the collector exporter: %v", err) } @@ -145,7 +145,7 @@ func Example_withDifferentSignalCollectors() { ) driver := otlp.NewSplitDriver(otlp.WithMetricDriver(metricsDriver), otlp.WithTraceDriver(tracesDriver)) ctx := context.Background() - exp, err := otlp.NewExporter(ctx, driver) + exp, err := otlp.New(ctx, driver) if err != nil { log.Fatalf("failed to create the collector exporter: %v", err) } diff --git a/exporters/otlp/otlpgrpc/otlp_integration_test.go b/exporters/otlp/otlpgrpc/otlp_integration_test.go index 25dc243bad2..80fcc5bcc67 100644 --- a/exporters/otlp/otlpgrpc/otlp_integration_test.go +++ b/exporters/otlp/otlpgrpc/otlp_integration_test.go @@ -44,7 +44,7 @@ import ( var roSpans = tracetest.SpanStubs{{Name: "Span 0"}}.Snapshots() -func TestNewExporter_endToEnd(t *testing.T) { +func TestNew_endToEnd(t *testing.T) { tests := []struct { name string additionalOpts []otlpgrpc.Option @@ -88,7 +88,7 @@ func newGRPCExporter(t *testing.T, ctx context.Context, endpoint string, additio opts = append(opts, additionalOpts...) driver := otlpgrpc.NewDriver(opts...) - exp, err := otlp.NewExporter(ctx, driver) + exp, err := otlp.New(ctx, driver) if err != nil { t.Fatalf("failed to create a new collector exporter: %v", err) } @@ -117,7 +117,7 @@ func newExporterEndToEndTest(t *testing.T, additionalOpts []otlpgrpc.Option) { otlptest.RunEndToEndTest(ctx, t, exp, mc, mc) } -func TestNewExporter_invokeStartThenStopManyTimes(t *testing.T) { +func TestNew_invokeStartThenStopManyTimes(t *testing.T) { mc := runMockCollector(t) defer func() { _ = mc.stop() @@ -149,7 +149,7 @@ func TestNewExporter_invokeStartThenStopManyTimes(t *testing.T) { } } -func TestNewExporter_collectorConnectionDiesThenReconnectsWhenInRestMode(t *testing.T) { +func TestNew_collectorConnectionDiesThenReconnectsWhenInRestMode(t *testing.T) { mc := runMockCollector(t) reconnectionPeriod := 20 * time.Millisecond @@ -473,7 +473,7 @@ func newThrottlingError(code codes.Code, duration time.Duration) error { return s.Err() } -func TestNewExporter_collectorConnectionDiesThenReconnects(t *testing.T) { +func TestNew_collectorConnectionDiesThenReconnects(t *testing.T) { mc := runMockCollector(t) reconnectionPeriod := 50 * time.Millisecond @@ -527,7 +527,7 @@ func TestNewExporter_collectorConnectionDiesThenReconnects(t *testing.T) { } // This test takes a long time to run: to skip it, run tests using: -short -func TestNewExporter_collectorOnBadConnection(t *testing.T) { +func TestNew_collectorOnBadConnection(t *testing.T) { if testing.Short() { t.Skipf("Skipping this long running test") } @@ -548,7 +548,7 @@ func TestNewExporter_collectorOnBadConnection(t *testing.T) { _ = exp.Shutdown(ctx) } -func TestNewExporter_withEndpoint(t *testing.T) { +func TestNew_withEndpoint(t *testing.T) { mc := runMockCollector(t) defer func() { _ = mc.stop() @@ -559,7 +559,7 @@ func TestNewExporter_withEndpoint(t *testing.T) { _ = exp.Shutdown(ctx) } -func TestNewExporter_withHeaders(t *testing.T) { +func TestNew_withHeaders(t *testing.T) { mc := runMockCollector(t) defer func() { _ = mc.stop() @@ -579,7 +579,7 @@ func TestNewExporter_withHeaders(t *testing.T) { assert.Equal(t, "value1", headers.Get("header1")[0]) } -func TestNewExporter_WithTimeout(t *testing.T) { +func TestNew_WithTimeout(t *testing.T) { tts := []struct { name string fn func(exp *otlp.Exporter) error @@ -663,7 +663,7 @@ func TestNewExporter_WithTimeout(t *testing.T) { } } -func TestNewExporter_withInvalidSecurityConfiguration(t *testing.T) { +func TestNew_withInvalidSecurityConfiguration(t *testing.T) { mc := runMockCollector(t) defer func() { _ = mc.stop() @@ -671,7 +671,7 @@ func TestNewExporter_withInvalidSecurityConfiguration(t *testing.T) { ctx := context.Background() driver := otlpgrpc.NewDriver(otlpgrpc.WithEndpoint(mc.endpoint)) - exp, err := otlp.NewExporter(ctx, driver) + exp, err := otlp.New(ctx, driver) if err != nil { t.Fatalf("failed to create a new collector exporter: %v", err) } @@ -688,7 +688,7 @@ func TestNewExporter_withInvalidSecurityConfiguration(t *testing.T) { }() } -func TestNewExporter_withMultipleAttributeTypes(t *testing.T) { +func TestNew_withMultipleAttributeTypes(t *testing.T) { mc := runMockCollector(t) defer func() { @@ -903,7 +903,7 @@ func TestMultiConnectionDriver(t *testing.T) { metricsDriver := otlpgrpc.NewDriver(optsMetrics...) driver := otlp.NewSplitDriver(otlp.WithMetricDriver(metricsDriver), otlp.WithTraceDriver(tracesDriver)) ctx := context.Background() - exp, err := otlp.NewExporter(ctx, driver) + exp, err := otlp.New(ctx, driver) if err != nil { t.Fatalf("failed to create a new collector exporter: %v", err) } diff --git a/exporters/otlp/otlphttp/driver_test.go b/exporters/otlp/otlphttp/driver_test.go index 4e2a9defb5c..abd4355e30d 100644 --- a/exporters/otlp/otlphttp/driver_test.go +++ b/exporters/otlp/otlphttp/driver_test.go @@ -132,7 +132,7 @@ func TestEndToEnd(t *testing.T) { allOpts = append(allOpts, tc.opts...) driver := otlphttp.NewDriver(allOpts...) ctx := context.Background() - exporter, err := otlp.NewExporter(ctx, driver) + exporter, err := otlp.New(ctx, driver) if assert.NoError(t, err) { defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -160,7 +160,7 @@ func TestRetry(t *testing.T) { otlphttp.WithMaxAttempts(len(statuses)+1), ) ctx := context.Background() - exporter, err := otlp.NewExporter(ctx, driver) + exporter, err := otlp.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -182,7 +182,7 @@ func TestTimeout(t *testing.T) { otlphttp.WithTimeout(time.Nanosecond), ) ctx := context.Background() - exporter, err := otlp.NewExporter(ctx, driver) + exporter, err := otlp.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -207,7 +207,7 @@ func TestRetryFailed(t *testing.T) { otlphttp.WithMaxAttempts(1), ) ctx := context.Background() - exporter, err := otlp.NewExporter(ctx, driver) + exporter, err := otlp.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -232,7 +232,7 @@ func TestNoRetry(t *testing.T) { otlphttp.WithMaxAttempts(len(statuses)+1), ) ctx := context.Background() - exporter, err := otlp.NewExporter(ctx, driver) + exporter, err := otlp.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -252,7 +252,7 @@ func TestFailedCheckpoint(t *testing.T) { otlphttp.WithInsecure(), ) ctx := context.Background() - exporter, err := otlp.NewExporter(ctx, driver) + exporter, err := otlp.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -271,7 +271,7 @@ func TestEmptyData(t *testing.T) { otlphttp.WithInsecure(), ) ctx := context.Background() - exporter, err := otlp.NewExporter(ctx, driver) + exporter, err := otlp.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -320,7 +320,7 @@ func TestUnreasonableMaxAttempts(t *testing.T) { otlphttp.WithBackoff(time.Millisecond), ) ctx := context.Background() - exporter, err := otlp.NewExporter(ctx, driver) + exporter, err := otlp.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -356,7 +356,7 @@ func TestUnreasonableBackoff(t *testing.T) { ) ctx, cancel := context.WithTimeout(context.Background(), 3*otlphttp.DefaultBackoff) defer cancel() - exporter, err := otlp.NewExporter(ctx, driver) + exporter, err := otlp.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -375,7 +375,7 @@ func TestCancelledContext(t *testing.T) { otlphttp.WithInsecure(), ) ctx, cancel := context.WithCancel(context.Background()) - exporter, err := otlp.NewExporter(ctx, driver) + exporter, err := otlp.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -402,7 +402,7 @@ func TestDeadlineContext(t *testing.T) { otlphttp.WithBackoff(time.Minute), ) ctx := context.Background() - exporter, err := otlp.NewExporter(ctx, driver) + exporter, err := otlp.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -430,7 +430,7 @@ func TestStopWhileExporting(t *testing.T) { otlphttp.WithBackoff(time.Minute), ) ctx := context.Background() - exporter, err := otlp.NewExporter(ctx, driver) + exporter, err := otlp.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) diff --git a/exporters/otlp/otlptrace/exporter.go b/exporters/otlp/otlptrace/exporter.go index 175180eca48..d795db9127d 100644 --- a/exporters/otlp/otlptrace/exporter.go +++ b/exporters/otlp/otlptrace/exporter.go @@ -21,7 +21,6 @@ import ( "go.opentelemetry.io/otel/exporters/otlp/otlptrace/internal/tracetransform" - "go.opentelemetry.io/otel" tracesdk "go.opentelemetry.io/otel/sdk/trace" ) @@ -87,45 +86,18 @@ func (e *Exporter) Shutdown(ctx context.Context) error { var _ tracesdk.SpanExporter = (*Exporter)(nil) -// NewExporter constructs a new Exporter and starts it. -func NewExporter(ctx context.Context, client Client) (*Exporter, error) { - exp := NewUnstartedExporter(client) +// New constructs a new Exporter and starts it. +func New(ctx context.Context, client Client) (*Exporter, error) { + exp := NewUnstarted(client) if err := exp.Start(ctx); err != nil { return nil, err } return exp, nil } -// NewUnstartedExporter constructs a new Exporter and does not start it. -func NewUnstartedExporter(client Client) *Exporter { +// NewUnstarted constructs a new Exporter and does not start it. +func NewUnstarted(client Client) *Exporter { return &Exporter{ client: client, } } - -// NewExportPipeline sets up a complete export pipeline -// with the recommended TracerProvider setup. -func NewExportPipeline(ctx context.Context, client Client) (*Exporter, *tracesdk.TracerProvider, error) { - exp, err := NewExporter(ctx, client) - if err != nil { - return nil, nil, err - } - - tracerProvider := tracesdk.NewTracerProvider( - tracesdk.WithBatcher(exp), - ) - - return exp, tracerProvider, nil -} - -// InstallNewPipeline instantiates a NewExportPipeline with the -// recommended configuration and registers it globally. -func InstallNewPipeline(ctx context.Context, client Client) (*Exporter, *tracesdk.TracerProvider, error) { - exp, tp, err := NewExportPipeline(ctx, client) - if err != nil { - return nil, nil, err - } - - otel.SetTracerProvider(tp) - return exp, tp, err -} diff --git a/exporters/otlp/otlptrace/exporter_test.go b/exporters/otlp/otlptrace/exporter_test.go deleted file mode 100644 index 441c4ade4b4..00000000000 --- a/exporters/otlp/otlptrace/exporter_test.go +++ /dev/null @@ -1,66 +0,0 @@ -// Copyright The OpenTelemetry Authors -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -package otlptrace_test - -import ( - "context" - "testing" - - "go.opentelemetry.io/otel/exporters/otlp/otlptrace" - - "github.com/stretchr/testify/assert" - - "go.opentelemetry.io/otel" - tracesdk "go.opentelemetry.io/otel/sdk/trace" - tracepb "go.opentelemetry.io/proto/otlp/trace/v1" -) - -type noopClient struct { -} - -var _ otlptrace.Client = (*noopClient)(nil) - -func (m *noopClient) Start(_ context.Context) error { - return nil -} - -func (m *noopClient) Stop(ctx context.Context) error { - select { - case <-ctx.Done(): - return ctx.Err() - default: - } - return nil -} - -func (m *noopClient) UploadTraces(_ context.Context, _ []*tracepb.ResourceSpans) error { - return nil -} - -func (m *noopClient) Reset() { -} - -func TestInstallNewPipeline(t *testing.T) { - ctx := context.Background() - _, _, err := otlptrace.InstallNewPipeline(ctx, &noopClient{}) - assert.NoError(t, err) - assert.IsType(t, &tracesdk.TracerProvider{}, otel.GetTracerProvider()) -} - -func TestNewExportPipeline(t *testing.T) { - _, tp, err := otlptrace.NewExportPipeline(context.Background(), &noopClient{}) - assert.NoError(t, err) - assert.NotEqual(t, tp, otel.GetTracerProvider()) -} diff --git a/exporters/otlp/otlptrace/internal/otlptracetest/client.go b/exporters/otlp/otlptrace/internal/otlptracetest/client.go index 520e8aaad4d..70edfa0d9cb 100644 --- a/exporters/otlp/otlptrace/internal/otlptracetest/client.go +++ b/exporters/otlp/otlptrace/internal/otlptracetest/client.go @@ -46,7 +46,7 @@ func initializeExporter(t *testing.T, client otlptrace.Client) *otlptrace.Export ctx, cancel := context.WithTimeout(context.Background(), 1*time.Minute) defer cancel() - e, err := otlptrace.NewExporter(ctx, client) + e, err := otlptrace.New(ctx, client) if err != nil { t.Fatalf("failed to create exporter") } diff --git a/exporters/otlp/otlptrace/otlptracegrpc/client_test.go b/exporters/otlp/otlptrace/otlptracegrpc/client_test.go index fe5c101140c..3c53c1637a9 100644 --- a/exporters/otlp/otlptrace/otlptracegrpc/client_test.go +++ b/exporters/otlp/otlptrace/otlptracegrpc/client_test.go @@ -44,7 +44,7 @@ import ( var roSpans = tracetest.SpanStubs{{Name: "Span 0"}}.Snapshots() -func TestNewExporter_endToEnd(t *testing.T) { +func TestNew_endToEnd(t *testing.T) { tests := []struct { name string additionalOpts []otlptracegrpc.Option @@ -88,7 +88,7 @@ func newGRPCExporter(t *testing.T, ctx context.Context, endpoint string, additio opts = append(opts, additionalOpts...) client := otlptracegrpc.NewClient(opts...) - exp, err := otlptrace.NewExporter(ctx, client) + exp, err := otlptrace.New(ctx, client) if err != nil { t.Fatalf("failed to create a new collector exporter: %v", err) } @@ -133,7 +133,7 @@ func TestExporterShutdown(t *testing.T) { }) } -func TestNewExporter_invokeStartThenStopManyTimes(t *testing.T) { +func TestNew_invokeStartThenStopManyTimes(t *testing.T) { mc := runMockCollector(t) defer func() { _ = mc.stop() @@ -165,7 +165,7 @@ func TestNewExporter_invokeStartThenStopManyTimes(t *testing.T) { } } -func TestNewExporter_collectorConnectionDiesThenReconnectsWhenInRestMode(t *testing.T) { +func TestNew_collectorConnectionDiesThenReconnectsWhenInRestMode(t *testing.T) { mc := runMockCollector(t) reconnectionPeriod := 20 * time.Millisecond @@ -489,7 +489,7 @@ func newThrottlingError(code codes.Code, duration time.Duration) error { return s.Err() } -func TestNewExporter_collectorConnectionDiesThenReconnects(t *testing.T) { +func TestNew_collectorConnectionDiesThenReconnects(t *testing.T) { mc := runMockCollector(t) reconnectionPeriod := 50 * time.Millisecond @@ -543,7 +543,7 @@ func TestNewExporter_collectorConnectionDiesThenReconnects(t *testing.T) { } // This test takes a long time to run: to skip it, run tests using: -short -func TestNewExporter_collectorOnBadConnection(t *testing.T) { +func TestNew_collectorOnBadConnection(t *testing.T) { if testing.Short() { t.Skipf("Skipping this long running test") } @@ -564,7 +564,7 @@ func TestNewExporter_collectorOnBadConnection(t *testing.T) { _ = exp.Shutdown(ctx) } -func TestNewExporter_withEndpoint(t *testing.T) { +func TestNew_withEndpoint(t *testing.T) { mc := runMockCollector(t) defer func() { _ = mc.stop() @@ -575,7 +575,7 @@ func TestNewExporter_withEndpoint(t *testing.T) { _ = exp.Shutdown(ctx) } -func TestNewExporter_withHeaders(t *testing.T) { +func TestNew_withHeaders(t *testing.T) { mc := runMockCollector(t) defer func() { _ = mc.stop() @@ -595,7 +595,7 @@ func TestNewExporter_withHeaders(t *testing.T) { assert.Equal(t, "value1", headers.Get("header1")[0]) } -func TestNewExporter_WithTimeout(t *testing.T) { +func TestNew_WithTimeout(t *testing.T) { tts := []struct { name string fn func(exp *otlptrace.Exporter) error @@ -658,7 +658,7 @@ func TestNewExporter_WithTimeout(t *testing.T) { } } -func TestNewExporter_withInvalidSecurityConfiguration(t *testing.T) { +func TestNew_withInvalidSecurityConfiguration(t *testing.T) { mc := runMockCollector(t) defer func() { _ = mc.stop() @@ -666,7 +666,7 @@ func TestNewExporter_withInvalidSecurityConfiguration(t *testing.T) { ctx := context.Background() driver := otlptracegrpc.NewClient(otlptracegrpc.WithEndpoint(mc.endpoint)) - exp, err := otlptrace.NewExporter(ctx, driver) + exp, err := otlptrace.New(ctx, driver) if err != nil { t.Fatalf("failed to create a new collector exporter: %v", err) } @@ -683,7 +683,7 @@ func TestNewExporter_withInvalidSecurityConfiguration(t *testing.T) { }() } -func TestNewExporter_withMultipleAttributeTypes(t *testing.T) { +func TestNew_withMultipleAttributeTypes(t *testing.T) { mc := runMockCollector(t) defer func() { diff --git a/exporters/otlp/otlptrace/otlptracegrpc/exporter.go b/exporters/otlp/otlptrace/otlptracegrpc/exporter.go index d2c85b06080..89af41002f7 100644 --- a/exporters/otlp/otlptrace/otlptracegrpc/exporter.go +++ b/exporters/otlp/otlptrace/otlptracegrpc/exporter.go @@ -18,27 +18,14 @@ import ( "context" "go.opentelemetry.io/otel/exporters/otlp/otlptrace" - tracesdk "go.opentelemetry.io/otel/sdk/trace" ) -// NewExporter constructs a new Exporter and starts it. -func NewExporter(ctx context.Context, opts ...Option) (*otlptrace.Exporter, error) { - return otlptrace.NewExporter(ctx, NewClient(opts...)) +// New constructs a new Exporter and starts it. +func New(ctx context.Context, opts ...Option) (*otlptrace.Exporter, error) { + return otlptrace.New(ctx, NewClient(opts...)) } -// NewUnstartedExporter constructs a new Exporter and does not start it. -func NewUnstartedExporter(opts ...Option) *otlptrace.Exporter { - return otlptrace.NewUnstartedExporter(NewClient(opts...)) -} - -// NewExportPipeline sets up a complete export pipeline -// with the recommended TracerProvider setup. -func NewExportPipeline(ctx context.Context, opts ...Option) (*otlptrace.Exporter, *tracesdk.TracerProvider, error) { - return otlptrace.NewExportPipeline(ctx, NewClient(opts...)) -} - -// InstallNewPipeline instantiates a NewExportPipeline with the -// recommended configuration and registers it globally. -func InstallNewPipeline(ctx context.Context, opts ...Option) (*otlptrace.Exporter, *tracesdk.TracerProvider, error) { - return otlptrace.InstallNewPipeline(ctx, NewClient(opts...)) +// NewUnstarted constructs a new Exporter and does not start it. +func NewUnstarted(opts ...Option) *otlptrace.Exporter { + return otlptrace.NewUnstarted(NewClient(opts...)) } diff --git a/exporters/otlp/otlptrace/otlptracehttp/client_test.go b/exporters/otlp/otlptrace/otlptracehttp/client_test.go index 33340a4e668..2b4ae640691 100644 --- a/exporters/otlp/otlptrace/otlptracehttp/client_test.go +++ b/exporters/otlp/otlptrace/otlptracehttp/client_test.go @@ -111,7 +111,7 @@ func TestEndToEnd(t *testing.T) { allOpts = append(allOpts, tc.opts...) client := otlptracehttp.NewClient(allOpts...) ctx := context.Background() - exporter, err := otlptrace.NewExporter(ctx, client) + exporter, err := otlptrace.New(ctx, client) if assert.NoError(t, err) { defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -154,7 +154,7 @@ func TestRetry(t *testing.T) { otlptracehttp.WithMaxAttempts(len(statuses)+1), ) ctx := context.Background() - exporter, err := otlptrace.NewExporter(ctx, client) + exporter, err := otlptrace.New(ctx, client) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -176,7 +176,7 @@ func TestTimeout(t *testing.T) { otlptracehttp.WithTimeout(50*time.Millisecond), ) ctx := context.Background() - exporter, err := otlptrace.NewExporter(ctx, client) + exporter, err := otlptrace.New(ctx, client) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -201,7 +201,7 @@ func TestRetryFailed(t *testing.T) { otlptracehttp.WithMaxAttempts(1), ) ctx := context.Background() - exporter, err := otlptrace.NewExporter(ctx, driver) + exporter, err := otlptrace.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -226,7 +226,7 @@ func TestNoRetry(t *testing.T) { otlptracehttp.WithMaxAttempts(len(statuses)+1), ) ctx := context.Background() - exporter, err := otlptrace.NewExporter(ctx, driver) + exporter, err := otlptrace.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -246,7 +246,7 @@ func TestEmptyData(t *testing.T) { otlptracehttp.WithInsecure(), ) ctx := context.Background() - exporter, err := otlptrace.NewExporter(ctx, driver) + exporter, err := otlptrace.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -293,7 +293,7 @@ func TestUnreasonableMaxAttempts(t *testing.T) { otlptracehttp.WithBackoff(time.Millisecond), ) ctx := context.Background() - exporter, err := otlptrace.NewExporter(ctx, driver) + exporter, err := otlptrace.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) @@ -329,7 +329,7 @@ func TestUnreasonableBackoff(t *testing.T) { ) ctx, cancel := context.WithTimeout(context.Background(), 3*(300*time.Millisecond)) defer cancel() - exporter, err := otlptrace.NewExporter(ctx, driver) + exporter, err := otlptrace.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(context.Background())) @@ -348,7 +348,7 @@ func TestCancelledContext(t *testing.T) { otlptracehttp.WithInsecure(), ) ctx, cancel := context.WithCancel(context.Background()) - exporter, err := otlptrace.NewExporter(ctx, driver) + exporter, err := otlptrace.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(context.Background())) @@ -375,7 +375,7 @@ func TestDeadlineContext(t *testing.T) { otlptracehttp.WithBackoff(time.Minute), ) ctx := context.Background() - exporter, err := otlptrace.NewExporter(ctx, driver) + exporter, err := otlptrace.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(context.Background())) @@ -403,7 +403,7 @@ func TestStopWhileExporting(t *testing.T) { otlptracehttp.WithBackoff(time.Minute), ) ctx := context.Background() - exporter, err := otlptrace.NewExporter(ctx, driver) + exporter, err := otlptrace.New(ctx, driver) require.NoError(t, err) defer func() { assert.NoError(t, exporter.Shutdown(ctx)) diff --git a/exporters/otlp/otlptrace/otlptracehttp/exporter.go b/exporters/otlp/otlptrace/otlptracehttp/exporter.go index 833935ac439..23b8642040d 100644 --- a/exporters/otlp/otlptrace/otlptracehttp/exporter.go +++ b/exporters/otlp/otlptrace/otlptracehttp/exporter.go @@ -18,27 +18,14 @@ import ( "context" "go.opentelemetry.io/otel/exporters/otlp/otlptrace" - tracesdk "go.opentelemetry.io/otel/sdk/trace" ) -// NewExporter constructs a new Exporter and starts it. -func NewExporter(ctx context.Context, opts ...Option) (*otlptrace.Exporter, error) { - return otlptrace.NewExporter(ctx, NewClient(opts...)) +// New constructs a new Exporter and starts it. +func New(ctx context.Context, opts ...Option) (*otlptrace.Exporter, error) { + return otlptrace.New(ctx, NewClient(opts...)) } -// NewUnstartedExporter constructs a new Exporter and does not start it. -func NewUnstartedExporter(opts ...Option) *otlptrace.Exporter { - return otlptrace.NewUnstartedExporter(NewClient(opts...)) -} - -// NewExportPipeline sets up a complete export pipeline -// with the recommended TracerProvider setup. -func NewExportPipeline(ctx context.Context, opts ...Option) (*otlptrace.Exporter, *tracesdk.TracerProvider, error) { - return otlptrace.NewExportPipeline(ctx, NewClient(opts...)) -} - -// InstallNewPipeline instantiates a NewExportPipeline with the -// recommended configuration and registers it globally. -func InstallNewPipeline(ctx context.Context, opts ...Option) (*otlptrace.Exporter, *tracesdk.TracerProvider, error) { - return otlptrace.InstallNewPipeline(ctx, NewClient(opts...)) +// NewUnstarted constructs a new Exporter and does not start it. +func NewUnstarted(opts ...Option) *otlptrace.Exporter { + return otlptrace.NewUnstarted(NewClient(opts...)) } diff --git a/exporters/otlp/otlptrace/otlptracehttp/go.mod b/exporters/otlp/otlptrace/otlptracehttp/go.mod index c5a1c4a5e30..5073e83bf39 100644 --- a/exporters/otlp/otlptrace/otlptracehttp/go.mod +++ b/exporters/otlp/otlptrace/otlptracehttp/go.mod @@ -6,7 +6,6 @@ require ( github.com/stretchr/testify v1.7.0 go.opentelemetry.io/otel v0.20.0 go.opentelemetry.io/otel/exporters/otlp/otlptrace v0.0.0-00010101000000-000000000000 - go.opentelemetry.io/otel/sdk v0.20.0 go.opentelemetry.io/proto/otlp v0.9.0 google.golang.org/protobuf v1.26.0 ) diff --git a/exporters/stdout/example_test.go b/exporters/stdout/example_test.go index f38a572bb82..c9151d3162b 100644 --- a/exporters/stdout/example_test.go +++ b/exporters/stdout/example_test.go @@ -23,6 +23,12 @@ import ( "go.opentelemetry.io/otel/exporters/stdout" "go.opentelemetry.io/otel/metric" "go.opentelemetry.io/otel/metric/global" + controller "go.opentelemetry.io/otel/sdk/metric/controller/basic" + processor "go.opentelemetry.io/otel/sdk/metric/processor/basic" + "go.opentelemetry.io/otel/sdk/metric/selector/simple" + "go.opentelemetry.io/otel/sdk/resource" + sdktrace "go.opentelemetry.io/otel/sdk/trace" + "go.opentelemetry.io/otel/semconv" "go.opentelemetry.io/otel/trace" ) @@ -77,23 +83,54 @@ func multiply(ctx context.Context, x, y int64) int64 { return x * y } -func Example() { - exportOpts := []stdout.Option{ - stdout.WithPrettyPrint(), - } - // Registers both a trace and meter Provider globally. - tracerProvider, pusher, err := stdout.InstallNewPipeline(exportOpts, nil) +func Resource() *resource.Resource { + return resource.NewWithAttributes( + semconv.SchemaURL, + semconv.ServiceNameKey.String("stdout-example"), + semconv.ServiceVersionKey.String("0.0.1"), + ) +} + +func InstallExportPipeline(ctx context.Context) func() { + exporter, err := stdout.New(stdout.WithPrettyPrint()) if err != nil { - log.Fatal("Could not initialize stdout exporter:", err) + log.Fatalf("creating stdout exporter: %v", err) } - ctx := context.Background() - - log.Println("the answer is", add(ctx, multiply(ctx, multiply(ctx, 2, 2), 10), 2)) - if err := pusher.Stop(ctx); err != nil { - log.Fatal("Could not stop stdout exporter:", err) + tracerProvider := sdktrace.NewTracerProvider( + sdktrace.WithBatcher(exporter), + sdktrace.WithResource(Resource()), + ) + otel.SetTracerProvider(tracerProvider) + + pusher := controller.New( + processor.New( + simple.NewWithInexpensiveDistribution(), + exporter, + ), + controller.WithExporter(exporter), + ) + if err = pusher.Start(ctx); err != nil { + log.Fatalf("starting push controller: %v", err) } - if err := tracerProvider.Shutdown(ctx); err != nil { - log.Fatal("Could not stop stdout tracer:", err) + global.SetMeterProvider(pusher.MeterProvider()) + + return func() { + if err := pusher.Stop(ctx); err != nil { + log.Fatalf("stopping push controller: %v", err) + } + if err := tracerProvider.Shutdown(ctx); err != nil { + log.Fatalf("stopping tracer provider: %v", err) + } } } + +func Example() { + ctx := context.Background() + + // Registers both a tracer and meter Provider globally. + cleanup := InstallExportPipeline(ctx) + defer cleanup() + + log.Println("the answer is", add(ctx, multiply(ctx, multiply(ctx, 2, 2), 10), 2)) +} diff --git a/exporters/stdout/exporter.go b/exporters/stdout/exporter.go index 443fc1806b9..b47106d86db 100644 --- a/exporters/stdout/exporter.go +++ b/exporters/stdout/exporter.go @@ -15,14 +15,7 @@ package stdout // import "go.opentelemetry.io/otel/exporters/stdout" import ( - "context" - - "go.opentelemetry.io/otel" - "go.opentelemetry.io/otel/metric/global" "go.opentelemetry.io/otel/sdk/export/metric" - controller "go.opentelemetry.io/otel/sdk/metric/controller/basic" - processor "go.opentelemetry.io/otel/sdk/metric/processor/basic" - "go.opentelemetry.io/otel/sdk/metric/selector/simple" sdktrace "go.opentelemetry.io/otel/sdk/trace" ) @@ -36,8 +29,8 @@ var ( _ sdktrace.SpanExporter = &Exporter{} ) -// NewExporter creates an Exporter with the passed options. -func NewExporter(options ...Option) (*Exporter, error) { +// New creates an Exporter with the passed options. +func New(options ...Option) (*Exporter, error) { cfg, err := newConfig(options...) if err != nil { return nil, err @@ -47,50 +40,3 @@ func NewExporter(options ...Option) (*Exporter, error) { metricExporter: metricExporter{cfg}, }, nil } - -// NewExportPipeline creates a complete export pipeline with the default -// selectors, processors, and trace registration. It is the responsibility -// of the caller to stop the returned tracer provider and push Controller. -func NewExportPipeline(exportOpts []Option, pushOpts []controller.Option) (*sdktrace.TracerProvider, *controller.Controller, error) { - exporter, err := NewExporter(exportOpts...) - if err != nil { - return nil, nil, err - } - - tp := sdktrace.NewTracerProvider(sdktrace.WithBatcher(exporter)) - pusher := controller.New( - processor.New( - simple.NewWithInexpensiveDistribution(), - exporter, - ), - append( - pushOpts, - controller.WithExporter(exporter), - )..., - ) - err = pusher.Start(context.Background()) - - return tp, pusher, err -} - -// InstallNewPipeline creates a complete export pipelines with defaults and -// registers it globally. It is the responsibility of the caller to stop the -// returned tracer provider and push Controller. -// -// Typically this is called as: -// -// pipeline, err := stdout.InstallNewPipeline(stdout.Config{...}) -// if err != nil { -// ... -// } -// defer pipeline.Stop() -// ... Done -func InstallNewPipeline(exportOpts []Option, pushOpts []controller.Option) (*sdktrace.TracerProvider, *controller.Controller, error) { - tracerProvider, controller, err := NewExportPipeline(exportOpts, pushOpts) - if err != nil { - return tracerProvider, controller, err - } - otel.SetTracerProvider(tracerProvider) - global.SetMeterProvider(controller.MeterProvider()) - return tracerProvider, controller, err -} diff --git a/exporters/stdout/metric_test.go b/exporters/stdout/metric_test.go index 7e5318443ad..c385f4f27fc 100644 --- a/exporters/stdout/metric_test.go +++ b/exporters/stdout/metric_test.go @@ -52,7 +52,7 @@ func newFixture(t *testing.T, opts ...stdout.Option) testFixture { buf := &bytes.Buffer{} opts = append(opts, stdout.WithWriter(buf)) opts = append(opts, stdout.WithoutTimestamps()) - exp, err := stdout.NewExporter(opts...) + exp, err := stdout.New(opts...) if err != nil { t.Fatal("Error building fixture: ", err) } @@ -77,7 +77,7 @@ func (fix testFixture) Export(checkpointSet export.CheckpointSet) { func TestStdoutTimestamp(t *testing.T) { var buf bytes.Buffer - exporter, err := stdout.NewExporter( + exporter, err := stdout.New( stdout.WithWriter(&buf), ) if err != nil { diff --git a/exporters/stdout/trace_test.go b/exporters/stdout/trace_test.go index 748bd6213e6..4c3579e7daf 100644 --- a/exporters/stdout/trace_test.go +++ b/exporters/stdout/trace_test.go @@ -37,7 +37,7 @@ import ( func TestExporter_ExportSpan(t *testing.T) { // write to buffer for testing var b bytes.Buffer - ex, err := stdout.NewExporter(stdout.WithWriter(&b), stdout.WithPrettyPrint()) + ex, err := stdout.New(stdout.WithWriter(&b), stdout.WithPrettyPrint()) if err != nil { t.Errorf("Error constructing stdout exporter %s", err) } @@ -183,7 +183,7 @@ func TestExporterShutdownHonorsTimeout(t *testing.T) { ctx, cancel := context.WithTimeout(context.Background(), 1*time.Minute) defer cancel() - e, err := stdout.NewExporter() + e, err := stdout.New() if err != nil { t.Fatalf("failed to create exporter: %v", err) } @@ -202,7 +202,7 @@ func TestExporterShutdownHonorsCancel(t *testing.T) { ctx, cancel := context.WithTimeout(context.Background(), 1*time.Minute) defer cancel() - e, err := stdout.NewExporter() + e, err := stdout.New() if err != nil { t.Fatalf("failed to create exporter: %v", err) } @@ -217,7 +217,7 @@ func TestExporterShutdownHonorsCancel(t *testing.T) { } func TestExporterShutdownNoError(t *testing.T) { - e, err := stdout.NewExporter() + e, err := stdout.New() if err != nil { t.Fatalf("failed to create exporter: %v", err) } diff --git a/exporters/trace/jaeger/agent_test.go b/exporters/trace/jaeger/agent_test.go index 8b52e974b8c..62de111dae5 100644 --- a/exporters/trace/jaeger/agent_test.go +++ b/exporters/trace/jaeger/agent_test.go @@ -121,7 +121,7 @@ func TestJaegerAgentUDPLimitBatching(t *testing.T) { n := 1500 s := make(tracetest.SpanStubs, n).Snapshots() - exp, err := NewRawExporter( + exp, err := New( WithAgentEndpoint(WithAgentHost(host), WithAgentPort(port)), ) require.NoError(t, err) @@ -153,7 +153,7 @@ func TestSpanExceedsMaxPacketLimit(t *testing.T) { largeSpans := tracetest.SpanStubs{generateALargeSpan(), {}}.Snapshots() normalSpans := tracetest.SpanStubs{{}, {}}.Snapshots() - exp, err := NewRawExporter( + exp, err := New( WithAgentEndpoint(WithAgentHost(host), WithAgentPort(port), WithMaxPacketSize(maxSize+1)), ) require.NoError(t, err) @@ -177,7 +177,7 @@ func TestEmitBatchWithMultipleErrors(t *testing.T) { largeSpans := tracetest.SpanStubs{span, span}.Snapshots() // make max packet size smaller than span maxSize := len(span.Name) - exp, err := NewRawExporter( + exp, err := New( WithAgentEndpoint(WithAgentHost(host), WithAgentPort(port), WithMaxPacketSize(maxSize)), ) require.NoError(t, err) diff --git a/exporters/trace/jaeger/env_test.go b/exporters/trace/jaeger/env_test.go index 182d30ec928..0a9ee1900ba 100644 --- a/exporters/trace/jaeger/env_test.go +++ b/exporters/trace/jaeger/env_test.go @@ -32,7 +32,7 @@ func TestNewRawExporterWithDefault(t *testing.T) { ) // Create Jaeger Exporter with default values - exp, err := NewRawExporter( + exp, err := New( WithCollectorEndpoint(), ) @@ -63,7 +63,7 @@ func TestNewRawExporterWithEnv(t *testing.T) { }() // Create Jaeger Exporter with environment variables - exp, err := NewRawExporter( + exp, err := New( WithCollectorEndpoint(), ) @@ -95,7 +95,7 @@ func TestNewRawExporterWithPassedOption(t *testing.T) { }() // Create Jaeger Exporter with passed endpoint option, should be used over envEndpoint - exp, err := NewRawExporter( + exp, err := New( WithCollectorEndpoint(WithEndpoint(optionEndpoint)), ) diff --git a/exporters/trace/jaeger/jaeger.go b/exporters/trace/jaeger/jaeger.go index cb24243002f..70485f11651 100644 --- a/exporters/trace/jaeger/jaeger.go +++ b/exporters/trace/jaeger/jaeger.go @@ -21,7 +21,6 @@ import ( "fmt" "sync" - "go.opentelemetry.io/otel" "go.opentelemetry.io/otel/attribute" "go.opentelemetry.io/otel/codes" gen "go.opentelemetry.io/otel/exporters/trace/jaeger/internal/gen-go/jaeger" @@ -42,9 +41,9 @@ const ( keyEventName = "event" ) -// NewRawExporter returns an OTel Exporter implementation that exports the -// collected spans to Jaeger. -func NewRawExporter(endpointOption EndpointOption) (*Exporter, error) { +// New returns an OTel Exporter implementation that exports the collected +// spans to Jaeger. +func New(endpointOption EndpointOption) (*Exporter, error) { uploader, err := endpointOption.newBatchUploader() if err != nil { return nil, err @@ -69,30 +68,6 @@ func NewRawExporter(endpointOption EndpointOption) (*Exporter, error) { return e, nil } -// NewExportPipeline sets up a complete export pipeline -// with the recommended setup for trace provider -func NewExportPipeline(endpointOption EndpointOption) (*sdktrace.TracerProvider, error) { - exporter, err := NewRawExporter(endpointOption) - if err != nil { - return nil, err - } - - tp := sdktrace.NewTracerProvider(sdktrace.WithBatcher(exporter)) - return tp, nil -} - -// InstallNewPipeline instantiates a NewExportPipeline with the -// recommended configuration and registers it globally. -func InstallNewPipeline(endpointOption EndpointOption) (*sdktrace.TracerProvider, error) { - tp, err := NewExportPipeline(endpointOption) - if err != nil { - return tp, err - } - - otel.SetTracerProvider(tp) - return tp, nil -} - // Exporter exports OpenTelemetry spans to a Jaeger agent or collector. type Exporter struct { uploader batchUploader diff --git a/exporters/trace/jaeger/jaeger_benchmark_test.go b/exporters/trace/jaeger/jaeger_benchmark_test.go index 92a11d35941..ab96ac8c9ed 100644 --- a/exporters/trace/jaeger/jaeger_benchmark_test.go +++ b/exporters/trace/jaeger/jaeger_benchmark_test.go @@ -72,7 +72,7 @@ func spans(n int) []tracesdk.ReadOnlySpan { func benchmarkExportSpans(b *testing.B, o EndpointOption, i int) { ctx := context.Background() s := spans(i) - exp, err := NewRawExporter(o) + exp, err := New(o) if err != nil { b.Fatal(err) } diff --git a/exporters/trace/jaeger/jaeger_test.go b/exporters/trace/jaeger/jaeger_test.go index 3eeb48ad0ee..948c90f8860 100644 --- a/exporters/trace/jaeger/jaeger_test.go +++ b/exporters/trace/jaeger/jaeger_test.go @@ -17,7 +17,6 @@ package jaeger import ( "context" "encoding/binary" - "errors" "fmt" "os" "sort" @@ -28,7 +27,6 @@ import ( "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" - "go.opentelemetry.io/otel" "go.opentelemetry.io/otel/attribute" "go.opentelemetry.io/otel/codes" gen "go.opentelemetry.io/otel/exporters/trace/jaeger/internal/gen-go/jaeger" @@ -41,52 +39,6 @@ import ( "go.opentelemetry.io/otel/trace" ) -const ( - collectorEndpoint = "http://localhost:14268/api/traces" -) - -func TestInstallNewPipeline(t *testing.T) { - tp, err := InstallNewPipeline(WithCollectorEndpoint(WithEndpoint(collectorEndpoint))) - require.NoError(t, err) - // Ensure InstallNewPipeline sets the global TracerProvider. By default - // the global tracer provider will be a NoOp implementation, this checks - // if that has been overwritten. - assert.IsType(t, tp, otel.GetTracerProvider()) -} - -func TestNewExportPipelinePassthroughError(t *testing.T) { - for _, testcase := range []struct { - name string - failing bool - epo EndpointOption - }{ - { - name: "failing underlying NewRawExporter", - failing: true, - epo: endpointOptionFunc(func() (batchUploader, error) { - return nil, errors.New("error") - }), - }, - { - name: "with default agent endpoint", - epo: WithAgentEndpoint(), - }, - { - name: "with collector endpoint", - epo: WithCollectorEndpoint(WithEndpoint(collectorEndpoint)), - }, - } { - t.Run(testcase.name, func(t *testing.T) { - _, err := NewExportPipeline(testcase.epo) - if testcase.failing { - require.Error(t, err) - return - } - require.NoError(t, err) - }) - } -} - func TestNewRawExporter(t *testing.T) { testCases := []struct { name string @@ -104,7 +56,7 @@ func TestNewRawExporter(t *testing.T) { for _, tc := range testCases { t.Run(tc.name, func(t *testing.T) { - _, err := NewRawExporter(tc.endpoint) + _, err := New(tc.endpoint) assert.NoError(t, err) }) } @@ -120,7 +72,7 @@ func TestNewRawExporterUseEnvVarIfOptionUnset(t *testing.T) { // If the user sets the environment variable OTEL_EXPORTER_JAEGER_ENDPOINT, endpoint will always get a value. require.NoError(t, os.Unsetenv(envEndpoint)) - _, err := NewRawExporter( + _, err := New( WithCollectorEndpoint(), ) @@ -162,7 +114,7 @@ func TestExporterExportSpan(t *testing.T) { ) testCollector := &testCollectorEndpoint{} - exp, err := NewRawExporter(withTestCollectorEndpointInjected(testCollector)) + exp, err := New(withTestCollectorEndpointInjected(testCollector)) require.NoError(t, err) tp := sdktrace.NewTracerProvider( sdktrace.WithBatcher(exp), @@ -471,7 +423,7 @@ func TestExporterShutdownHonorsCancel(t *testing.T) { ctx, cancel := context.WithCancel(context.Background()) cancel() - e, err := NewRawExporter(withTestCollectorEndpoint()) + e, err := New(withTestCollectorEndpoint()) require.NoError(t, err) assert.EqualError(t, e.Shutdown(ctx), context.Canceled.Error()) } @@ -480,21 +432,21 @@ func TestExporterShutdownHonorsTimeout(t *testing.T) { ctx, cancel := context.WithTimeout(context.Background(), 1*time.Nanosecond) <-ctx.Done() - e, err := NewRawExporter(withTestCollectorEndpoint()) + e, err := New(withTestCollectorEndpoint()) require.NoError(t, err) assert.EqualError(t, e.Shutdown(ctx), context.DeadlineExceeded.Error()) cancel() } func TestErrorOnExportShutdownExporter(t *testing.T) { - e, err := NewRawExporter(withTestCollectorEndpoint()) + e, err := New(withTestCollectorEndpoint()) require.NoError(t, err) assert.NoError(t, e.Shutdown(context.Background())) assert.NoError(t, e.ExportSpans(context.Background(), nil)) } func TestExporterExportSpansHonorsCancel(t *testing.T) { - e, err := NewRawExporter(withTestCollectorEndpoint()) + e, err := New(withTestCollectorEndpoint()) require.NoError(t, err) now := time.Now() ss := tracetest.SpanStubs{ @@ -524,7 +476,7 @@ func TestExporterExportSpansHonorsCancel(t *testing.T) { } func TestExporterExportSpansHonorsTimeout(t *testing.T) { - e, err := NewRawExporter(withTestCollectorEndpoint()) + e, err := New(withTestCollectorEndpoint()) require.NoError(t, err) now := time.Now() ss := tracetest.SpanStubs{ diff --git a/exporters/trace/zipkin/zipkin.go b/exporters/trace/zipkin/zipkin.go index ee926912307..8c6c3a52ed9 100644 --- a/exporters/trace/zipkin/zipkin.go +++ b/exporters/trace/zipkin/zipkin.go @@ -27,7 +27,6 @@ import ( "net/url" "sync" - "go.opentelemetry.io/otel" sdktrace "go.opentelemetry.io/otel/sdk/trace" ) @@ -85,8 +84,8 @@ func WithSDKOptions(tpOpts ...sdktrace.TracerProviderOption) Option { }) } -// NewRawExporter creates a new Zipkin exporter. -func NewRawExporter(collectorURL string, opts ...Option) (*Exporter, error) { +// New creates a new Zipkin exporter. +func New(collectorURL string, opts ...Option) (*Exporter, error) { if collectorURL == "" { return nil, errors.New("collector URL cannot be empty") } @@ -113,32 +112,6 @@ func NewRawExporter(collectorURL string, opts ...Option) (*Exporter, error) { }, nil } -// NewExportPipeline sets up a complete export pipeline -// with the recommended setup for trace provider -func NewExportPipeline(collectorURL string, opts ...Option) (*sdktrace.TracerProvider, error) { - exporter, err := NewRawExporter(collectorURL, opts...) - if err != nil { - return nil, err - } - - tpOpts := append(exporter.config.tpOpts, sdktrace.WithBatcher(exporter)) - tp := sdktrace.NewTracerProvider(tpOpts...) - - return tp, err -} - -// InstallNewPipeline instantiates a NewExportPipeline with the -// recommended configuration and registers it globally. -func InstallNewPipeline(collectorURL string, opts ...Option) error { - tp, err := NewExportPipeline(collectorURL, opts...) - if err != nil { - return err - } - - otel.SetTracerProvider(tp) - return nil -} - // ExportSpans exports spans to a Zipkin receiver. func (e *Exporter) ExportSpans(ctx context.Context, spans []sdktrace.ReadOnlySpan) error { e.stoppedMu.RLock() diff --git a/exporters/trace/zipkin/zipkin_test.go b/exporters/trace/zipkin/zipkin_test.go index a611a1018a7..7d1b5ec2fb9 100644 --- a/exporters/trace/zipkin/zipkin_test.go +++ b/exporters/trace/zipkin/zipkin_test.go @@ -30,7 +30,6 @@ import ( "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" - "go.opentelemetry.io/otel" "go.opentelemetry.io/otel/codes" "go.opentelemetry.io/otel/sdk/resource" sdktrace "go.opentelemetry.io/otel/sdk/trace" @@ -43,62 +42,8 @@ const ( collectorURL = "http://localhost:9411/api/v2/spans" ) -func TestInstallNewPipeline(t *testing.T) { - err := InstallNewPipeline( - collectorURL, - ) - assert.NoError(t, err) - assert.IsType(t, &sdktrace.TracerProvider{}, otel.GetTracerProvider()) -} - -func TestNewExportPipeline(t *testing.T) { - testCases := []struct { - name string - options []Option - testSpanSampling, spanShouldBeSampled bool - }{ - { - name: "simple pipeline", - }, - { - name: "always on", - options: []Option{ - WithSDKOptions(sdktrace.WithSampler(sdktrace.AlwaysSample())), - }, - testSpanSampling: true, - spanShouldBeSampled: true, - }, - { - name: "never", - options: []Option{ - WithSDKOptions(sdktrace.WithSampler(sdktrace.NeverSample())), - }, - testSpanSampling: true, - spanShouldBeSampled: false, - }, - } - - for _, tc := range testCases { - t.Run(tc.name, func(t *testing.T) { - tp, err := NewExportPipeline( - collectorURL, - tc.options..., - ) - assert.NoError(t, err) - assert.NotEqual(t, tp, otel.GetTracerProvider()) - - if tc.testSpanSampling { - _, span := tp.Tracer("zipkin test").Start(context.Background(), tc.name) - spanCtx := span.SpanContext() - assert.Equal(t, tc.spanShouldBeSampled, spanCtx.IsSampled()) - span.End() - } - }) - } -} - func TestNewRawExporter(t *testing.T) { - _, err := NewRawExporter( + _, err := New( collectorURL, ) @@ -112,7 +57,7 @@ func TestNewRawExporterShouldFailInvalidCollectorURL(t *testing.T) { ) // cannot be empty - exp, err = NewRawExporter( + exp, err = New( "", ) @@ -121,7 +66,7 @@ func TestNewRawExporterShouldFailInvalidCollectorURL(t *testing.T) { assert.Nil(t, exp) // invalid URL - exp, err = NewRawExporter( + exp, err = New( "localhost", ) @@ -339,7 +284,7 @@ func TestExportSpans(t *testing.T) { defer collector.Close() ls := &logStore{T: t} logger := logStoreLogger(ls) - exporter, err := NewRawExporter(collector.url, WithLogger(logger)) + exporter, err := New(collector.url, WithLogger(logger)) require.NoError(t, err) ctx := context.Background() require.Len(t, ls.Messages, 0) @@ -364,7 +309,7 @@ func TestExporterShutdownHonorsTimeout(t *testing.T) { ctx, cancel := context.WithTimeout(context.Background(), 1*time.Minute) defer cancel() - exp, err := NewRawExporter(collectorURL) + exp, err := New(collectorURL) require.NoError(t, err) innerCtx, innerCancel := context.WithTimeout(ctx, time.Nanosecond) @@ -377,7 +322,7 @@ func TestExporterShutdownHonorsCancel(t *testing.T) { ctx, cancel := context.WithTimeout(context.Background(), 1*time.Minute) defer cancel() - exp, err := NewRawExporter(collectorURL) + exp, err := New(collectorURL) require.NoError(t, err) innerCtx, innerCancel := context.WithCancel(ctx) @@ -386,39 +331,8 @@ func TestExporterShutdownHonorsCancel(t *testing.T) { } func TestErrorOnExportShutdownExporter(t *testing.T) { - exp, err := NewRawExporter(collectorURL) + exp, err := New(collectorURL) require.NoError(t, err) assert.NoError(t, exp.Shutdown(context.Background())) assert.NoError(t, exp.ExportSpans(context.Background(), nil)) } - -func TestNewExportPipelineWithOptions(t *testing.T) { - const eventCountLimit = 10 - - collector := startMockZipkinCollector(t) - defer collector.Close() - - tp, err := NewExportPipeline(collector.url, - WithSDKOptions( - sdktrace.WithResource(resource.NewSchemaless( - semconv.ServiceNameKey.String("zipkin-test"), - )), - sdktrace.WithSpanLimits(sdktrace.SpanLimits{ - EventCountLimit: eventCountLimit, - }), - ), - ) - require.NoError(t, err) - - otel.SetTracerProvider(tp) - _, span := otel.Tracer("zipkin-tracer").Start(context.Background(), "test-span") - for i := 0; i < eventCountLimit*2; i++ { - span.AddEvent(fmt.Sprintf("event-%d", i)) - } - span.End() - - require.NoError(t, tp.Shutdown(context.Background())) - require.Equal(t, 1, collector.ModelsLen()) - model := collector.StealModels()[0] - require.Equal(t, len(model.Annotations), eventCountLimit) -} diff --git a/sdk/metric/controller/basic/controller_test.go b/sdk/metric/controller/basic/controller_test.go index 37772e3c294..9bfced75bd6 100644 --- a/sdk/metric/controller/basic/controller_test.go +++ b/sdk/metric/controller/basic/controller_test.go @@ -261,7 +261,7 @@ type blockingExporter struct { func newBlockingExporter() *blockingExporter { return &blockingExporter{ - exporter: processortest.NewExporter( + exporter: processortest.New( export.CumulativeExportKindSelector(), attribute.DefaultEncoder(), ), @@ -342,7 +342,7 @@ func TestExportTimeout(t *testing.T) { } func TestCollectAfterStopThenStartAgain(t *testing.T) { - exp := processortest.NewExporter( + exp := processortest.New( export.CumulativeExportKindSelector(), attribute.DefaultEncoder(), ) diff --git a/sdk/metric/controller/basic/push_test.go b/sdk/metric/controller/basic/push_test.go index 249fe41a8cc..56a623954df 100644 --- a/sdk/metric/controller/basic/push_test.go +++ b/sdk/metric/controller/basic/push_test.go @@ -66,7 +66,7 @@ func init() { } func newExporter() *processortest.Exporter { - return processortest.NewExporter( + return processortest.New( export.StatelessExportKindSelector(), attribute.DefaultEncoder(), ) diff --git a/sdk/metric/processor/basic/basic_test.go b/sdk/metric/processor/basic/basic_test.go index 6b207caa5e5..48a2abcab14 100644 --- a/sdk/metric/processor/basic/basic_test.go +++ b/sdk/metric/processor/basic/basic_test.go @@ -500,7 +500,7 @@ func TestSumObserverEndToEnd(t *testing.T) { accum.Collect(ctx) require.NoError(t, proc.FinishCollection()) - exporter := processortest.NewExporter(eselector, attribute.DefaultEncoder()) + exporter := processortest.New(eselector, attribute.DefaultEncoder()) require.NoError(t, exporter.Export(ctx, data)) require.EqualValues(t, map[string]float64{ diff --git a/sdk/metric/processor/processortest/test.go b/sdk/metric/processor/processortest/test.go index 933639f38c0..6aeb306c703 100644 --- a/sdk/metric/processor/processortest/test.go +++ b/sdk/metric/processor/processortest/test.go @@ -309,7 +309,7 @@ func (o *Output) AddAccumulation(acc export.Accumulation) error { ) } -// NewExporter returns a new testing Exporter implementation. +// New returns a new testing Exporter implementation. // Verify exporter outputs using Values(), e.g.,: // // require.EqualValues(t, map[string]float64{ @@ -318,7 +318,7 @@ func (o *Output) AddAccumulation(acc export.Accumulation) error { // // Where in the example A=1,B=2 is the encoded labels and R=V is the // encoded resource value. -func NewExporter(selector export.ExportKindSelector, encoder attribute.Encoder) *Exporter { +func New(selector export.ExportKindSelector, encoder attribute.Encoder) *Exporter { return &Exporter{ ExportKindSelector: selector, output: NewOutput(encoder), diff --git a/sdk/metric/processor/processortest/test_test.go b/sdk/metric/processor/processortest/test_test.go index 42ec361f393..0b650ac4f70 100644 --- a/sdk/metric/processor/processortest/test_test.go +++ b/sdk/metric/processor/processortest/test_test.go @@ -73,7 +73,7 @@ func TestProcessorTesting(t *testing.T) { require.EqualValues(t, expect, testProc.Values()) // Export the data and validate it again. - exporter := processorTest.NewExporter( + exporter := processorTest.New( export.StatelessExportKindSelector(), attribute.DefaultEncoder(), ) diff --git a/sdk/metric/processor/reducer/reducer_test.go b/sdk/metric/processor/reducer/reducer_test.go index 09912c93da3..0acfe87018c 100644 --- a/sdk/metric/processor/reducer/reducer_test.go +++ b/sdk/metric/processor/reducer/reducer_test.go @@ -94,7 +94,7 @@ func TestFilterBasicProcessor(t *testing.T) { reducer.New(testFilter{}, basicProc), resource.NewSchemaless(attribute.String("R", "V")), ) - exporter := processorTest.NewExporter(basicProc, attribute.DefaultEncoder()) + exporter := processorTest.New(basicProc, attribute.DefaultEncoder()) generateData(accum) diff --git a/website_docs/getting-started.md b/website_docs/getting-started.md index 33285ea642c..65f6a705222 100644 --- a/website_docs/getting-started.md +++ b/website_docs/getting-started.md @@ -51,7 +51,7 @@ To initialize the console exporter, add the following code to the file your `mai ```go func main() { - exporter, err := stdout.NewExporter( + exporter, err := stdout.New( stdout.WithPrettyPrint(), ) if err != nil { @@ -202,7 +202,3 @@ In this snippet, we're doing a few things. First, we're asking the global trace Inside our function, we're creating a new span by calling `tracer.Start` with the context we just created, and a name. Passing the context will set our span as 'active' in it, which is used in our inner function to make a new child span. The name is important - every span needs a name, and these names are the primary method of indicating what a span represents. Calling `defer span.End()` ensures that our span will complete once this function has finished its work. Spans can have attributes and events, which are metadata and log statements that help you interpret traces after-the-fact. Finally, in this code snippet we can see an example of creating a new function and propagating the span to it inside our code. When you run this program, you'll see that the 'Sub operation...' span has been created as a child of the 'operation' span. We also record some measurements. Recording measurements with asynchronous instruments is controlled by SDK and the controller we use, so we do not need to do anything else after creating the instrument and passing the callback to it. For synchronous instruments there are two ways of recording measurements - either through the instrument, bounded or not (in our case it's a value recorder, so we use the `Record` function), or by making a batched measurement (with `meter.RecordBatch`). Batched measurements allow you to use multiple instruments to create measurement and record them once. - -# Final notes - -You may have noticed that setting up a tracing and metric pipeline can be a bit involved (create an exporter, a batcher, a tracer provider, a selector, a processor and a controller, and then start the controller, then use the controller to get a meter provider, so it can be registered as a global instance together with the trace provider we got earlier). Some exporters provide a utility functions simplifying these steps. For example the stdout exporter used in this document provides a `NewExportPipeline` that creates all the necessary items, and a `InstallNewPipeline` function that also registers the tracer and meter providers globally.