Skip to content

Commit

Permalink
Migrate zap to use zapcore
Browse files Browse the repository at this point in the history
Migrate zap to use the new zapcore package, dropping all references to the `spy`
and `spywrite` packages along the way. This collects most types and functions
relevant to zap's end users in the base package.
  • Loading branch information
Akshay Shah committed Feb 15, 2017
1 parent 6bd8382 commit 5c9ffae
Show file tree
Hide file tree
Showing 43 changed files with 707 additions and 4,296 deletions.
55 changes: 0 additions & 55 deletions benchmarks/logrus_bench_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,11 +25,7 @@ import (
"testing"
"time"

"go.uber.org/zap"
"go.uber.org/zap/zbark"

"github.com/Sirupsen/logrus"
"github.com/uber-common/bark"
)

func newLogrus() *logrus.Logger {
Expand Down Expand Up @@ -62,31 +58,6 @@ func BenchmarkLogrusAddingFields(b *testing.B) {
})
}

func BenchmarkZapBarkifyAddingFields(b *testing.B) {
logger := zbark.Barkify(zap.New(zap.WriterFacility(
zap.NewJSONEncoder(),
zap.Discard,
zap.DebugLevel,
)))
b.ResetTimer()
b.RunParallel(func(pb *testing.PB) {
for pb.Next() {
logger.WithFields(bark.Fields{
"int": 1,
"int64": int64(1),
"float": 3.0,
"string": "four!",
"bool": true,
"time": time.Unix(0, 0),
"error": errExample.Error(),
"duration": time.Second,
"user-defined type": _jane,
"another string": "done!",
}).Info("Go fast.")
}
})
}

