mirror of
https://github.com/gohugoio/hugo.git
synced 2025-08-21 21:35:28 +02:00
Write all logging (INFO, WARN, ERROR) to stderr
The old setup tried to log >= warning to stderr, the rest to stdout. However, that logic was flawed, so warnings ended up in stdout, which makes `hugo list all` etc. hard to reason about from scripts. This commit fixes this by making all logging (info, warn, error) log to stderr and let stdout be reserved for program output. Fixes #13074
This commit is contained in:
committed by
GitHub
parent
ec1933f79d
commit
9dfa112617
@@ -40,8 +40,8 @@ func newNoAnsiEscapeHandler(outWriter, errWriter io.Writer, noLevelPrefix bool,
|
||||
|
||||
type noAnsiEscapeHandler struct {
|
||||
mu sync.Mutex
|
||||
outWriter io.Writer // Defaults to os.Stdout.
|
||||
errWriter io.Writer // Defaults to os.Stderr.
|
||||
outWriter io.Writer
|
||||
errWriter io.Writer
|
||||
predicate func(*logg.Entry) bool
|
||||
noLevelPrefix bool
|
||||
}
|
||||
|
@@ -38,8 +38,8 @@ var (
|
||||
// Options defines options for the logger.
|
||||
type Options struct {
|
||||
Level logg.Level
|
||||
Stdout io.Writer
|
||||
Stderr io.Writer
|
||||
StdOut io.Writer
|
||||
StdErr io.Writer
|
||||
DistinctLevel logg.Level
|
||||
StoreErrors bool
|
||||
HandlerPost func(e *logg.Entry) error
|
||||
@@ -48,21 +48,22 @@ type Options struct {
|
||||
|
||||
// New creates a new logger with the given options.
|
||||
func New(opts Options) Logger {
|
||||
if opts.Stdout == nil {
|
||||
opts.Stdout = os.Stdout
|
||||
if opts.StdOut == nil {
|
||||
opts.StdOut = os.Stdout
|
||||
}
|
||||
if opts.Stderr == nil {
|
||||
opts.Stderr = os.Stdout
|
||||
if opts.StdErr == nil {
|
||||
opts.StdErr = os.Stderr
|
||||
}
|
||||
|
||||
if opts.Level == 0 {
|
||||
opts.Level = logg.LevelWarn
|
||||
}
|
||||
|
||||
var logHandler logg.Handler
|
||||
if terminal.PrintANSIColors(os.Stdout) {
|
||||
logHandler = newDefaultHandler(opts.Stdout, opts.Stderr)
|
||||
if terminal.PrintANSIColors(os.Stderr) {
|
||||
logHandler = newDefaultHandler(opts.StdErr, opts.StdErr)
|
||||
} else {
|
||||
logHandler = newNoAnsiEscapeHandler(opts.Stdout, opts.Stderr, false, nil)
|
||||
logHandler = newNoAnsiEscapeHandler(opts.StdErr, opts.StdErr, false, nil)
|
||||
}
|
||||
|
||||
errorsw := &strings.Builder{}
|
||||
@@ -137,7 +138,8 @@ func New(opts Options) Logger {
|
||||
logCounters: logCounters,
|
||||
errors: errorsw,
|
||||
reset: reset,
|
||||
out: opts.Stdout,
|
||||
stdOut: opts.StdOut,
|
||||
stdErr: opts.StdErr,
|
||||
level: opts.Level,
|
||||
logger: logger,
|
||||
tracel: l.WithLevel(logg.LevelTrace),
|
||||
@@ -153,8 +155,6 @@ func NewDefault() Logger {
|
||||
opts := Options{
|
||||
DistinctLevel: logg.LevelWarn,
|
||||
Level: logg.LevelWarn,
|
||||
Stdout: os.Stdout,
|
||||
Stderr: os.Stdout,
|
||||
}
|
||||
return New(opts)
|
||||
}
|
||||
@@ -163,8 +163,6 @@ func NewTrace() Logger {
|
||||
opts := Options{
|
||||
DistinctLevel: logg.LevelWarn,
|
||||
Level: logg.LevelTrace,
|
||||
Stdout: os.Stdout,
|
||||
Stderr: os.Stdout,
|
||||
}
|
||||
return New(opts)
|
||||
}
|
||||
@@ -189,7 +187,8 @@ type Logger interface {
|
||||
Level() logg.Level
|
||||
LoggCount(logg.Level) int
|
||||
Logger() logg.Logger
|
||||
Out() io.Writer
|
||||
StdOut() io.Writer
|
||||
StdErr() io.Writer
|
||||
Printf(format string, v ...any)
|
||||
Println(v ...any)
|
||||
PrintTimerIfDelayed(start time.Time, name string)
|
||||
@@ -207,7 +206,8 @@ type logAdapter struct {
|
||||
logCounters *logLevelCounter
|
||||
errors *strings.Builder
|
||||
reset func()
|
||||
out io.Writer
|
||||
stdOut io.Writer
|
||||
stdErr io.Writer
|
||||
level logg.Level
|
||||
logger logg.Logger
|
||||
tracel logg.LevelLogger
|
||||
@@ -259,8 +259,12 @@ func (l *logAdapter) Logger() logg.Logger {
|
||||
return l.logger
|
||||
}
|
||||
|
||||
func (l *logAdapter) Out() io.Writer {
|
||||
return l.out
|
||||
func (l *logAdapter) StdOut() io.Writer {
|
||||
return l.stdOut
|
||||
}
|
||||
|
||||
func (l *logAdapter) StdErr() io.Writer {
|
||||
return l.stdErr
|
||||
}
|
||||
|
||||
// PrintTimerIfDelayed prints a time statement to the FEEDBACK logger
|
||||
@@ -279,11 +283,11 @@ func (l *logAdapter) Printf(format string, v ...any) {
|
||||
if !strings.HasSuffix(format, "\n") {
|
||||
format += "\n"
|
||||
}
|
||||
fmt.Fprintf(l.out, format, v...)
|
||||
fmt.Fprintf(l.stdOut, format, v...)
|
||||
}
|
||||
|
||||
func (l *logAdapter) Println(v ...any) {
|
||||
fmt.Fprintln(l.out, v...)
|
||||
fmt.Fprintln(l.stdOut, v...)
|
||||
}
|
||||
|
||||
func (l *logAdapter) Reset() {
|
||||
|
@@ -31,8 +31,8 @@ func TestLogDistinct(t *testing.T) {
|
||||
opts := loggers.Options{
|
||||
DistinctLevel: logg.LevelWarn,
|
||||
StoreErrors: true,
|
||||
Stdout: io.Discard,
|
||||
Stderr: io.Discard,
|
||||
StdOut: io.Discard,
|
||||
StdErr: io.Discard,
|
||||
}
|
||||
|
||||
l := loggers.New(opts)
|
||||
@@ -54,8 +54,8 @@ func TestHookLast(t *testing.T) {
|
||||
HandlerPost: func(e *logg.Entry) error {
|
||||
panic(e.Message)
|
||||
},
|
||||
Stdout: io.Discard,
|
||||
Stderr: io.Discard,
|
||||
StdOut: io.Discard,
|
||||
StdErr: io.Discard,
|
||||
}
|
||||
|
||||
l := loggers.New(opts)
|
||||
@@ -70,8 +70,8 @@ func TestOptionStoreErrors(t *testing.T) {
|
||||
|
||||
opts := loggers.Options{
|
||||
StoreErrors: true,
|
||||
Stderr: &sb,
|
||||
Stdout: &sb,
|
||||
StdErr: &sb,
|
||||
StdOut: &sb,
|
||||
}
|
||||
|
||||
l := loggers.New(opts)
|
||||
@@ -131,8 +131,8 @@ func TestReset(t *testing.T) {
|
||||
opts := loggers.Options{
|
||||
StoreErrors: true,
|
||||
DistinctLevel: logg.LevelWarn,
|
||||
Stdout: io.Discard,
|
||||
Stderr: io.Discard,
|
||||
StdOut: io.Discard,
|
||||
StdErr: io.Discard,
|
||||
}
|
||||
|
||||
l := loggers.New(opts)
|
||||
|
Reference in New Issue
Block a user