151 lines
3.3 KiB
Go
151 lines
3.3 KiB
Go
package logpackage
|
|
|
|
import (
|
|
"context"
|
|
"fmt"
|
|
"os"
|
|
"path/filepath"
|
|
"runtime"
|
|
"sync"
|
|
"time"
|
|
|
|
"github.com/rs/zerolog"
|
|
"gopkg.in/natefinch/lumberjack.v2"
|
|
"gopkg.in/yaml.v2"
|
|
)
|
|
|
|
type LoggerConfig struct {
|
|
Level string `yaml:"level"`
|
|
FilePath string `yaml:"file_path"`
|
|
MaxSize int `yaml:"max_size"`
|
|
MaxBackups int `yaml:"max_backups"`
|
|
MaxAge int `yaml:"max_age"`
|
|
ContextKeys []string `yaml:"context_keys"`
|
|
}
|
|
|
|
var (
|
|
logger zerolog.Logger
|
|
cfg LoggerConfig
|
|
once sync.Once
|
|
|
|
getConfigPath = func() (string, error) {
|
|
_, file, _, ok := runtime.Caller(0)
|
|
if !ok {
|
|
return "", fmt.Errorf("failed to get runtime caller")
|
|
}
|
|
dir := filepath.Dir(file)
|
|
return filepath.Join(dir, "log.yaml"), nil
|
|
}
|
|
)
|
|
|
|
func loadConfig() (LoggerConfig, error) {
|
|
var config LoggerConfig
|
|
|
|
configPath, err := getConfigPath()
|
|
if err != nil {
|
|
return config, fmt.Errorf("error finding config path: %w", err)
|
|
}
|
|
|
|
data, err := os.ReadFile(configPath)
|
|
if err != nil {
|
|
return config, fmt.Errorf("failed to read config file: %w", err)
|
|
}
|
|
|
|
err = yaml.Unmarshal(data, &config)
|
|
if err != nil {
|
|
return config, fmt.Errorf("failed to parse YAML: %w", err)
|
|
}
|
|
|
|
return config, nil
|
|
}
|
|
|
|
func InitLogger(configs ...LoggerConfig) {
|
|
once.Do(func() {
|
|
var err error
|
|
|
|
if len(configs) > 0 {
|
|
cfg = configs[0]
|
|
} else {
|
|
cfg, err = loadConfig()
|
|
if err != nil {
|
|
fmt.Println("Logger initialization failed:", err)
|
|
return
|
|
}
|
|
}
|
|
|
|
level, err := zerolog.ParseLevel(cfg.Level)
|
|
if err != nil {
|
|
level = zerolog.InfoLevel
|
|
}
|
|
|
|
zerolog.SetGlobalLevel(level)
|
|
zerolog.TimeFieldFormat = time.RFC3339
|
|
|
|
logWriter := zerolog.ConsoleWriter{Out: os.Stdout, TimeFormat: time.RFC3339}
|
|
fileWriter := &lumberjack.Logger{
|
|
Filename: cfg.FilePath,
|
|
MaxSize: cfg.MaxSize,
|
|
MaxBackups: cfg.MaxBackups,
|
|
MaxAge: cfg.MaxAge,
|
|
}
|
|
|
|
multi := zerolog.MultiLevelWriter(logWriter, fileWriter)
|
|
logger = zerolog.New(multi).With().Timestamp().Logger()
|
|
})
|
|
}
|
|
|
|
func Debug(ctx context.Context, msg string) {
|
|
logEvent(ctx, logger.Debug(), msg)
|
|
}
|
|
|
|
func Debugf(ctx context.Context, format string, v ...any) {
|
|
logEvent(ctx, logger.Debug(), fmt.Sprintf(format, v...))
|
|
}
|
|
|
|
func Info(ctx context.Context, msg string) {
|
|
logEvent(ctx, logger.Info(), msg)
|
|
}
|
|
|
|
func Infof(ctx context.Context, format string, v ...any) {
|
|
logEvent(ctx, logger.Info(), fmt.Sprintf(format, v...))
|
|
}
|
|
|
|
func Warn(ctx context.Context, msg string) {
|
|
logEvent(ctx, logger.Warn(), msg)
|
|
}
|
|
|
|
func Warnf(ctx context.Context, format string, v ...any) {
|
|
logEvent(ctx, logger.Warn(), fmt.Sprintf(format, v...))
|
|
}
|
|
|
|
func Error(ctx context.Context, err error, msg string) {
|
|
logEvent(ctx, logger.Error().Err(err), msg)
|
|
}
|
|
|
|
func Errorf(ctx context.Context, err error, format string, v ...any) {
|
|
logEvent(ctx, logger.Error().Err(err), fmt.Sprintf(format, v...))
|
|
}
|
|
|
|
var ExitFunc = func(code int) {
|
|
os.Exit(code)
|
|
}
|
|
|
|
func Fatal(ctx context.Context, msg string) {
|
|
logEvent(ctx, logger.Error(), msg)
|
|
ExitFunc(1)
|
|
}
|
|
|
|
func Fatalf(ctx context.Context, format string, v ...any) {
|
|
logEvent(ctx, logger.Fatal(), fmt.Sprintf(format, v...))
|
|
ExitFunc(1)
|
|
}
|
|
|
|
func logEvent(ctx context.Context, event *zerolog.Event, msg string) {
|
|
for _, key := range cfg.ContextKeys {
|
|
if val, ok := ctx.Value(key).(string); ok && val != "" {
|
|
event.Str(key, val)
|
|
}
|
|
}
|
|
event.Msg(msg)
|
|
}
|