func BenchmarkLogrusWithAccumulatedContext(b *testing.B) {
baseLogger := newLogrus()
logger := baseLogger.WithFields(logrus.Fields{
Expand All @@ -109,32 +80,6 @@ func BenchmarkLogrusWithAccumulatedContext(b *testing.B) {
})
}

func BenchmarkZapBarkifyWithAccumulatedContext(b *testing.B) {
baseLogger := zbark.Barkify(zap.New(zap.WriterFacility(
zap.NewJSONEncoder(),
zap.Discard,
zap.DebugLevel,
)))
logger := baseLogger.WithFields(bark.Fields{
"int": 1,
"int64": int64(1),
"float": 3.0,
"string": "four!",
"bool": true,
"time": time.Unix(0, 0),
"error": errExample.Error(),
"duration": time.Second,
"user-defined type": _jane,
"another string": "done!",
})
b.ResetTimer()
b.RunParallel(func(pb *testing.PB) {
for pb.Next() {
logger.Info("Go really fast.")
}
})
}

func BenchmarkLogrusWithoutFields(b *testing.B) {
logger := newLogrus()
b.ResetTimer()
Expand Down
32 changes: 16 additions & 16 deletions benchmarks/stdlib_bench_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,9 +24,7 @@ import (
"io/ioutil"
"log"
"testing"

"go.uber.org/zap"
"go.uber.org/zap/zwrap"
"time"
)

func BenchmarkStandardLibraryWithoutFields(b *testing.B) {
Expand All @@ -39,22 +37,24 @@ func BenchmarkStandardLibraryWithoutFields(b *testing.B) {
})
}

func BenchmarkZapStandardizeWithoutFields(b *testing.B) {
logger, err := zwrap.Standardize(
zap.New(zap.WriterFacility(
zap.NewJSONEncoder(),
zap.Discard,
zap.DebugLevel,
)),
zap.InfoLevel,
)
if err != nil {
panic("Failed to Standardize a zap.Logger.")
}
func BenchmarkStandardLibraryWithFormatting(b *testing.B) {
logger := log.New(ioutil.Discard, "", log.LstdFlags)
b.ResetTimer()
b.RunParallel(func(pb *testing.PB) {
for pb.Next() {
logger.Println("Go fast.")
logger.Printf(
"Go fast. %v %v %v %s %v %v %v %v %v %s\n",
1,
int64(1),
3.0,
"four!",
true,
time.Unix(0, 0),
errExample,
time.Second,
_jane,
"done!",
)
}
})
}
102 changes: 61 additions & 41 deletions benchmarks/zap_bench_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,8 @@ import (
"time"

"go.uber.org/zap"
"go.uber.org/zap/zwrap"
"go.uber.org/zap/testutils"
"go.uber.org/zap/zapcore"
)

var errExample = errors.New("fail")
Expand All @@ -38,10 +39,10 @@ type user struct {
CreatedAt time.Time `json:"created_at"`
}

func (u user) MarshalLog(kv zap.KeyValue) error {
kv.AddString("name", u.Name)
kv.AddString("email", u.Email)
kv.AddInt64("created_at", u.CreatedAt.UnixNano())
func (u user) MarshalLogObject(enc zapcore.ObjectEncoder) error {
enc.AddString("name", u.Name)
enc.AddString("email", u.Email)
enc.AddInt64("created_at", u.CreatedAt.UnixNano())
return nil
}

Expand All @@ -51,8 +52,27 @@ var _jane = user{
CreatedAt: time.Date(1980, 1, 1, 12, 0, 0, 0, time.UTC),
}

func fakeFields() []zap.Field {
return []zap.Field{
// TODO: remove this when we figure out a new config & options story.
func benchEncoder() zapcore.Encoder {
msgF := func(msg string) zapcore.Field {
return zapcore.Field{Type: zapcore.StringType, String: msg, Key: "msg"}
}
timeF := func(t time.Time) zapcore.Field {
millis := t.UnixNano() / int64(time.Millisecond)
return zapcore.Field{Type: zapcore.Int64Type, Integer: millis, Key: "ts"}
}
levelF := func(l zapcore.Level) zapcore.Field {
return zapcore.Field{Type: zapcore.StringType, String: l.String(), Key: "level"}
}
return zapcore.NewJSONEncoder(zapcore.JSONConfig{
MessageFormatter: msgF,
TimeFormatter: timeF,
LevelFormatter: levelF,
})
}

func fakeFields() []zapcore.Field {
return []zapcore.Field{
zap.Int("int", 1),
zap.Int64("int64", 2),
zap.Float64("float", 3.0),
Expand All @@ -61,7 +81,7 @@ func fakeFields() []zap.Field {
zap.Time("time", time.Unix(0, 0)),
zap.Error(errExample),
zap.Duration("duration", time.Second),
zap.Marshaler("user-defined type", _jane),
zap.Object("user-defined type", _jane),
zap.String("another string", "done!"),
}
}
Expand All @@ -75,9 +95,9 @@ func fakeMessages(n int) []string {
}

func BenchmarkZapDisabledLevelsWithoutFields(b *testing.B) {
logger := zap.New(zap.WriterFacility(
zap.NewJSONEncoder(),
zap.Discard,
logger := zap.New(zapcore.WriterFacility(
benchEncoder(),
&testutils.Discarder{},
zap.ErrorLevel,
))
b.ResetTimer()
Expand All @@ -91,9 +111,9 @@ func BenchmarkZapDisabledLevelsWithoutFields(b *testing.B) {
func BenchmarkZapDisabledLevelsAccumulatedContext(b *testing.B) {
context := fakeFields()
logger := zap.New(
zap.WriterFacility(
zap.NewJSONEncoder(),
zap.Discard,
zapcore.WriterFacility(
benchEncoder(),
&testutils.Discarder{},
zap.ErrorLevel,
),
zap.Fields(context...),
Expand All @@ -107,9 +127,9 @@ func BenchmarkZapDisabledLevelsAccumulatedContext(b *testing.B) {
}

func BenchmarkZapDisabledLevelsAddingFields(b *testing.B) {
logger := zap.New(zap.WriterFacility(
zap.NewJSONEncoder(),
zap.Discard,
logger := zap.New(zapcore.WriterFacility(
benchEncoder(),
&testutils.Discarder{},
zap.ErrorLevel,
))
b.ResetTimer()
Expand All @@ -121,9 +141,9 @@ func BenchmarkZapDisabledLevelsAddingFields(b *testing.B) {
}

func BenchmarkZapDisabledLevelsCheckAddingFields(b *testing.B) {
logger := zap.New(zap.WriterFacility(
zap.NewJSONEncoder(),
zap.Discard,
logger := zap.New(zapcore.WriterFacility(
benchEncoder(),
&testutils.Discarder{},
zap.ErrorLevel,
))
b.ResetTimer()
Expand All @@ -137,9 +157,9 @@ func BenchmarkZapDisabledLevelsCheckAddingFields(b *testing.B) {
}

func BenchmarkZapAddingFields(b *testing.B) {
logger := zap.New(zap.WriterFacility(
zap.NewJSONEncoder(),
zap.Discard,
logger := zap.New(zapcore.WriterFacility(
benchEncoder(),
&testutils.Discarder{},
zap.DebugLevel,
))
b.ResetTimer()
Expand All @@ -153,9 +173,9 @@ func BenchmarkZapAddingFields(b *testing.B) {
func BenchmarkZapWithAccumulatedContext(b *testing.B) {
context := fakeFields()
logger := zap.New(
zap.WriterFacility(
zap.NewJSONEncoder(),
zap.Discard,
zapcore.WriterFacility(
benchEncoder(),
&testutils.Discarder{},
zap.DebugLevel,
),
zap.Fields(context...),
Expand All @@ -169,9 +189,9 @@ func BenchmarkZapWithAccumulatedContext(b *testing.B) {
}

func BenchmarkZapWithoutFields(b *testing.B) {
logger := zap.New(zap.WriterFacility(
zap.NewJSONEncoder(),
zap.Discard,
logger := zap.New(zapcore.WriterFacility(
benchEncoder(),
&testutils.Discarder{},
zap.DebugLevel,
))
b.ResetTimer()
Expand All @@ -184,9 +204,9 @@ func BenchmarkZapWithoutFields(b *testing.B) {

func BenchmarkZapSampleWithoutFields(b *testing.B) {
messages := fakeMessages(1000)
logger := zap.New(zwrap.Sample(zap.WriterFacility(
zap.NewJSONEncoder(),
zap.Discard,
logger := zap.New(zapcore.Sample(zapcore.WriterFacility(
benchEncoder(),
&testutils.Discarder{},
zap.DebugLevel,
), time.Second, 10, 10000))
b.ResetTimer()
Expand All @@ -201,9 +221,9 @@ func BenchmarkZapSampleWithoutFields(b *testing.B) {

func BenchmarkZapSampleAddingFields(b *testing.B) {
messages := fakeMessages(1000)
logger := zap.New(zwrap.Sample(zap.WriterFacility(
zap.NewJSONEncoder(),
zap.Discard,
logger := zap.New(zapcore.Sample(zapcore.WriterFacility(
benchEncoder(),
&testutils.Discarder{},
zap.DebugLevel,
), time.Second, 10, 10000))
b.ResetTimer()
Expand All @@ -218,9 +238,9 @@ func BenchmarkZapSampleAddingFields(b *testing.B) {

func BenchmarkZapSampleCheckWithoutFields(b *testing.B) {
messages := fakeMessages(1000)
logger := zap.New(zwrap.Sample(zap.WriterFacility(
zap.NewJSONEncoder(),
zap.Discard,
logger := zap.New(zapcore.Sample(zapcore.WriterFacility(
benchEncoder(),
&testutils.Discarder{},
zap.DebugLevel,
), time.Second, 10, 10000))
b.ResetTimer()
Expand All @@ -237,9 +257,9 @@ func BenchmarkZapSampleCheckWithoutFields(b *testing.B) {

func BenchmarkZapSampleCheckAddingFields(b *testing.B) {
messages := fakeMessages(1000)
logger := zap.New(zwrap.Sample(zap.WriterFacility(
zap.NewJSONEncoder(),
zap.Discard,
logger := zap.New(zapcore.Sample(zapcore.WriterFacility(
benchEncoder(),
&testutils.Discarder{},
zap.DebugLevel,
), time.Second, 10, 10000))
b.ResetTimer()
Expand Down
46 changes: 7 additions & 39 deletions common_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -21,54 +21,22 @@
package zap

import (
"os"
"sync"
"testing"

"github.com/stretchr/testify/assert"
"go.uber.org/zap/zapcore"
)

func opts(opts ...Option) []Option {
return opts
}

type stubbedExit struct {
Status *int
}

func (se *stubbedExit) Unstub() {
_exit = os.Exit
}

func (se *stubbedExit) AssertNoExit(t testing.TB) {
assert.Nil(t, se.Status, "Unexpected exit.")
}

func (se *stubbedExit) AssertStatus(t testing.TB, expected int) {
if assert.NotNil(t, se.Status, "Expected to exit.") {
assert.Equal(t, expected, *se.Status, "Unexpected exit code.")
}
}

func stubExit() *stubbedExit {
stub := &stubbedExit{}
_exit = func(s int) { stub.Status = &s }
return stub
}

func withJSONLogger(t testing.TB, enab LevelEnabler, opts []Option, f func(Logger, *testBuffer)) {
sink := &testBuffer{}
errSink := &testBuffer{}

allOpts := make([]Option, 0, 2+len(opts))
allOpts = append(allOpts, ErrorOutput(errSink))
allOpts = append(allOpts, opts...)
logger := New(
WriterFacility(newJSONEncoder(NoTime()), sink, enab),
allOpts...)

f(logger, sink)
assert.Empty(t, errSink.String(), "Expected error sink to be empty.")
// Here specifically to introduce an easily-identifiable filename for testing
// stacktraces and caller skips.
func withLogger(t testing.TB, e zapcore.LevelEnabler, opts []Option, f func(Logger, *zapcore.ObservedLogs)) {
fac, logs := zapcore.NewObserver(e, 1024)
log := New(fac, opts...)
f(log, logs)
}

func runConcurrently(goroutines, iterations int, wg *sync.WaitGroup, f func()) {
Expand Down
Loading

0 comments on commit 5c9ffae

Please sign in to comment.