Add zap encoding configurable

Json encoding is the default zap encoding value and can not be changeable.
This PR enables configuring zap encoding to console via new flag `log-format`.
dependabot/go_modules/go.uber.org/atomic-1.10.0
Arda Güçlü 2021-09-10 11:47:13 +03:00
parent 69015027b6
commit e647995a38
8 changed files with 85 additions and 2 deletions

View File

@ -28,3 +28,7 @@ See [code changes](https://github.com/etcd-io/etcd/compare/v3.5.0...v3.6.0).
- Package `mvcc/buckets` was moved to `storage/schema`
- Package `wal` was moved to `storage/wal`
- Package `datadir` was moved to `storage/datadir`
### etcd server
- Add [`etcd --log-format`](https://github.com/etcd-io/etcd/pull/13339) flag to support log format.

View File

@ -0,0 +1,31 @@
// Copyright 2019 The etcd Authors
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
package logutil
const (
JsonLogFormat = "json"
ConsoleLogFormat = "console"
)
var DefaultLogFormat = JsonLogFormat
// ConvertToZapFormat converts log level string to zapcore.Level.
func ConvertToZapFormat(format string) string {
if format == ConsoleLogFormat {
return format
}
return DefaultLogFormat
}

View File

@ -0,0 +1,35 @@
// Copyright 2019 The etcd Authors
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
package logutil
import "testing"
func TestLogFormat(t *testing.T) {
tests := []struct {
given string
want string
}{
{"json", JsonLogFormat},
{"console", ConsoleLogFormat},
{"", JsonLogFormat},
}
for i, tt := range tests {
got := ConvertToZapFormat(tt.given)
if got != tt.want {
t.Errorf("#%d: ConvertToZapFormat failure: want=%v, got=%v", i, tt.want, got)
}
}
}

View File

@ -31,7 +31,7 @@ var DefaultZapLoggerConfig = zap.Config{
Thereafter: 100,
},
Encoding: "json",
Encoding: ConvertToZapFormat(DefaultLogFormat),
// copied from "zap.NewProductionEncoderConfig" with some updates
EncoderConfig: zapcore.EncoderConfig{

View File

@ -361,6 +361,8 @@ type Config struct {
Logger string `json:"logger"`
// LogLevel configures log level. Only supports debug, info, warn, error, panic, or fatal. Default 'info'.
LogLevel string `json:"log-level"`
// LogFormat set log encoding. Only supports json, console. Default is 'json'.
LogFormat string `json:"log-format"`
// LogOutputs is either:
// - "default" as os.Stderr,
// - "stderr" as os.Stderr,

View File

@ -106,6 +106,7 @@ func (cfg *Config) setupLogging() error {
copied.ErrorOutputPaths = errOutputPaths
copied = logutil.MergeOutputPaths(copied)
copied.Level = zap.NewAtomicLevelAt(logutil.ConvertToZapLevel(cfg.LogLevel))
copied.Encoding = logutil.ConvertToZapFormat(cfg.LogFormat)
if cfg.ZapLoggerBuilder == nil {
lg, err := copied.Build()
if err != nil {
@ -130,10 +131,17 @@ func (cfg *Config) setupLogging() error {
lvl := zap.NewAtomicLevelAt(logutil.ConvertToZapLevel(cfg.LogLevel))
var encoder zapcore.Encoder
if logutil.ConvertToZapFormat(cfg.LogFormat) == logutil.ConsoleLogFormat {
encoder = zapcore.NewConsoleEncoder(logutil.DefaultZapLoggerConfig.EncoderConfig)
} else {
encoder = zapcore.NewJSONEncoder(logutil.DefaultZapLoggerConfig.EncoderConfig)
}
// WARN: do not change field names in encoder config
// journald logging writer assumes field names of "level" and "caller"
cr := zapcore.NewCore(
zapcore.NewJSONEncoder(logutil.DefaultZapLoggerConfig.EncoderConfig),
encoder,
syncer,
lvl,
)

View File

@ -247,6 +247,7 @@ func newConfig() *config {
fs.StringVar(&cfg.ec.Logger, "logger", "zap", "Currently only supports 'zap' for structured logging.")
fs.Var(flags.NewUniqueStringsValue(embed.DefaultLogOutput), "log-outputs", "Specify 'stdout' or 'stderr' to skip journald logging even when running under systemd, or list of comma separated output targets.")
fs.StringVar(&cfg.ec.LogLevel, "log-level", logutil.DefaultLogLevel, "Configures log level. Only supports debug, info, warn, error, panic, or fatal. Default 'info'.")
fs.StringVar(&cfg.ec.LogFormat, "log-format", logutil.DefaultLogFormat, "Configures log format. Only supports json, console. Default is 'json'.")
fs.BoolVar(&cfg.ec.EnableLogRotation, "enable-log-rotation", false, "Enable log rotation of a single log-outputs file target.")
fs.StringVar(&cfg.ec.LogRotationConfigJSON, "log-rotation-config-json", embed.DefaultLogRotationConfig, "Configures log rotation if enabled with a JSON logger config. Default: MaxSize=100(MB), MaxAge=0(days,no limit), MaxBackups=0(no limit), LocalTime=false(UTC), Compress=false(gzip)")

View File

@ -196,6 +196,8 @@ Logging:
Specify 'stdout' or 'stderr' to skip journald logging even when running under systemd, or list of comma separated output targets.
--log-level 'info'
Configures log level. Only supports debug, info, warn, error, panic, or fatal.
--log-format 'json'
Configures log format. Only supports json, console.
--enable-log-rotation 'false'
Enable log rotation of a single log-outputs file target.
--log-rotation-config-json '{"maxsize": 100, "maxage": 0, "maxbackups": 0, "localtime": false, "compress": false}'