From b796f0f55cc67e794641305de85aa7176171c8e0 Mon Sep 17 00:00:00 2001 From: Khushi Jain Date: Mon, 18 Mar 2024 15:38:01 +0530 Subject: [PATCH 01/15] Add catalog-info.yaml config file --- catalog-info.yaml | 10 ++++++++++ 1 file changed, 10 insertions(+) create mode 100644 catalog-info.yaml diff --git a/catalog-info.yaml b/catalog-info.yaml new file mode 100644 index 00000000000..8986b549326 --- /dev/null +++ b/catalog-info.yaml @@ -0,0 +1,10 @@ +apiVersion: backstage.io/v1alpha1 +kind: Component +metadata: + name: opentelemetry-go-contrib + annotations: + github.com/project-slug: khushijain21/opentelemetry-go-contrib +spec: + type: other + lifecycle: unknown + owner: guests From 927d4384db9e03ea6605a82b66182152bc3c3423 Mon Sep 17 00:00:00 2001 From: khushijain21 Date: Mon, 6 May 2024 20:59:59 +0530 Subject: [PATCH 02/15] delete config.yaml --- catalog-info.yaml | 10 ---------- 1 file changed, 10 deletions(-) delete mode 100644 catalog-info.yaml diff --git a/catalog-info.yaml b/catalog-info.yaml deleted file mode 100644 index 8986b549326..00000000000 --- a/catalog-info.yaml +++ /dev/null @@ -1,10 +0,0 @@ -apiVersion: backstage.io/v1alpha1 -kind: Component -metadata: - name: opentelemetry-go-contrib - annotations: - github.com/project-slug: khushijain21/opentelemetry-go-contrib -spec: - type: other - lifecycle: unknown - owner: guests From 088bca5648f6a022c4da136ead162d3b85542326 Mon Sep 17 00:00:00 2001 From: khushijain21 Date: Mon, 6 May 2024 22:04:08 +0530 Subject: [PATCH 03/15] Skeleton of Zapcore and config options --- .github/dependabot.yml | 9 ++++ bridges/otelzap/config.go | 82 ++++++++++++++++++++++++++++++++++++ bridges/otelzap/core.go | 62 +++++++++++++++++++++++++++ bridges/otelzap/core_test.go | 51 ++++++++++++++++++++++ bridges/otelzap/go.mod | 22 ++++++++++ bridges/otelzap/go.sum | 33 +++++++++++++++ bridges/otelzap/version.go | 7 +++ versions.yaml | 1 + 8 files changed, 267 insertions(+) create mode 100644 bridges/otelzap/config.go create mode 100644 bridges/otelzap/core.go create mode 100644 bridges/otelzap/core_test.go create mode 100644 bridges/otelzap/go.mod create mode 100644 bridges/otelzap/go.sum create mode 100644 bridges/otelzap/version.go diff --git a/.github/dependabot.yml b/.github/dependabot.yml index bb6bf7d7278..6701e2807f5 100644 --- a/.github/dependabot.yml +++ b/.github/dependabot.yml @@ -109,6 +109,15 @@ updates: schedule: interval: weekly day: sunday + - package-ecosystem: gomod + directory: /bridges/otelzap + labels: + - dependencies + - go + - Skip Changelog + schedule: + interval: weekly + day: sunday - package-ecosystem: gomod directory: /bridges/prometheus labels: diff --git a/bridges/otelzap/config.go b/bridges/otelzap/config.go new file mode 100644 index 00000000000..871ad5b50d0 --- /dev/null +++ b/bridges/otelzap/config.go @@ -0,0 +1,82 @@ +// Copyright The OpenTelemetry Authors +// SPDX-License-Identifier: Apache-2.0 + +package otelzap // import "otelzap" + +import ( + "go.opentelemetry.io/otel/log" + "go.opentelemetry.io/otel/log/global" + "go.opentelemetry.io/otel/sdk/instrumentation" +) + +type config struct { + provider log.LoggerProvider + scope instrumentation.Scope +} + +func newConfig(options []Option) config { + var c config + for _, opt := range options { + c = opt.apply(c) + } + + var emptyScope instrumentation.Scope + if c.scope == emptyScope { + c.scope = instrumentation.Scope{ + Name: bridgeName, + Version: version, + } + } + + if c.provider == nil { + c.provider = global.GetLoggerProvider() + } + + return c +} + +func (c config) logger() log.Logger { + var opts []log.LoggerOption + if c.scope.Version != "" { + opts = append(opts, log.WithInstrumentationVersion(c.scope.Version)) + } + if c.scope.SchemaURL != "" { + opts = append(opts, log.WithSchemaURL(c.scope.SchemaURL)) + } + return c.provider.Logger(c.scope.Name, opts...) +} + +// Option configures a [zapcore]. +type Option interface { + apply(config) config +} + +type optFunc func(config) config + +func (f optFunc) apply(c config) config { return f(c) } + +// WithInstrumentationScope returns an [Option] that configures the scope of +// the [log.Logger] used by a [zapcore]. +// +// By default if this Option is not provided, the zapcore will use a default +// instrumentation scope describing this bridge package. It is recommended to +// provide this so log data can be associated with its source package or +// module. +func WithInstrumentationScope(scope instrumentation.Scope) Option { + return optFunc(func(c config) config { + c.scope = scope + return c + }) +} + +// WithLoggerProvider returns an [Option] that configures [log.LoggerProvider] +// used by a [Core] to create its [log.Logger]. +// +// By default if this Option is not provided, the Handler will use the global +// LoggerProvider. +func WithLoggerProvider(provider log.LoggerProvider) Option { + return optFunc(func(c config) config { + c.provider = provider + return c + }) +} diff --git a/bridges/otelzap/core.go b/bridges/otelzap/core.go new file mode 100644 index 00000000000..60d71972424 --- /dev/null +++ b/bridges/otelzap/core.go @@ -0,0 +1,62 @@ +// Copyright The OpenTelemetry Authors +// SPDX-License-Identifier: Apache-2.0 + +// Package otelzap provides a bridge between the [go.uber.org/zap] and +// OpenTelemetry logging. +package otelzap // import "otelzap" + +import ( + "go.uber.org/zap/zapcore" + + "go.opentelemetry.io/otel/log" +) + +const ( + bridgeName = "go.opentelemetry.io/contrib/bridges/otelzap" +) + +// Core is a [zapcore.Core] that sends logging records to OpenTelemetry. +type Core struct { + logger log.Logger +} + +// Compile-time check *Core implements zapcore.Core. +var _ zapcore.Core = (*Core)(nil) + +// NewOTelZapCore creates a new [zapcore.Core] that can be used with zap.New() +// this instance will translate zap logs to opentelemetry logs and export them. +func NewCore(opts ...Option) *Core { + cfg := newConfig(opts) + return &Core{ + logger: cfg.logger(), + } +} + +// TODO +// LevelEnabler decides whether a given logging level is enabled when logging a message. +func (o *Core) Enabled(level zapcore.Level) bool { + return true +} + +// TODO +// With adds structured context to the Core. +func (o *Core) With(fields []zapcore.Field) zapcore.Core { + return o +} + +// Sync flushes buffered logs (if any). +func (o *Core) Sync() error { + return nil +} + +// Check determines whether the supplied Entry should be logged using core.Enabled method. +func (o *Core) Check(ent zapcore.Entry, ce *zapcore.CheckedEntry) *zapcore.CheckedEntry { + // TODO + return ce +} + +// TODO +// Write method encodes zap fields to OTel logs and emits them. +func (o *Core) Write(ent zapcore.Entry, fields []zapcore.Field) error { + return nil +} diff --git a/bridges/otelzap/core_test.go b/bridges/otelzap/core_test.go new file mode 100644 index 00000000000..45cc01cdd33 --- /dev/null +++ b/bridges/otelzap/core_test.go @@ -0,0 +1,51 @@ +// Copyright The OpenTelemetry Authors +// SPDX-License-Identifier: Apache-2.0 + +// Copyright (c) 2016-2017 Uber Technologies, Inc. +package otelzap + +import ( + "testing" + + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" + + "go.opentelemetry.io/otel/log/global" + "go.opentelemetry.io/otel/log/logtest" + "go.opentelemetry.io/otel/sdk/instrumentation" +) + +func TestNewCoreConfiguration(t *testing.T) { + t.Run("Default", func(t *testing.T) { + r := logtest.NewRecorder() + global.SetLoggerProvider(r) + + var h *Core + assert.NotPanics(t, func() { h = NewCore() }) + assert.NotNil(t, h.logger) + require.IsType(t, &logtest.Recorder{}, h.logger) + + l := h.logger.(*logtest.Recorder) + want := &logtest.ScopeRecords{Name: bridgeName, Version: version} + assert.Equal(t, want, l.Result()[0]) + }) + + t.Run("Options", func(t *testing.T) { + r := logtest.NewRecorder() + scope := instrumentation.Scope{Name: "name", Version: "ver", SchemaURL: "url"} + var h *Core + assert.NotPanics(t, func() { + h = NewCore( + WithLoggerProvider(r), + WithInstrumentationScope(scope), + ) + }) + assert.NotNil(t, h.logger) + require.IsType(t, &logtest.Recorder{}, h.logger) + + l := h.logger.(*logtest.Recorder) + assert.Equal(t, scope.Name, l.Result()[0].Name) + assert.Equal(t, scope.Version, l.Result()[0].Version) + assert.Equal(t, scope.SchemaURL, l.Result()[0].SchemaURL) + }) +} diff --git a/bridges/otelzap/go.mod b/bridges/otelzap/go.mod new file mode 100644 index 00000000000..87ee2a56db5 --- /dev/null +++ b/bridges/otelzap/go.mod @@ -0,0 +1,22 @@ +module otelzap + +go 1.21 + +require ( + github.com/stretchr/testify v1.9.0 + go.opentelemetry.io/otel/log v0.2.0-alpha + go.opentelemetry.io/otel/sdk v1.26.0 + go.uber.org/zap v1.27.0 +) + +require ( + github.com/davecgh/go-spew v1.1.1 // indirect + github.com/go-logr/logr v1.4.1 // indirect + github.com/go-logr/stdr v1.2.2 // indirect + github.com/pmezard/go-difflib v1.0.0 // indirect + go.opentelemetry.io/otel v1.26.0 // indirect + go.opentelemetry.io/otel/metric v1.26.0 // indirect + go.opentelemetry.io/otel/trace v1.26.0 // indirect + go.uber.org/multierr v1.10.0 // indirect + gopkg.in/yaml.v3 v3.0.1 // indirect +) diff --git a/bridges/otelzap/go.sum b/bridges/otelzap/go.sum new file mode 100644 index 00000000000..91b4bbf7fa1 --- /dev/null +++ b/bridges/otelzap/go.sum @@ -0,0 +1,33 @@ +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= +github.com/go-logr/logr v1.4.1 h1:pKouT5E8xu9zeFC39JXRDukb6JFQPXM5p5I91188VAQ= +github.com/go-logr/logr v1.4.1/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY= +github.com/go-logr/stdr v1.2.2 h1:hSWxHoqTgW2S2qGc0LTAI563KZ5YKYRhT3MFKZMbjag= +github.com/go-logr/stdr v1.2.2/go.mod h1:mMo/vtBO5dYbehREoey6XUKy/eSumjCCveDpRre4VKE= +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/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= +github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= +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= +go.opentelemetry.io/otel v1.26.0 h1:LQwgL5s/1W7YiiRwxf03QGnWLb2HW4pLiAhaA5cZXBs= +go.opentelemetry.io/otel v1.26.0/go.mod h1:UmLkJHUAidDval2EICqBMbnAd0/m2vmpf/dAM+fvFs4= +go.opentelemetry.io/otel/log v0.2.0-alpha h1:ixOPvMzserpqA07SENHvRzkZOsnG0XbPr74hv1AQ+n0= +go.opentelemetry.io/otel/log v0.2.0-alpha/go.mod h1:vbFZc65yq4c4ssvXY43y/nIqkNJLxORrqw0L85P59LA= +go.opentelemetry.io/otel/metric v1.26.0 h1:7S39CLuY5Jgg9CrnA9HHiEjGMF/X2VHvoXGgSllRz30= +go.opentelemetry.io/otel/metric v1.26.0/go.mod h1:SY+rHOI4cEawI9a7N1A4nIg/nTQXe1ccCNWYOJUrpX4= +go.opentelemetry.io/otel/sdk v1.26.0 h1:Y7bumHf5tAiDlRYFmGqetNcLaVUZmh4iYfmGxtmz7F8= +go.opentelemetry.io/otel/sdk v1.26.0/go.mod h1:0p8MXpqLeJ0pzcszQQN4F0S5FVjBLgypeGSngLsmirs= +go.opentelemetry.io/otel/trace v1.26.0 h1:1ieeAUb4y0TE26jUFrCIXKpTuVK7uJGN9/Z/2LP5sQA= +go.opentelemetry.io/otel/trace v1.26.0/go.mod h1:4iDxvGDQuUkHve82hJJ8UqrwswHYsZuWCBllGV2U2y0= +go.uber.org/goleak v1.3.0 h1:2K3zAYmnTNqV73imy9J1T3WC+gmCePx2hEGkimedGto= +go.uber.org/goleak v1.3.0/go.mod h1:CoHD4mav9JJNrW/WLlf7HGZPjdw8EucARQHekz1X6bE= +go.uber.org/multierr v1.10.0 h1:S0h4aNzvfcFsC3dRF1jLoaov7oRaKqRGC/pUEJ2yvPQ= +go.uber.org/multierr v1.10.0/go.mod h1:20+QtiLqy0Nd6FdQB9TLXag12DsQkrbs3htMFfDN80Y= +go.uber.org/zap v1.27.0 h1:aJMhYGrd5QSmlpLMr2MftRKl7t8J8PTZPA732ud/XR8= +go.uber.org/zap v1.27.0/go.mod h1:GB2qFLM7cTU87MWRP2mPIjqfIDnGu+VIO4V/SdhGo2E= +gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= +gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= +gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= diff --git a/bridges/otelzap/version.go b/bridges/otelzap/version.go new file mode 100644 index 00000000000..0219fcd68a9 --- /dev/null +++ b/bridges/otelzap/version.go @@ -0,0 +1,7 @@ +// Copyright The OpenTelemetry Authors +// SPDX-License-Identifier: Apache-2.0 + +package otelzap // import "otelzap" + +// Version is the current release version of otelzap in use. +const version = "0.1.0" diff --git a/versions.yaml b/versions.yaml index e3163f56852..3e796053753 100644 --- a/versions.yaml +++ b/versions.yaml @@ -81,3 +81,4 @@ excluded-modules: - go.opentelemetry.io/contrib/instrgen - go.opentelemetry.io/contrib/instrgen/driver - go.opentelemetry.io/contrib/instrgen/testdata/interface + - go.opentelemetry.io/contrib/bridges/otelzap \ No newline at end of file From 7ec5532edd8b5134b9fbe70d00c3bcace9e89824 Mon Sep 17 00:00:00 2001 From: Khushi Jain Date: Tue, 7 May 2024 09:22:03 +0530 Subject: [PATCH 04/15] Update bridges/otelzap/config.go MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Robert Pająk --- bridges/otelzap/config.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bridges/otelzap/config.go b/bridges/otelzap/config.go index 871ad5b50d0..bd425860255 100644 --- a/bridges/otelzap/config.go +++ b/bridges/otelzap/config.go @@ -46,7 +46,7 @@ func (c config) logger() log.Logger { return c.provider.Logger(c.scope.Name, opts...) } -// Option configures a [zapcore]. +// Option configures a [Core]. type Option interface { apply(config) config } From 4920c4121af0de92225ae1846058eea4cc86b7da Mon Sep 17 00:00:00 2001 From: Khushi Jain Date: Tue, 7 May 2024 09:23:36 +0530 Subject: [PATCH 05/15] Update bridges/otelzap/config.go MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Robert Pająk --- bridges/otelzap/config.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bridges/otelzap/config.go b/bridges/otelzap/config.go index bd425860255..8b5167a608a 100644 --- a/bridges/otelzap/config.go +++ b/bridges/otelzap/config.go @@ -56,7 +56,7 @@ type optFunc func(config) config func (f optFunc) apply(c config) config { return f(c) } // WithInstrumentationScope returns an [Option] that configures the scope of -// the [log.Logger] used by a [zapcore]. +// the [log.Logger] used by a [Core]. // // By default if this Option is not provided, the zapcore will use a default // instrumentation scope describing this bridge package. It is recommended to From 6f08b25c9f65651a6c0d1e7e7e319e26785837cf Mon Sep 17 00:00:00 2001 From: Khushi Jain Date: Tue, 7 May 2024 09:23:56 +0530 Subject: [PATCH 06/15] Update bridges/otelzap/core.go MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Robert Pająk --- bridges/otelzap/core.go | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/bridges/otelzap/core.go b/bridges/otelzap/core.go index 60d71972424..fc1051e104a 100644 --- a/bridges/otelzap/core.go +++ b/bridges/otelzap/core.go @@ -23,8 +23,7 @@ type Core struct { // Compile-time check *Core implements zapcore.Core. var _ zapcore.Core = (*Core)(nil) -// NewOTelZapCore creates a new [zapcore.Core] that can be used with zap.New() -// this instance will translate zap logs to opentelemetry logs and export them. +// NewCore creates a new [zapcore.Core] that can be used with [go.uber.org/zap.New]. func NewCore(opts ...Option) *Core { cfg := newConfig(opts) return &Core{ From dae2877857b2f18d9c0f9db7fc17e020fb9b143b Mon Sep 17 00:00:00 2001 From: Khushi Jain Date: Tue, 7 May 2024 09:25:25 +0530 Subject: [PATCH 07/15] Update bridges/otelzap/config.go MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Robert Pająk --- bridges/otelzap/config.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bridges/otelzap/config.go b/bridges/otelzap/config.go index 8b5167a608a..5cafda71aa9 100644 --- a/bridges/otelzap/config.go +++ b/bridges/otelzap/config.go @@ -58,7 +58,7 @@ func (f optFunc) apply(c config) config { return f(c) } // WithInstrumentationScope returns an [Option] that configures the scope of // the [log.Logger] used by a [Core]. // -// By default if this Option is not provided, the zapcore will use a default +// By default if this Option is not provided, [Core] will use a default // instrumentation scope describing this bridge package. It is recommended to // provide this so log data can be associated with its source package or // module. From aafddc269a662648f06e2fd0daa3db782cdab97c Mon Sep 17 00:00:00 2001 From: khushijain21 Date: Tue, 7 May 2024 09:27:02 +0530 Subject: [PATCH 08/15] follow up commit --- bridges/otelzap/config.go | 2 +- bridges/otelzap/core.go | 5 +++-- bridges/otelzap/core_test.go | 1 - bridges/otelzap/go.mod | 2 +- bridges/otelzap/version.go | 2 +- versions.yaml | 3 ++- 6 files changed, 8 insertions(+), 7 deletions(-) diff --git a/bridges/otelzap/config.go b/bridges/otelzap/config.go index 5cafda71aa9..5c94a4b53fe 100644 --- a/bridges/otelzap/config.go +++ b/bridges/otelzap/config.go @@ -1,7 +1,7 @@ // Copyright The OpenTelemetry Authors // SPDX-License-Identifier: Apache-2.0 -package otelzap // import "otelzap" +package otelzap // import "go.opentelemetry.io/contrib/bridges/otelzap" import ( "go.opentelemetry.io/otel/log" diff --git a/bridges/otelzap/core.go b/bridges/otelzap/core.go index fc1051e104a..d2fe8fa0390 100644 --- a/bridges/otelzap/core.go +++ b/bridges/otelzap/core.go @@ -3,7 +3,7 @@ // Package otelzap provides a bridge between the [go.uber.org/zap] and // OpenTelemetry logging. -package otelzap // import "otelzap" +package otelzap // import "go.opentelemetry.io/contrib/bridges/otelzap" import ( "go.uber.org/zap/zapcore" @@ -43,14 +43,15 @@ func (o *Core) With(fields []zapcore.Field) zapcore.Core { return o } +// TODO // Sync flushes buffered logs (if any). func (o *Core) Sync() error { return nil } +// TODO // Check determines whether the supplied Entry should be logged using core.Enabled method. func (o *Core) Check(ent zapcore.Entry, ce *zapcore.CheckedEntry) *zapcore.CheckedEntry { - // TODO return ce } diff --git a/bridges/otelzap/core_test.go b/bridges/otelzap/core_test.go index 45cc01cdd33..d946d03ac98 100644 --- a/bridges/otelzap/core_test.go +++ b/bridges/otelzap/core_test.go @@ -1,7 +1,6 @@ // Copyright The OpenTelemetry Authors // SPDX-License-Identifier: Apache-2.0 -// Copyright (c) 2016-2017 Uber Technologies, Inc. package otelzap import ( diff --git a/bridges/otelzap/go.mod b/bridges/otelzap/go.mod index 87ee2a56db5..51781478671 100644 --- a/bridges/otelzap/go.mod +++ b/bridges/otelzap/go.mod @@ -1,4 +1,4 @@ -module otelzap +module go.opentelemetry.io/contrib/bridges/otelzap go 1.21 diff --git a/bridges/otelzap/version.go b/bridges/otelzap/version.go index 0219fcd68a9..2c3a0431ac4 100644 --- a/bridges/otelzap/version.go +++ b/bridges/otelzap/version.go @@ -1,7 +1,7 @@ // Copyright The OpenTelemetry Authors // SPDX-License-Identifier: Apache-2.0 -package otelzap // import "otelzap" +package otelzap // import "go.opentelemetry.io/contrib/bridges/otelzap" // Version is the current release version of otelzap in use. const version = "0.1.0" diff --git a/versions.yaml b/versions.yaml index 3e796053753..4456d20433a 100644 --- a/versions.yaml +++ b/versions.yaml @@ -78,7 +78,8 @@ module-sets: modules: - go.opentelemetry.io/contrib/bridges/otelslog excluded-modules: + - go.opentelemetry.io/contrib/bridges/otelzap - go.opentelemetry.io/contrib/instrgen - go.opentelemetry.io/contrib/instrgen/driver - go.opentelemetry.io/contrib/instrgen/testdata/interface - - go.opentelemetry.io/contrib/bridges/otelzap \ No newline at end of file + \ No newline at end of file From f048cd4abd99602d5ed3fc45b1fc340ff6be70af Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Robert=20Paj=C4=85k?= Date: Tue, 7 May 2024 14:55:27 +0200 Subject: [PATCH 09/15] Update versions.yaml --- versions.yaml | 1 - 1 file changed, 1 deletion(-) diff --git a/versions.yaml b/versions.yaml index 01e06cb5d46..b49942eacbc 100644 --- a/versions.yaml +++ b/versions.yaml @@ -86,4 +86,3 @@ excluded-modules: - go.opentelemetry.io/contrib/instrgen - go.opentelemetry.io/contrib/instrgen/driver - go.opentelemetry.io/contrib/instrgen/testdata/interface - \ No newline at end of file From fde029a386291a9a33b270111ee33eed1e4979c7 Mon Sep 17 00:00:00 2001 From: Khushi Jain Date: Tue, 7 May 2024 19:45:27 +0530 Subject: [PATCH 10/15] Update bridges/otelzap/core_test.go MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Robert Pająk --- bridges/otelzap/core_test.go | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/bridges/otelzap/core_test.go b/bridges/otelzap/core_test.go index d946d03ac98..bfede8e7b61 100644 --- a/bridges/otelzap/core_test.go +++ b/bridges/otelzap/core_test.go @@ -41,10 +41,11 @@ func TestNewCoreConfiguration(t *testing.T) { }) assert.NotNil(t, h.logger) require.IsType(t, &logtest.Recorder{}, h.logger) - l := h.logger.(*logtest.Recorder) - assert.Equal(t, scope.Name, l.Result()[0].Name) - assert.Equal(t, scope.Version, l.Result()[0].Version) - assert.Equal(t, scope.SchemaURL, l.Result()[0].SchemaURL) + require.Len(t, l.Result(), 1) + + want := &logtest.ScopeRecords{Name: scope.Name, Version: scope.Version, SchemaURL: scope.SchemaURL} + got := l.Result()[0] + assert.Equal(t, want, got) }) } From f30866d088c4abaf5f739a287dec040b63e4755c Mon Sep 17 00:00:00 2001 From: Khushi Jain Date: Tue, 7 May 2024 19:45:36 +0530 Subject: [PATCH 11/15] Update bridges/otelzap/core_test.go MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Robert Pająk --- bridges/otelzap/core_test.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bridges/otelzap/core_test.go b/bridges/otelzap/core_test.go index bfede8e7b61..0f9968d080a 100644 --- a/bridges/otelzap/core_test.go +++ b/bridges/otelzap/core_test.go @@ -39,7 +39,7 @@ func TestNewCoreConfiguration(t *testing.T) { WithInstrumentationScope(scope), ) }) - assert.NotNil(t, h.logger) + require.NotNil(t, h.logger) require.IsType(t, &logtest.Recorder{}, h.logger) l := h.logger.(*logtest.Recorder) require.Len(t, l.Result(), 1) From 72381e5bd9964592924fccb382db42062590d5e9 Mon Sep 17 00:00:00 2001 From: Khushi Jain Date: Tue, 7 May 2024 19:46:19 +0530 Subject: [PATCH 12/15] Update bridges/otelzap/core_test.go MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Robert Pająk --- bridges/otelzap/core_test.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bridges/otelzap/core_test.go b/bridges/otelzap/core_test.go index 0f9968d080a..27f12317292 100644 --- a/bridges/otelzap/core_test.go +++ b/bridges/otelzap/core_test.go @@ -33,7 +33,7 @@ func TestNewCoreConfiguration(t *testing.T) { r := logtest.NewRecorder() scope := instrumentation.Scope{Name: "name", Version: "ver", SchemaURL: "url"} var h *Core - assert.NotPanics(t, func() { + require.NotPanics(t, func() { h = NewCore( WithLoggerProvider(r), WithInstrumentationScope(scope), From 75cb0499ab79ebcde4f4a3250f45a774557ed2e6 Mon Sep 17 00:00:00 2001 From: Khushi Jain Date: Tue, 7 May 2024 19:47:55 +0530 Subject: [PATCH 13/15] Update bridges/otelzap/core_test.go MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Robert Pająk --- bridges/otelzap/core_test.go | 2 ++ 1 file changed, 2 insertions(+) diff --git a/bridges/otelzap/core_test.go b/bridges/otelzap/core_test.go index 27f12317292..236e163a711 100644 --- a/bridges/otelzap/core_test.go +++ b/bridges/otelzap/core_test.go @@ -17,6 +17,8 @@ import ( func TestNewCoreConfiguration(t *testing.T) { t.Run("Default", func(t *testing.T) { r := logtest.NewRecorder() + prev := global.GetLoggerProvider() + defer global.SetLoggerProvider(prev) global.SetLoggerProvider(r) var h *Core From e99b08fb39da8607df25b44ec52f5673c21f62b8 Mon Sep 17 00:00:00 2001 From: Khushi Jain Date: Tue, 7 May 2024 19:48:57 +0530 Subject: [PATCH 14/15] Update bridges/otelzap/core_test.go MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Robert Pająk --- bridges/otelzap/core_test.go | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/bridges/otelzap/core_test.go b/bridges/otelzap/core_test.go index 236e163a711..5be764b98ad 100644 --- a/bridges/otelzap/core_test.go +++ b/bridges/otelzap/core_test.go @@ -22,13 +22,15 @@ func TestNewCoreConfiguration(t *testing.T) { global.SetLoggerProvider(r) var h *Core - assert.NotPanics(t, func() { h = NewCore() }) - assert.NotNil(t, h.logger) + require.NotPanics(t, func() { h = NewCore() }) + require.NotNil(t, h.logger) require.IsType(t, &logtest.Recorder{}, h.logger) - l := h.logger.(*logtest.Recorder) + require.Len(t, l.Result(), 1) + want := &logtest.ScopeRecords{Name: bridgeName, Version: version} - assert.Equal(t, want, l.Result()[0]) + got := l.Result()[0] + assert.Equal(t, want, got) }) t.Run("Options", func(t *testing.T) { From 33d60a11328582a643af816f64ee5b022eb4a53f Mon Sep 17 00:00:00 2001 From: khushijain21 Date: Tue, 7 May 2024 20:00:18 +0530 Subject: [PATCH 15/15] applied suggestions --- CODEOWNERS | 1 + bridges/otelzap/config.go | 82 ------------------------------------ bridges/otelzap/core.go | 74 ++++++++++++++++++++++++++++++++ bridges/otelzap/core_test.go | 2 +- 4 files changed, 76 insertions(+), 83 deletions(-) delete mode 100644 bridges/otelzap/config.go diff --git a/CODEOWNERS b/CODEOWNERS index 197c0971bd8..087b4446c14 100644 --- a/CODEOWNERS +++ b/CODEOWNERS @@ -23,6 +23,7 @@ CODEOWNERS @MrAlias @MadVikingGod @pellared @dashpole bridges/prometheus/ @open-telemetry/go-approvers @dashpole +bridges/otelzap/ @open-telemetry/go-approvers @pellared @khushijain21 config/ @open-telemetry/go-approvers @MadVikingGod @pellared @codeboten diff --git a/bridges/otelzap/config.go b/bridges/otelzap/config.go deleted file mode 100644 index 5c94a4b53fe..00000000000 --- a/bridges/otelzap/config.go +++ /dev/null @@ -1,82 +0,0 @@ -// Copyright The OpenTelemetry Authors -// SPDX-License-Identifier: Apache-2.0 - -package otelzap // import "go.opentelemetry.io/contrib/bridges/otelzap" - -import ( - "go.opentelemetry.io/otel/log" - "go.opentelemetry.io/otel/log/global" - "go.opentelemetry.io/otel/sdk/instrumentation" -) - -type config struct { - provider log.LoggerProvider - scope instrumentation.Scope -} - -func newConfig(options []Option) config { - var c config - for _, opt := range options { - c = opt.apply(c) - } - - var emptyScope instrumentation.Scope - if c.scope == emptyScope { - c.scope = instrumentation.Scope{ - Name: bridgeName, - Version: version, - } - } - - if c.provider == nil { - c.provider = global.GetLoggerProvider() - } - - return c -} - -func (c config) logger() log.Logger { - var opts []log.LoggerOption - if c.scope.Version != "" { - opts = append(opts, log.WithInstrumentationVersion(c.scope.Version)) - } - if c.scope.SchemaURL != "" { - opts = append(opts, log.WithSchemaURL(c.scope.SchemaURL)) - } - return c.provider.Logger(c.scope.Name, opts...) -} - -// Option configures a [Core]. -type Option interface { - apply(config) config -} - -type optFunc func(config) config - -func (f optFunc) apply(c config) config { return f(c) } - -// WithInstrumentationScope returns an [Option] that configures the scope of -// the [log.Logger] used by a [Core]. -// -// By default if this Option is not provided, [Core] will use a default -// instrumentation scope describing this bridge package. It is recommended to -// provide this so log data can be associated with its source package or -// module. -func WithInstrumentationScope(scope instrumentation.Scope) Option { - return optFunc(func(c config) config { - c.scope = scope - return c - }) -} - -// WithLoggerProvider returns an [Option] that configures [log.LoggerProvider] -// used by a [Core] to create its [log.Logger]. -// -// By default if this Option is not provided, the Handler will use the global -// LoggerProvider. -func WithLoggerProvider(provider log.LoggerProvider) Option { - return optFunc(func(c config) config { - c.provider = provider - return c - }) -} diff --git a/bridges/otelzap/core.go b/bridges/otelzap/core.go index d2fe8fa0390..1e934666c58 100644 --- a/bridges/otelzap/core.go +++ b/bridges/otelzap/core.go @@ -9,12 +9,86 @@ import ( "go.uber.org/zap/zapcore" "go.opentelemetry.io/otel/log" + "go.opentelemetry.io/otel/log/global" + "go.opentelemetry.io/otel/sdk/instrumentation" ) const ( bridgeName = "go.opentelemetry.io/contrib/bridges/otelzap" ) +type config struct { + provider log.LoggerProvider + scope instrumentation.Scope +} + +func newConfig(options []Option) config { + var c config + for _, opt := range options { + c = opt.apply(c) + } + + var emptyScope instrumentation.Scope + if c.scope == emptyScope { + c.scope = instrumentation.Scope{ + Name: bridgeName, + Version: version, + } + } + + if c.provider == nil { + c.provider = global.GetLoggerProvider() + } + + return c +} + +func (c config) logger() log.Logger { + var opts []log.LoggerOption + if c.scope.Version != "" { + opts = append(opts, log.WithInstrumentationVersion(c.scope.Version)) + } + if c.scope.SchemaURL != "" { + opts = append(opts, log.WithSchemaURL(c.scope.SchemaURL)) + } + return c.provider.Logger(c.scope.Name, opts...) +} + +// Option configures a [Core]. +type Option interface { + apply(config) config +} + +type optFunc func(config) config + +func (f optFunc) apply(c config) config { return f(c) } + +// WithInstrumentationScope returns an [Option] that configures the scope of +// the [log.Logger] used by a [Core]. +// +// By default if this Option is not provided, [Core] will use a default +// instrumentation scope describing this bridge package. It is recommended to +// provide this so log data can be associated with its source package or +// module. +func WithInstrumentationScope(scope instrumentation.Scope) Option { + return optFunc(func(c config) config { + c.scope = scope + return c + }) +} + +// WithLoggerProvider returns an [Option] that configures [log.LoggerProvider] +// used by a [Core] to create its [log.Logger]. +// +// By default if this Option is not provided, the Handler will use the global +// LoggerProvider. +func WithLoggerProvider(provider log.LoggerProvider) Option { + return optFunc(func(c config) config { + c.provider = provider + return c + }) +} + // Core is a [zapcore.Core] that sends logging records to OpenTelemetry. type Core struct { logger log.Logger diff --git a/bridges/otelzap/core_test.go b/bridges/otelzap/core_test.go index 5be764b98ad..9d41da03d20 100644 --- a/bridges/otelzap/core_test.go +++ b/bridges/otelzap/core_test.go @@ -27,7 +27,7 @@ func TestNewCoreConfiguration(t *testing.T) { require.IsType(t, &logtest.Recorder{}, h.logger) l := h.logger.(*logtest.Recorder) require.Len(t, l.Result(), 1) - + want := &logtest.ScopeRecords{Name: bridgeName, Version: version} got := l.Result()[0] assert.Equal(t, want, got)