package chart import ( "fmt" "io" "os" "time" ) var ( _ Logger = (*StdoutLogger)(nil) ) // NewLogger returns a new logger. func NewLogger(options ...LoggerOption) Logger { stl := &StdoutLogger{ TimeFormat: time.RFC3339Nano, Stdout: os.Stdout, Stderr: os.Stderr, } for _, option := range options { option(stl) } return stl } // Logger is a type that implements the logging interface. type Logger interface { Info(...interface{}) Infof(string, ...interface{}) Debug(...interface{}) Debugf(string, ...interface{}) Err(error) FatalErr(error) Error(...interface{}) Errorf(string, ...interface{}) } // Info logs an info message if the logger is set. func Info(log Logger, arguments ...interface{}) { if log == nil { return } log.Info(arguments...) } // Infof logs an info message if the logger is set. func Infof(log Logger, format string, arguments ...interface{}) { if log == nil { return } log.Infof(format, arguments...) } // Debug logs an debug message if the logger is set. func Debug(log Logger, arguments ...interface{}) { if log == nil { return } log.Debug(arguments...) } // Debugf logs an debug message if the logger is set. func Debugf(log Logger, format string, arguments ...interface{}) { if log == nil { return } log.Debugf(format, arguments...) } // LoggerOption mutates a stdout logger. type LoggerOption = func(*StdoutLogger) //OptLoggerStdout sets the Stdout writer. func OptLoggerStdout(wr io.Writer) LoggerOption { return func(stl *StdoutLogger) { stl.Stdout = wr } } // OptLoggerStderr sets the Stdout writer. func OptLoggerStderr(wr io.Writer) LoggerOption { return func(stl *StdoutLogger) { stl.Stderr = wr } } // StdoutLogger is a basic logger. type StdoutLogger struct { TimeFormat string Stdout io.Writer Stderr io.Writer } // Info writes an info message. func (l *StdoutLogger) Info(arguments ...interface{}) { l.Println(append([]interface{}{"[INFO]"}, arguments...)...) } // Infof writes an info message. func (l *StdoutLogger) Infof(format string, arguments ...interface{}) { l.Println(append([]interface{}{"[INFO]"}, fmt.Sprintf(format, arguments...))...) } // Debug writes an debug message. func (l *StdoutLogger) Debug(arguments ...interface{}) { l.Println(append([]interface{}{"[DEBUG]"}, arguments...)...) } // Debugf writes an debug message. func (l *StdoutLogger) Debugf(format string, arguments ...interface{}) { l.Println(append([]interface{}{"[DEBUG]"}, fmt.Sprintf(format, arguments...))...) } // Error writes an error message. func (l *StdoutLogger) Error(arguments ...interface{}) { l.Println(append([]interface{}{"[ERROR]"}, arguments...)...) } // Errorf writes an error message. func (l *StdoutLogger) Errorf(format string, arguments ...interface{}) { l.Println(append([]interface{}{"[ERROR]"}, fmt.Sprintf(format, arguments...))...) } // Err writes an error message. func (l *StdoutLogger) Err(err error) { if err != nil { l.Println(append([]interface{}{"[ERROR]"}, err.Error())...) } } // FatalErr writes an error message and exits. func (l *StdoutLogger) FatalErr(err error) { if err != nil { l.Println(append([]interface{}{"[FATAL]"}, err.Error())...) os.Exit(1) } } // Println prints a new message. func (l *StdoutLogger) Println(arguments ...interface{}) { fmt.Fprintln(l.Stdout, append([]interface{}{time.Now().UTC().Format(l.TimeFormat)}, arguments...)...) } // Errorln prints a new message. func (l *StdoutLogger) Errorln(arguments ...interface{}) { fmt.Fprintln(l.Stderr, append([]interface{}{time.Now().UTC().Format(l.TimeFormat)}, arguments...)...) }