Add the ability to capture the logger caller file and line number
Fixes #34, #22
This commit is contained in:
parent
fcbdf23e9e
commit
27e0a22cbc
14
context.go
14
context.go
@ -302,3 +302,17 @@ func (c Context) Interface(key string, i interface{}) Context {
|
||||
c.l.context = json.AppendInterface(json.AppendKey(c.l.context, key), i)
|
||||
return c
|
||||
}
|
||||
|
||||
type callerHook struct{}
|
||||
|
||||
func (ch callerHook) Run(e *Event, level Level, msg string) {
|
||||
e.caller(4)
|
||||
}
|
||||
|
||||
var ch = callerHook{}
|
||||
|
||||
// Caller adds the file:line of the caller with the zerolog.CallerFieldName key.
|
||||
func (c Context) Caller() Context {
|
||||
c.l = c.l.Hook(ch)
|
||||
return c
|
||||
}
|
||||
|
19
event.go
19
event.go
@ -4,6 +4,8 @@ import (
|
||||
"fmt"
|
||||
"io/ioutil"
|
||||
"os"
|
||||
"runtime"
|
||||
"strconv"
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
@ -561,3 +563,20 @@ func (e *Event) Interface(key string, i interface{}) *Event {
|
||||
e.buf = json.AppendInterface(json.AppendKey(e.buf, key), i)
|
||||
return e
|
||||
}
|
||||
|
||||
// Caller adds the file:line of the caller with the zerolog.CallerFieldName key.
|
||||
func (e *Event) Caller() *Event {
|
||||
return e.caller(2)
|
||||
}
|
||||
|
||||
func (e *Event) caller(skip int) *Event {
|
||||
if e == nil {
|
||||
return e
|
||||
}
|
||||
_, file, line, ok := runtime.Caller(skip)
|
||||
if !ok {
|
||||
return e
|
||||
}
|
||||
e.buf = json.AppendString(json.AppendKey(e.buf, CallerFieldName), file+":"+strconv.Itoa(line))
|
||||
return e
|
||||
}
|
||||
|
@ -16,6 +16,9 @@ var (
|
||||
// ErrorFieldName is the field name used for error fields.
|
||||
ErrorFieldName = "error"
|
||||
|
||||
// CallerFieldName is the field name used for caller field.
|
||||
CallerFieldName = "caller"
|
||||
|
||||
// TimeFieldFormat defines the time format of the Time field type.
|
||||
// If set to an empty string, the time is formatted as an UNIX timestamp
|
||||
// as integer.
|
||||
|
17
log_test.go
17
log_test.go
@ -3,7 +3,9 @@ package zerolog
|
||||
import (
|
||||
"bytes"
|
||||
"errors"
|
||||
"fmt"
|
||||
"reflect"
|
||||
"runtime"
|
||||
"testing"
|
||||
"time"
|
||||
)
|
||||
@ -74,7 +76,7 @@ func TestInfo(t *testing.T) {
|
||||
|
||||
func TestWith(t *testing.T) {
|
||||
out := &bytes.Buffer{}
|
||||
log := New(out).With().
|
||||
ctx := New(out).With().
|
||||
Str("foo", "bar").
|
||||
AnErr("some_err", nil).
|
||||
Err(errors.New("some error")).
|
||||
@ -91,10 +93,12 @@ func TestWith(t *testing.T) {
|
||||
Uint64("uint64", 10).
|
||||
Float32("float32", 11).
|
||||
Float64("float64", 12).
|
||||
Time("time", time.Time{}).
|
||||
Logger()
|
||||
Time("time", time.Time{})
|
||||
_, file, line, _ := runtime.Caller(0)
|
||||
caller := fmt.Sprintf("%s:%d", file, line+3)
|
||||
log := ctx.Caller().Logger()
|
||||
log.Log().Msg("")
|
||||
if got, want := out.String(), `{"foo":"bar","error":"some error","bool":true,"int":1,"int8":2,"int16":3,"int32":4,"int64":5,"uint":6,"uint8":7,"uint16":8,"uint32":9,"uint64":10,"float32":11,"float64":12,"time":"0001-01-01T00:00:00Z"}`+"\n"; got != want {
|
||||
if got, want := out.String(), `{"foo":"bar","error":"some error","bool":true,"int":1,"int8":2,"int16":3,"int32":4,"int64":5,"uint":6,"uint8":7,"uint16":8,"uint32":9,"uint64":10,"float32":11,"float64":12,"time":"0001-01-01T00:00:00Z","caller":"`+caller+`"}`+"\n"; got != want {
|
||||
t.Errorf("invalid log output:\ngot: %v\nwant: %v", got, want)
|
||||
}
|
||||
}
|
||||
@ -132,7 +136,10 @@ func TestFields(t *testing.T) {
|
||||
out := &bytes.Buffer{}
|
||||
log := New(out)
|
||||
now := time.Now()
|
||||
_, file, line, _ := runtime.Caller(0)
|
||||
caller := fmt.Sprintf("%s:%d", file, line+3)
|
||||
log.Log().
|
||||
Caller().
|
||||
Str("string", "foo").
|
||||
Bytes("bytes", []byte("bar")).
|
||||
AnErr("some_err", nil).
|
||||
@ -154,7 +161,7 @@ func TestFields(t *testing.T) {
|
||||
Time("time", time.Time{}).
|
||||
TimeDiff("diff", now, now.Add(-10*time.Second)).
|
||||
Msg("")
|
||||
if got, want := out.String(), `{"string":"foo","bytes":"bar","error":"some error","bool":true,"int":1,"int8":2,"int16":3,"int32":4,"int64":5,"uint":6,"uint8":7,"uint16":8,"uint32":9,"uint64":10,"float32":11,"float64":12,"dur":1000,"time":"0001-01-01T00:00:00Z","diff":10000}`+"\n"; got != want {
|
||||
if got, want := out.String(), `{"caller":"`+caller+`","string":"foo","bytes":"bar","error":"some error","bool":true,"int":1,"int8":2,"int16":3,"int32":4,"int64":5,"uint":6,"uint8":7,"uint16":8,"uint32":9,"uint64":10,"float32":11,"float64":12,"dur":1000,"time":"0001-01-01T00:00:00Z","diff":10000}`+"\n"; got != want {
|
||||
t.Errorf("invalid log output:\ngot: %v\nwant: %v", got, want)
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user