From 475badc7b044d7dc3bb24b5edec7a19fdaed3fb8 Mon Sep 17 00:00:00 2001 From: Tyler Yahn Date: Tue, 9 Apr 2024 08:29:37 -0700 Subject: [PATCH 1/2] Implement the Export method --- .../otlp/otlplog/otlploghttp/exporter.go | 14 ++++- .../otlp/otlplog/otlploghttp/exporter_test.go | 56 +++++++++++++++++++ .../otlploghttp/internal/transform/log.go | 17 ++++++ 3 files changed, 85 insertions(+), 2 deletions(-) create mode 100644 exporters/otlp/otlplog/otlploghttp/internal/transform/log.go diff --git a/exporters/otlp/otlplog/otlploghttp/exporter.go b/exporters/otlp/otlplog/otlploghttp/exporter.go index 2338361e4c7..3cad99d2a8b 100644 --- a/exporters/otlp/otlplog/otlploghttp/exporter.go +++ b/exporters/otlp/otlplog/otlploghttp/exporter.go @@ -5,8 +5,10 @@ package otlploghttp // import "go.opentelemetry.io/otel/exporters/otlp/otlplog/o import ( "context" + "errors" "sync/atomic" + "go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploghttp/internal/transform" "go.opentelemetry.io/otel/sdk/log" ) @@ -37,13 +39,21 @@ func newExporter(c *client, _ config) (*Exporter, error) { return e, nil } +// Used for testing. +var transformResourceLogs = transform.ResourceLogs + // Export transforms and transmits log records to an OTLP receiver. func (e *Exporter) Export(ctx context.Context, records []log.Record) error { if e.stopped.Load() { return nil } - // TODO: implement. - return nil + + otlp, err := transformResourceLogs(records) + if otlp != nil { + // Best effort upload of transformable logs. + err = errors.Join(err, e.client.Load().UploadLogs(ctx, otlp)) + } + return err } // Shutdown shuts down the Exporter. Calls to Export or ForceFlush will perform diff --git a/exporters/otlp/otlplog/otlploghttp/exporter_test.go b/exporters/otlp/otlplog/otlploghttp/exporter_test.go index 2474836c84a..c09b7ec48c3 100644 --- a/exporters/otlp/otlplog/otlploghttp/exporter_test.go +++ b/exporters/otlp/otlplog/otlploghttp/exporter_test.go @@ -5,14 +5,70 @@ package otlploghttp import ( "context" + "errors" "testing" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" "go.opentelemetry.io/otel/sdk/log" + logpb "go.opentelemetry.io/proto/otlp/logs/v1" ) +func TestExporterExportErrors(t *testing.T) { + var ( + errUpload = errors.New("upload") + errTForm = errors.New("transform") + ) + + c := &client{ + uploadLogs: func(context.Context, *logpb.ResourceLogs) error { + return errUpload + }, + } + + orig := transformResourceLogs + transformResourceLogs = func(r []log.Record) (*logpb.ResourceLogs, error) { + return new(logpb.ResourceLogs), errTForm + } + t.Cleanup(func() { transformResourceLogs = orig }) + + e, err := newExporter(c, config{}) + require.NoError(t, err, "New") + + err = e.Export(context.Background(), make([]log.Record, 1)) + assert.ErrorIs(t, err, errUpload) + assert.ErrorIs(t, err, errTForm) +} + +func TestExporterExport(t *testing.T) { + var uploads int + c := &client{ + uploadLogs: func(context.Context, *logpb.ResourceLogs) error { + uploads++ + return nil + }, + } + + orig := transformResourceLogs + var got []log.Record + transformResourceLogs = func(r []log.Record) (*logpb.ResourceLogs, error) { + got = r + return new(logpb.ResourceLogs), nil + } + t.Cleanup(func() { transformResourceLogs = orig }) + + e, err := newExporter(c, config{}) + require.NoError(t, err, "New") + + ctx := context.Background() + want := make([]log.Record, 1) + assert.NoError(t, e.Export(ctx, want)) + + assert.Equal(t, 1, uploads, "client UploadLogs calls") + assert.Equal(t, want, got, "transformed log records") +} + func TestExporterShutdown(t *testing.T) { ctx := context.Background() e, err := New(ctx) diff --git a/exporters/otlp/otlplog/otlploghttp/internal/transform/log.go b/exporters/otlp/otlplog/otlploghttp/internal/transform/log.go new file mode 100644 index 00000000000..bea72f2991a --- /dev/null +++ b/exporters/otlp/otlplog/otlploghttp/internal/transform/log.go @@ -0,0 +1,17 @@ +// Copyright The OpenTelemetry Authors +// SPDX-License-Identifier: Apache-2.0 + +// Package transform provides transformation functionality from the +// sdk/log data-types into OTLP data-types. +package transform // import "go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploghttp/internal/transform" + +import ( + lpb "go.opentelemetry.io/proto/otlp/logs/v1" + + "go.opentelemetry.io/otel/sdk/log" +) + +func ResourceLogs([]log.Record) (*lpb.ResourceLogs, error) { + // TODO: implement + return nil, nil +} From 34e471192494cbfb9467e946463bc34e56407d1a Mon Sep 17 00:00:00 2001 From: Tyler Yahn Date: Tue, 9 Apr 2024 11:52:57 -0700 Subject: [PATCH 2/2] Update exporters/otlp/otlplog/otlploghttp/exporter.go MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Robert PajÄ…k --- exporters/otlp/otlplog/otlploghttp/exporter.go | 1 - 1 file changed, 1 deletion(-) diff --git a/exporters/otlp/otlplog/otlploghttp/exporter.go b/exporters/otlp/otlplog/otlploghttp/exporter.go index 3cad99d2a8b..ac4c403a970 100644 --- a/exporters/otlp/otlplog/otlploghttp/exporter.go +++ b/exporters/otlp/otlplog/otlploghttp/exporter.go @@ -47,7 +47,6 @@ func (e *Exporter) Export(ctx context.Context, records []log.Record) error { if e.stopped.Load() { return nil } - otlp, err := transformResourceLogs(records) if otlp != nil { // Best effort upload of transformable logs.