mirror of
https://github.com/zeromicro/go-zero.git
synced 2026-05-07 15:10:01 +08:00
feat: support customize of log keys (#5103)
This commit is contained in:
@@ -44,4 +44,25 @@ type LogConf struct {
|
||||
Rotation string `json:",default=daily,options=[daily,size]"`
|
||||
// FileTimeFormat represents the time format for file name, default is `2006-01-02T15:04:05.000Z07:00`.
|
||||
FileTimeFormat string `json:",optional"`
|
||||
// LogKey represents the log key.
|
||||
LogKey logKeyConf `json:",optional"`
|
||||
}
|
||||
|
||||
type logKeyConf struct {
|
||||
// CallerKey represents the caller key.
|
||||
CallerKey string `json:",default=caller"`
|
||||
// ContentKey represents the content key.
|
||||
ContentKey string `json:",default=content"`
|
||||
// DurationKey represents the duration key.
|
||||
DurationKey string `json:",default=duration"`
|
||||
// LevelKey represents the level key.
|
||||
LevelKey string `json:",default=level"`
|
||||
// SpanKey represents the span key.
|
||||
SpanKey string `json:",default=span"`
|
||||
// TimestampKey represents the timestamp key.
|
||||
TimestampKey string `json:",default=@timestamp"`
|
||||
// TraceKey represents the trace key.
|
||||
TraceKey string `json:",default=trace"`
|
||||
// TruncatedKey represents the truncated key.
|
||||
TruncatedKey string `json:",default=truncated"`
|
||||
}
|
||||
|
||||
@@ -277,6 +277,7 @@ func SetUp(c LogConf) (err error) {
|
||||
// Need to wait for the first caller to complete the execution.
|
||||
setupOnce.Do(func() {
|
||||
setupLogLevel(c)
|
||||
setupLogKey(c.LogKey)
|
||||
|
||||
if !c.Stat {
|
||||
DisableStat()
|
||||
@@ -579,3 +580,30 @@ func writeStack(msg string) {
|
||||
func writeStat(msg string) {
|
||||
getWriter().Stat(msg, mergeGlobalFields(addCaller())...)
|
||||
}
|
||||
|
||||
func setupLogKey(c logKeyConf) {
|
||||
if c.CallerKey != "" {
|
||||
callerKey = c.CallerKey
|
||||
}
|
||||
if c.ContentKey != "" {
|
||||
contentKey = c.ContentKey
|
||||
}
|
||||
if c.DurationKey != "" {
|
||||
durationKey = c.DurationKey
|
||||
}
|
||||
if c.LevelKey != "" {
|
||||
levelKey = c.LevelKey
|
||||
}
|
||||
if c.SpanKey != "" {
|
||||
spanKey = c.SpanKey
|
||||
}
|
||||
if c.TimestampKey != "" {
|
||||
timestampKey = c.TimestampKey
|
||||
}
|
||||
if c.TraceKey != "" {
|
||||
traceKey = c.TraceKey
|
||||
}
|
||||
if c.TruncatedKey != "" {
|
||||
truncatedKey = c.TruncatedKey
|
||||
}
|
||||
}
|
||||
|
||||
@@ -17,6 +17,8 @@ import (
|
||||
"time"
|
||||
|
||||
"github.com/stretchr/testify/assert"
|
||||
"go.opentelemetry.io/otel"
|
||||
sdktrace "go.opentelemetry.io/otel/sdk/trace"
|
||||
)
|
||||
|
||||
var (
|
||||
@@ -1157,3 +1159,66 @@ func (s *countingStringer) String() string {
|
||||
atomic.AddInt32(&s.count, 1)
|
||||
return "countingStringer"
|
||||
}
|
||||
|
||||
func TestLogKey(t *testing.T) {
|
||||
setupOnce = sync.Once{}
|
||||
MustSetup(LogConf{
|
||||
ServiceName: "any",
|
||||
Mode: "console",
|
||||
Encoding: "json",
|
||||
TimeFormat: timeFormat,
|
||||
LogKey: logKeyConf{
|
||||
CallerKey: "_caller",
|
||||
ContentKey: "_content",
|
||||
DurationKey: "_duration",
|
||||
LevelKey: "_level",
|
||||
SpanKey: "_span",
|
||||
TimestampKey: "_timestamp",
|
||||
TraceKey: "_trace",
|
||||
TruncatedKey: "_truncated",
|
||||
},
|
||||
})
|
||||
|
||||
t.Cleanup(func() {
|
||||
setupLogKey(logKeyConf{
|
||||
CallerKey: defaultCallerKey,
|
||||
ContentKey: defaultContentKey,
|
||||
DurationKey: defaultDurationKey,
|
||||
LevelKey: defaultLevelKey,
|
||||
SpanKey: defaultSpanKey,
|
||||
TimestampKey: defaultTimestampKey,
|
||||
TraceKey: defaultTraceKey,
|
||||
TruncatedKey: defaultTruncatedKey,
|
||||
})
|
||||
})
|
||||
|
||||
const message = "hello there"
|
||||
w := new(mockWriter)
|
||||
old := writer.Swap(w)
|
||||
defer writer.Store(old)
|
||||
|
||||
otp := otel.GetTracerProvider()
|
||||
tp := sdktrace.NewTracerProvider(sdktrace.WithSampler(sdktrace.AlwaysSample()))
|
||||
otel.SetTracerProvider(tp)
|
||||
defer otel.SetTracerProvider(otp)
|
||||
|
||||
ctx, span := tp.Tracer("trace-id").Start(context.Background(), "span-id")
|
||||
defer span.End()
|
||||
|
||||
WithContext(ctx).WithDuration(time.Second).Info(message)
|
||||
now := time.Now()
|
||||
|
||||
var m map[string]string
|
||||
if err := json.Unmarshal([]byte(w.String()), &m); err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
assert.Equal(t, "info", m["_level"])
|
||||
assert.Equal(t, message, m["_content"])
|
||||
assert.Equal(t, "1000.0ms", m["_duration"])
|
||||
assert.Regexp(t, `logx/logs_test.go:\d+`, m["_caller"])
|
||||
assert.NotEmpty(t, m["_trace"])
|
||||
assert.NotEmpty(t, m["_span"])
|
||||
parsedTime, err := time.Parse(timeFormat, m["_timestamp"])
|
||||
assert.True(t, err == nil)
|
||||
assert.Equal(t, now.Minute(), parsedTime.Minute())
|
||||
}
|
||||
|
||||
@@ -53,14 +53,25 @@ const (
|
||||
)
|
||||
|
||||
const (
|
||||
callerKey = "caller"
|
||||
contentKey = "content"
|
||||
durationKey = "duration"
|
||||
levelKey = "level"
|
||||
spanKey = "span"
|
||||
timestampKey = "@timestamp"
|
||||
traceKey = "trace"
|
||||
truncatedKey = "truncated"
|
||||
defaultCallerKey = "caller"
|
||||
defaultContentKey = "content"
|
||||
defaultDurationKey = "duration"
|
||||
defaultLevelKey = "level"
|
||||
defaultSpanKey = "span"
|
||||
defaultTimestampKey = "@timestamp"
|
||||
defaultTraceKey = "trace"
|
||||
defaultTruncatedKey = "truncated"
|
||||
)
|
||||
|
||||
var (
|
||||
callerKey = defaultCallerKey
|
||||
contentKey = defaultContentKey
|
||||
durationKey = defaultDurationKey
|
||||
levelKey = defaultLevelKey
|
||||
spanKey = defaultSpanKey
|
||||
timestampKey = defaultTimestampKey
|
||||
traceKey = defaultTraceKey
|
||||
truncatedKey = defaultTruncatedKey
|
||||
)
|
||||
|
||||
var (
|
||||
|
||||
Reference in New Issue
Block a user