github.com/ngocphuongnb/tetua@v0.0.7-alpha/packages/zaplogger/logger.go (about)

     1  package zapLogger
     2  
     3  import (
     4  	"log"
     5  	"os"
     6  	"path"
     7  	"time"
     8  
     9  	"github.com/ngocphuongnb/tetua/app/logger"
    10  	"go.uber.org/zap"
    11  	"go.uber.org/zap/zapcore"
    12  )
    13  
    14  type ZapLogger struct {
    15  	*zap.Logger
    16  	logger.Context
    17  }
    18  
    19  type Config struct {
    20  	Development bool `json:"development"`
    21  	LogFile     string
    22  }
    23  
    24  var loggerInstance *ZapLogger
    25  
    26  func New(config Config) *ZapLogger {
    27  	if config.LogFile != "" {
    28  		if err := os.MkdirAll(path.Dir(config.LogFile), 0755); err != nil {
    29  			log.Fatal(err)
    30  		}
    31  		logFile, err := os.OpenFile(config.LogFile, os.O_APPEND|os.O_CREATE|os.O_WRONLY, 0644)
    32  		if err != nil {
    33  			log.Fatal(err)
    34  		}
    35  
    36  		logFile.Close()
    37  	}
    38  	zapConfig := zap.NewProductionEncoderConfig()
    39  	// zapConfig.EncodeTime = zapcore.ISO8601TimeEncoder
    40  	zapConfig.EncodeTime = zapcore.TimeEncoderOfLayout(time.RFC3339Nano)
    41  	fileEncoder := zapcore.NewJSONEncoder(zapConfig)
    42  	consoleEncoder := zapcore.NewConsoleEncoder(zapConfig)
    43  	logFile, _ := os.OpenFile(config.LogFile, os.O_APPEND|os.O_CREATE|os.O_WRONLY, 0644)
    44  	writer := zapcore.AddSync(logFile)
    45  	defaultLogLevel := zapcore.DebugLevel
    46  	core := zapcore.NewTee(
    47  		zapcore.NewCore(fileEncoder, writer, defaultLogLevel),
    48  		zapcore.NewCore(consoleEncoder, zapcore.AddSync(os.Stdout), defaultLogLevel),
    49  	)
    50  
    51  	zapLogger := zap.New(
    52  		core,
    53  		zap.AddCaller(),
    54  		zap.AddCallerSkip(1),
    55  		zap.AddStacktrace(zapcore.ErrorLevel),
    56  	)
    57  
    58  	defer zapLogger.Sync()
    59  	return &ZapLogger{zapLogger, logger.Context{}}
    60  }
    61  
    62  func Get(context logger.Context) logger.Logger {
    63  	return &ZapLogger{loggerInstance.Logger, context}
    64  }
    65  
    66  func WithContext(contexts ...logger.Context) logger.Logger {
    67  	if len(contexts) > 0 {
    68  		return &ZapLogger{loggerInstance.Logger, contexts[0]}
    69  	}
    70  
    71  	return loggerInstance
    72  }
    73  
    74  func (l *ZapLogger) WithContext(context logger.Context) logger.Logger {
    75  	return &ZapLogger{l.Logger, context}
    76  }
    77  
    78  func (l *ZapLogger) Debug(params ...interface{}) {
    79  	msg, contexts := l.getLogContext(params...)
    80  	l.Logger.Debug(msg, getZapFields(contexts...)...)
    81  }
    82  
    83  func (l *ZapLogger) Info(params ...interface{}) {
    84  	msg, contexts := l.getLogContext(params...)
    85  	l.Logger.Info(msg, getZapFields(contexts...)...)
    86  }
    87  
    88  func (l *ZapLogger) Warn(params ...interface{}) {
    89  	msg, contexts := l.getLogContext(params...)
    90  	l.Logger.Warn(msg, getZapFields(contexts...)...)
    91  }
    92  
    93  func (l *ZapLogger) Error(params ...interface{}) {
    94  	msg, contexts := l.getLogContext(params...)
    95  	l.Logger.Error(msg, getZapFields(contexts...)...)
    96  }
    97  
    98  func (l *ZapLogger) DPanic(params ...interface{}) {
    99  	msg, contexts := l.getLogContext(params...)
   100  	l.Logger.DPanic(msg, getZapFields(contexts...)...)
   101  }
   102  
   103  func (l *ZapLogger) Panic(params ...interface{}) {
   104  	msg, contexts := l.getLogContext(params...)
   105  	l.Logger.Panic(msg, getZapFields(contexts...)...)
   106  }
   107  
   108  func (l *ZapLogger) Fatal(params ...interface{}) {
   109  	msg, contexts := l.getLogContext(params...)
   110  	l.Logger.Fatal(msg, getZapFields(contexts...)...)
   111  }
   112  
   113  func getZapFields(contexts ...logger.Context) []zapcore.Field {
   114  	var contextFields []zapcore.Field
   115  	for _, context := range contexts {
   116  		for key, val := range context {
   117  			// keyIndex := fmt.Sprintf("%d_%s", contexIndex, key)
   118  			keyIndex := key
   119  			contextFields = append(contextFields, zap.Any(keyIndex, val))
   120  		}
   121  	}
   122  	return contextFields
   123  }