139 lines
3.5 KiB
Go
139 lines
3.5 KiB
Go
![]() |
//go:build !(windows || plan9 || wasip1 || js || ios || linux)
|
||
|
// +build !windows,!plan9,!wasip1,!js,!ios,!linux
|
||
|
|
||
|
// Linux is excluded because it has its own.
|
||
|
|
||
|
package logging
|
||
|
|
||
|
import (
|
||
|
native "log"
|
||
|
"os"
|
||
|
"path"
|
||
|
|
||
|
"r00t2.io/goutils/bitmask"
|
||
|
"r00t2.io/sysutils/paths"
|
||
|
)
|
||
|
|
||
|
var (
|
||
|
_ = native.Logger{}
|
||
|
_ = os.Interrupt
|
||
|
)
|
||
|
|
||
|
/*
|
||
|
GetLogger returns an instance of Logger that best suits your system's capabilities.
|
||
|
|
||
|
If enableDebug is true, debug messages (which according to your program may or may not contain sensitive data) are rendered and written.
|
||
|
|
||
|
If prefix is "\x00" (a null byte), then the default logging prefix will be used. If anything else, even an empty string,
|
||
|
is specified then that will be used instead for the prefix.
|
||
|
|
||
|
logConfigFlags is the corresponding flag(s) OR'd for StdLogger.LogFlags / FileLogger.StdLogger.LogFlags if either is selected. See StdLogger.LogFlags and
|
||
|
https://pkg.go.dev/log#pkg-constants for details.
|
||
|
|
||
|
logPaths is an (optional) list of strings to use as paths to test for writing. If the file can be created/written to,
|
||
|
it will be used (assuming you have no higher-level loggers available). Only the first logPaths entry that "works" will be used, later entries will be ignored.
|
||
|
If you want to log to multiple files simultaneously, use a MultiLogger instead.
|
||
|
|
||
|
If you call GetLogger, you will only get a single ("best") logger your system supports.
|
||
|
If you want to log to multiple Logger destinations at once (or want to log to an explicit Logger type),
|
||
|
use GetMultiLogger.
|
||
|
*/
|
||
|
func GetLogger(enableDebug bool, prefix string, logConfigFlags int, logPaths ...string) (logger Logger, err error) {
|
||
|
|
||
|
var logPath string
|
||
|
var logFlags bitmask.MaskBit
|
||
|
var currentPrefix string
|
||
|
|
||
|
// Configure system-supported logger(s).
|
||
|
|
||
|
// If we can detect syslog, use that. If not, try to use a file logger (+ stdout).
|
||
|
// Last ditch, stdout.
|
||
|
var hasSyslog bool
|
||
|
var stat os.FileInfo
|
||
|
var devlogPath string = devlog
|
||
|
|
||
|
if hasSyslog, stat, err = paths.RealPathExistsStat(&devlogPath); hasSyslog && err != nil {
|
||
|
return
|
||
|
}
|
||
|
|
||
|
if hasSyslog && !stat.Mode().IsRegular() {
|
||
|
logFlags.AddFlag(LogSyslog)
|
||
|
} else {
|
||
|
var exists bool
|
||
|
var success bool
|
||
|
var ckLogPaths []string
|
||
|
|
||
|
logFlags.AddFlag(LogStdout)
|
||
|
ckLogPaths = defLogPaths
|
||
|
if logPaths != nil {
|
||
|
ckLogPaths = logPaths
|
||
|
}
|
||
|
for _, p := range ckLogPaths {
|
||
|
if exists, _ = paths.RealPathExists(&p); exists {
|
||
|
if success, err = testOpen(p); err != nil {
|
||
|
continue
|
||
|
} else if !success {
|
||
|
continue
|
||
|
}
|
||
|
logFlags.AddFlag(LogFile)
|
||
|
logPath = p
|
||
|
break
|
||
|
} else {
|
||
|
dirPath := path.Dir(p)
|
||
|
if err = paths.MakeDirIfNotExist(dirPath); err != nil {
|
||
|
continue
|
||
|
}
|
||
|
if success, err = testOpen(p); err != nil {
|
||
|
continue
|
||
|
} else if !success {
|
||
|
continue
|
||
|
}
|
||
|
logFlags.AddFlag(LogFile)
|
||
|
logPath = p
|
||
|
break
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if logFlags.HasFlag(LogSyslog) {
|
||
|
logger = &SyslogLogger{
|
||
|
Prefix: logPrefix,
|
||
|
EnableDebug: enableDebug,
|
||
|
}
|
||
|
} else {
|
||
|
if logFlags.HasFlag(LogFile) {
|
||
|
logger = &FileLogger{
|
||
|
StdLogger: StdLogger{
|
||
|
Prefix: logPrefix,
|
||
|
EnableDebug: enableDebug,
|
||
|
LogFlags: logConfigFlags,
|
||
|
},
|
||
|
Path: logPath,
|
||
|
}
|
||
|
} else {
|
||
|
logger = &StdLogger{
|
||
|
Prefix: logPrefix,
|
||
|
EnableDebug: enableDebug,
|
||
|
LogFlags: logConfigFlags,
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if prefix != "\x00" {
|
||
|
if err = logger.SetPrefix(prefix); err != nil {
|
||
|
return
|
||
|
}
|
||
|
}
|
||
|
if err = logger.Setup(); err != nil {
|
||
|
return
|
||
|
}
|
||
|
|
||
|
if currentPrefix, err = logger.GetPrefix(); err != nil {
|
||
|
return
|
||
|
}
|
||
|
|
||
|
logger.Debug("logger initialized of type %T with prefix %v", logger, currentPrefix)
|
||
|
|
||
|
return
|
||
|
}
|