| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115 | package logimport (	"github.com/gin-gonic/gin"	"github.com/spf13/viper"	"go.uber.org/zap"	"go.uber.org/zap/zapcore"	"gopkg.in/natefinch/lumberjack.v2"	"os"	"time")const LOGGER_KEY = "zapLogger"type Logger struct {	*zap.Logger}func NewLog(conf *viper.Viper) *Logger {	return initZap(conf)}func initZap(conf *viper.Viper) *Logger {	// 日志地址 "out.log" 自定义	lp := conf.GetString("log.log_file_name")	// 日志级别 DEBUG,ERROR, INFO	lv := conf.GetString("log.log_level")	var level zapcore.Level	//debug<info<warn<error<fatal<panic	switch lv {	case "debug":		level = zap.DebugLevel	case "info":		level = zap.InfoLevel	case "warn":		level = zap.WarnLevel	case "error":		level = zap.ErrorLevel	default:		level = zap.InfoLevel	}	hook := lumberjack.Logger{		Filename:   lp,                             // 日志文件路径		MaxSize:    conf.GetInt("log.max_size"),    // 每个日志文件保存的最大尺寸 单位:M		MaxBackups: conf.GetInt("log.max_backups"), // 日志文件最多保存多少个备份		MaxAge:     conf.GetInt("log.max_age"),     // 文件最多保存多少天		Compress:   conf.GetBool("log.compress"),   // 是否压缩	}	var encoder zapcore.Encoder	if conf.GetString("log.encoding") == "console" {		encoder = zapcore.NewConsoleEncoder(zapcore.EncoderConfig{			TimeKey:        "ts",			LevelKey:       "level",			NameKey:        "Logger",			CallerKey:      "caller",			MessageKey:     "msg",			StacktraceKey:  "stacktrace",			LineEnding:     zapcore.DefaultLineEnding,			EncodeLevel:    zapcore.LowercaseColorLevelEncoder,			EncodeTime:     timeEncoder,			EncodeDuration: zapcore.SecondsDurationEncoder,			EncodeCaller:   zapcore.FullCallerEncoder,		})	} else {		encoder = zapcore.NewJSONEncoder(zapcore.EncoderConfig{			TimeKey:        "ts",			LevelKey:       "level",			NameKey:        "logger",			CallerKey:      "caller",			FunctionKey:    zapcore.OmitKey,			MessageKey:     "msg",			StacktraceKey:  "stacktrace",			LineEnding:     zapcore.DefaultLineEnding,			EncodeLevel:    zapcore.LowercaseLevelEncoder,			EncodeTime:     zapcore.EpochTimeEncoder,			EncodeDuration: zapcore.SecondsDurationEncoder,			EncodeCaller:   zapcore.ShortCallerEncoder,		})	}	core := zapcore.NewCore(		encoder, // 编码器配置		zapcore.NewMultiWriteSyncer(zapcore.AddSync(os.Stdout), zapcore.AddSync(&hook)), // 打印到控制台和文件		level, // 日志级别	)	if conf.GetString("env") != "prod" {		return &Logger{zap.New(core, zap.Development(), zap.AddCaller(), zap.AddStacktrace(zap.ErrorLevel))}	}	return &Logger{zap.New(core, zap.AddCaller(), zap.AddStacktrace(zap.ErrorLevel))}}// 自定义时间编码器func timeEncoder(t time.Time, enc zapcore.PrimitiveArrayEncoder) {	//enc.AppendString(t.Format("2006-01-02 15:04:05"))	enc.AppendString(t.Format("2006-01-02 15:04:05.000000000"))}// NewContext 给指定的context添加字段func (l *Logger) NewContext(ctx *gin.Context, fields ...zapcore.Field) {	ctx.Set(LOGGER_KEY, l.WithContext(ctx).With(fields...))}// WithContext 从指定的context返回一个zap实例func (l *Logger) WithContext(ctx *gin.Context) *Logger {	if ctx == nil {		return l	}	zl, _ := ctx.Get(LOGGER_KEY)	ctxLogger, ok := zl.(*zap.Logger)	if ok {		return &Logger{ctxLogger}	}	return l}
 |