diff --git a/internal/logger/logger.go b/internal/logger/logger.go new file mode 100644 index 00000000000..43877e878e9 --- /dev/null +++ b/internal/logger/logger.go @@ -0,0 +1,84 @@ +package logger + +import ( + "fmt" + "os" + + "go.opentelemetry.io/otel/otellog" +) + +var Logger otellog.Logger = otellog.NewDefaultLogger(os.Stdout, otellog.LogLevelInfo) + +func Tracef(format string, args ...interface{}) { + Logger.Log(otellog.LogLevelTrace, printfArgs{format, args}) +} + +func Trace(args ...interface{}) { + Logger.Log(otellog.LogLevelTrace, printArgs(args)) +} + +func Debugf(format string, args ...interface{}) { + Logger.Log(otellog.LogLevelDebug, printfArgs{format, args}) +} + +func Debug(args ...interface{}) { + Logger.Log(otellog.LogLevelDebug, printArgs(args)) +} + +func DebugDeferred(fn func() string) { + Logger.Log(otellog.LogLevelDebug, stringerFunc(fn)) +} + +func Infof(format string, args ...interface{}) { + Logger.Log(otellog.LogLevelInfo, printfArgs{format, args}) +} + +func Info(args ...interface{}) { + Logger.Log(otellog.LogLevelInfo, printArgs(args)) +} + +func Warnf(format string, args ...interface{}) { + Logger.Log(otellog.LogLevelWarn, printfArgs{format, args}) +} + +func Warn(args ...interface{}) { + Logger.Log(otellog.LogLevelWarn, printArgs(args)) +} + +func Errorf(format string, args ...interface{}) { + Logger.Log(otellog.LogLevelError, printfArgs{format, args}) +} + +func Error(args ...interface{}) { + Logger.Log(otellog.LogLevelError, printArgs(args)) +} + +func Fatalf(format string, args ...interface{}) { + Logger.Log(otellog.LogLevelFatal, printfArgs{format, args}) +} + +func Fatal(args ...interface{}) { + Logger.Log(otellog.LogLevelFatal, printArgs(args)) +} + +type printfArgs struct { + format string + args []interface{} +} + +func (p printfArgs) String() string { + return fmt.Sprintf(p.format, p.args...) +} + +type printArgs []interface{} + +func (p printArgs) String() string { + return fmt.Sprint([]interface{}(p)...) +} + +type stringerFunc func() string + +func (sf stringerFunc) String() string { + return sf() +} + diff --git a/otellog/otel_log.go b/otellog/otel_log.go new file mode 100644 index 00000000000..710a0d62f41 --- /dev/null +++ b/otellog/otel_log.go @@ -0,0 +1,80 @@ +package otellog + +import ( + "fmt" + "io" + "sync" + "time" +) + +type Logger interface { + Log(level LogLevel, msg fmt.Stringer) +} + +type LogLevel int + +const ( + // LogLevelTrace is used to for fine-grained debugging event and disabled in default configurations. + LogLevelTrace LogLevel = iota + 1 + + // LogLevelDebug is usually only enabled when debugging. + LogLevelDebug + + // LogLevelInfo is used only for informal event indicates that event has happened. + LogLevelInfo + + // LogLevelWarn is non-critical entries that deserve eyes. + LogLevelWarn + + // LogLevelError is used for errors that should definitely be noted. + LogLevelError + + // LogLevelError is used for fatal errors such as application or system crash. + LogLevelFatal +) + +func (ll LogLevel) String() string { + switch ll { + case LogLevelTrace: + return "TRACE" + case LogLevelDebug: + return "DEBUG" + case LogLevelInfo: + return "INFO" + case LogLevelWarn: + return "WARN" + case LogLevelError: + return "ERROR" + case LogLevelFatal: + return "FATAL" + default: + return fmt.Sprintf("UNKNOWNLOGLEVEL<%d>", ll) + } +} + +func NewDefaultLogger(w io.Writer, minLogLevel LogLevel) Logger { + return &defaultLogger{w: w, minLevel: minLogLevel} +} + +type defaultLogger struct { + mu sync.Mutex + w io.Writer + minLevel LogLevel +} + +func (l *defaultLogger) Log(ll LogLevel, msg fmt.Stringer) { + if ll < l.minLevel { + return + } + + l.mu.Lock() + defer l.mu.Unlock() + _, _ = fmt.Fprintf(l.w, "%s\t[%s]\t%s\n", time.Now().Format(time.RFC3339), ll, msg) +} + +var NullLogger = nullLogger{} + +type nullLogger struct{} + +func (nl nullLogger) Log(ll LogLevel, msg fmt.Stringer) { +}