commonlog

package module
v0.2.17 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Mar 28, 2024 License: Apache-2.0 Imports: 13 Imported by: 80

README

CommonLog

License Go Reference Go Report Card

A common Go API for structured and unstructured logging with support for pluggable backends and sinks.

Supported backends (you can log to these APIs):

Supported sinks (you can capture logs from these APIs):

Rationale

The main design goal is to unite your logging APIs and allow you to change its backend at startup. For example, you can choose to log to stderr by default or use journald when running as a systemd service. Sinks allow you to use your selected backend with imported 3rd-party libraries when they use different logging APIs. This design goal is inspired by SLF4J, and we must lament that the Go ecosystem ended up with the same logging challenges that have existed for years in the Java ecosystem.

A secondary design goal is to provide a home for a full-featured unstructured textual logging library, which we call the "simple" backend. It supports rich, customizable formatting, including ANSI coloring when logging to a terminal (even on Windows). So, CommonLog is useful if you're just looking for a straightforward logging solution right now that will not block you from using other backends in the future.

Note that efficiency and performance are not in themselves design goals for CommonLog, and indeed there is always some overhead involved in wrapper and sink implementations. For example, using zerolog directly involves no allocations, but using it via CommonLog will add allocations. To put it simply: if you want zero allocation you must use zerolog directly. Sinks can be especially inefficient because they may have to rely on capturing and parsing of log text. Programming is all about tradeoffs: CommonLog provides compatibility and flexibility at the cost of some efficiency and performance. However, as always, beware of premature optimization. How you are storing or transmitting your log messages is likely the biggest factor in your optimization narrative.

A FAQ is: Why not standardize on the built-in slog API? Slog indeed is a big step forward for Go, not only because it supports structured messages, but also because it decouples the handler, an interface, from the logger. This enables alternative backends, a feature tragically missing from Go's log library. Unfortunately, slog was introduced only in Go 1.21 and is thus not used by much go Go's pre-1.21 ecosystem of 3rd-party libraries. CommonLog supports slog both as a backend and as a sink, so you can easily mix the CommonLog API with slog API and handling.

Features

  • Fine-grained control over verbosity via hierarchical log names. For example, "engine.parser.background" inherits from "engine.parser", which in turn inherits from "engine". The empty name is the root of the hierarchy. Each name's default verbosity is that of its parent, which you can then override with commonlog.SetMaxLevel().
  • Support for call stack depth. This can be used by a backend (for example, by klog) to find out where in the code the logging happened.
  • No need to create logger objects. The "true" API entrypoint is the global function commonlog.NewMessage, which you provide with a name and a level. The default logger type is just a convenient wrapper around it that provides the familiar unstructured functions.
  • The unstructured commonlog.Logger type is an interface, allowing you to more easily switch implementations per use without having to introduce a whole backend. For example, you can assign the commonlog.MOCK_LOGGER to disable a logger without changing the rest of your implementation. Compare with Go's built-in Logger type, which frustratingly is a struct rather than an interface.

Basic Usage

The easiest way to plug in a backend is to anonymously import the correct sub-package into your program's main package:

import (
    _ "github.com/tliron/commonlog/simple"
)

This should enable the backend with sensible defaults. Specifically it will log to stderr with verbosity at the "notice" max level.

Example of structured logging:

import (
    "github.com/tliron/commonlog"
    _ "github.com/tliron/commonlog/simple"
    "github.com/tliron/kutil/util"
)

func main() {
    if m := commonlog.NewErrorMessage(0, "engine", "parser"); m != nil {
        m.Set("_message", "Hello world!").Set("myFloat", 10.2).Send()
    }
    util.Exit(0)
}

Note that commonlog.NewMessage will return nil if the message is not created, for example if the message level is higher than the max level for that name, so you always need to check against nil.

That first integer argument is "depth", referring to callstack depth. This is only used when tracing is enabled to add the file name and line number of the logging location in the source code. For example, a value of 0 would use this location, while a value of 1 would use the caller of the current function, and so on.

Set can accept any key and value, but special keys are recognized by the API:

  • _message: The main description of the message. This is the key used by unstructured logging.
  • _scope: An optional identifier that can be used to group messages, making them easier to filter (e.g. by grep on text). Backends may handle this specially. Unstructured backends may, for example, add it as a bracketed prefix for messages.
  • _file: Source code file name
  • _line: Source code line number within file (expected to be an integer)

Also note that calling util.Exit(0) to exit your program is not absolutely necessary, however it's good practice because it makes sure to flush buffered log messages for some backends.

Unstructured logging is just a trivial case of structured logging in which only the _message key is used. However, CommonLog provides a more familiar logging API:

import (
    "github.com/tliron/commonlog"
    _ "github.com/tliron/commonlog/simple"
    "github.com/tliron/kutil/util"
)

var log = commonlog.GetLogger("engine.parser")

func main() {
    log.Noticef("Hello %s!", "world")
    util.Exit(0)
}

The API also supports adding structured key-value pairs as optional additional arguments to the methods without the "f" suffix:

log.Error("my message",
    "myFloat", 10.2,
    "myName", "Linus Torvalds",
)

Use conditional logging to optimize to avoid costly unstructured message creation when the log message would not be sent:

if log.AllowLevel(commonlog.Debug) {
    log.Debugf("Status is: %s", getStatusFromDatabase())
}

The key-value logger can be used to automatically add key-values to all log messages. It automatically detects nesting to add new values or override existing ones:

var log = commonlog.GetLogger("engine.parser")
var yamlLog = commonlog.NewKeyValueLogger(log,
    "format", "yaml",
    "formatVersion", 2,
)
var newYamllog = commonlog.NewKeyValueLogger(yamlLog,
    "formatVersion", 3,
)

The scope logger constructor can be used to automatically set the _scope key for a logger. It automatically detects nesting, in which case it appends the new scope separated by a ".":

var log = commonlog.GetLogger("engine.parser")
var validationLog = commonlog.NewScopeLogger(log, "validation")
var syntaxLog = commonlog.NewScopeLogger(validationLog, "syntax")

func main() {
    // Name is "engine.parser" and scope is "validation.syntax"
    syntaxLog.Errorf("Hello %s!", "world")
    ...
}

Configuration

All backends can be configured via a common API to support writing to files or stderr. For example, to increase verbosity and write to a file:

func main() {
    path := "myapp.log"
    commonlog.Configure(1, &path) // nil path would write to stderr
    ...
}

Backends may also have their own (non-common) configuration APIs related to their specific features.

You can set the max level (verbosity) using either the global API or a logger. For example, here is a way to make all logging verbose by default, except for one name:

func init() {
    commonlog.SetMaxLevel(commonlog.Debug) // the root
    commonlog.SetMaxLevel(commonlog.Error, "engine", "parser")
}

Descendents of "engine.parser", e.g. "engine.parser.analysis", would inherit the "engine.parser" log levels rather than the root's. Here's the same effect using unstructured loggers:

var rootLog = commonlog.GetLogger("")
var parserLog = commonlog.GetLogger("engine.parser")

func init() {
    rootLog.SetMaxLevel(commonlog.Debug)
    parserLog.SetMaxLevel(commonlog.Error)
}

It's important to note that the configuration APIs are not thread safe. This includes Configure() and SetMaxLevel(). Thus, make sure to get all your configuration done before you start sending log messages. A good place for this is init() or main() functions.

Also supported is the ability to add the source code file name and line number automatically to all messages, taking into account the "depth" argument for commonlog.NewMessage. Note that for the logger API the "depth" is always 0:

commonlog.Trace = true

Colorization

For the simple backend you must explicitly attempt to enable ANSI color if desired. Note that if it's unsupported by the terminal then no ANSI codes will be sent (unless you force it via util.InitializeColorization("force")). This even works on Windows, which has complicated colorization support in its cmd terminal:

import (
    "github.com/tliron/commonlog"
    _ "github.com/tliron/commonlog/simple"
    "github.com/tliron/kutil/util"
)

func main() {
    util.InitializeColorization("true")
    commonlog.GetLogger("engine.parser").Error("Hello world!") // errors are in red
    util.Exit(0)
}

Documentation

Index

Constants

View Source
const (
	MESSAGE = "_message"
	SCOPE   = "_scope"
	FILE    = "_file"
	LINE    = "_line"
)

Variables

View Source
var Trace bool

Functions

func AllowLevel

func AllowLevel(level Level, name ...string) bool

Returns true if a level is loggable for the given name on the current backend.

Returns false if no backend was set.

func CallAndLogError

func CallAndLogError(f func() error, task string, log Logger)

Convenience method to call a function and log the error, if returned, using [Logger.Error]. If task is not empty it will be prefixed to the error message.

func CallAndLogWarning added in v0.2.7

func CallAndLogWarning(f func() error, task string, log Logger)

Convenience method to call a function and log the error, if returned, using [Logger.Warning]. If task is not empty it will be prefixed to the error message.

func Configure

func Configure(verbosity int, path *string)

Configures the current backend. Verbosity is mapped to maximum loggable level as follows:

Note that -4 (None) is a special case that is often optimized to turn off as much processing as possible.

No-op if no backend was set.

func GetKeyValue added in v0.2.9

func GetKeyValue(key any, keysAndValues ...any) (any, bool)

func GetWriter

func GetWriter() io.Writer

Gets the current backend's io.Writer. Guaranteed to always return a valid non-nil value.

Will be io.Discard if writing is unsupported by the backend or if no backend was set.

func Initialize added in v0.1.1

func Initialize(verbosity int, path string)

Convenience method to call Configure while automatically overriding the verbosity with -4 (None) if terminal.Quiet is set to false and the path is empty (meaning we want to log to stdout).

func MergeKeysAndValues added in v0.2.6

func MergeKeysAndValues(toKeysAndValues []any, fromKeysAndValues []any) ([]any, bool)

func PathToName added in v0.2.5

func PathToName(path string) []string

func SetBackend

func SetBackend(backend_ Backend)

Sets the current backend.

A nil backend will disable all logging (but the APIs would still not fail).

func SetKeyValue added in v0.2.9

func SetKeyValue(key any, value any, keysAndValues ...any) ([]any, bool)

func SetMaxLevel

func SetMaxLevel(level Level, name ...string)

Sets the maximum loggable level for the given name on the current backend. Will become the default maximum level for names deeper in the hierarchy unless explicitly set for them.

No-op if no backend was set.

func SetMessageKeysAndValues added in v0.2.6

func SetMessageKeysAndValues(message Message, keysAndValues ...any)

Calls [Message.Set] on a provided sequence of key-value pairs. Thus keysAndValues must have an even length.

Non-string keys are converted to strings using util.ToString.

Types

type Backend

type Backend interface {
	// Configures the backend. Verbosity is mapped to maximum
	// loggable level as follows:
	//
	//   - -4 and below: [None]
	//   - -3: [Critical]
	//   - -2: [Error]
	//   - -1: [Warning]
	//   - 0: [Notice]
	//   - 1: [Info]
	//   - 2 and above: [Debug]
	//
	// Note that -4 ([None]) is a special case that is often optimized to turn
	// off as much processing as possible.
	Configure(verbosity int, path *string)

	// Gets the backend's [io.Writer]. Can be nil if unsupported.
	GetWriter() io.Writer

	NewMessage(level Level, depth int, name ...string) Message

	// Returns true if a level is loggable for the given name.
	AllowLevel(level Level, name ...string) bool

	// Sets the maximum loggable level for the given name. Will become the
	// default maximum level for names deeper in the hierarchy unless
	// explicitly set for them.
	SetMaxLevel(level Level, name ...string)

	// Gets the maximum loggable level for the given name.
	GetMaxLevel(name ...string) Level
}

type BackendLogger

type BackendLogger struct {
	// contains filtered or unexported fields
}

Default Logger implementation that logs to the current backend set with SetBackend.

func NewBackendLogger

func NewBackendLogger(name ...string) BackendLogger

func (BackendLogger) AllowLevel

func (self BackendLogger) AllowLevel(level Level) bool

(Logger interface)

func (BackendLogger) Critical

func (self BackendLogger) Critical(message string, keysAndValues ...any)

(Logger interface)

func (BackendLogger) Criticalf

func (self BackendLogger) Criticalf(format string, args ...any)

(Logger interface)

func (BackendLogger) Debug

func (self BackendLogger) Debug(message string, keysAndValues ...any)

(Logger interface)

func (BackendLogger) Debugf

func (self BackendLogger) Debugf(format string, args ...any)

(Logger interface)

func (BackendLogger) Error

func (self BackendLogger) Error(message string, keysAndValues ...any)

(Logger interface)

func (BackendLogger) Errorf

func (self BackendLogger) Errorf(format string, args ...any)

(Logger interface)

func (BackendLogger) GetMaxLevel

func (self BackendLogger) GetMaxLevel() Level

(Logger interface)

func (BackendLogger) Info

func (self BackendLogger) Info(message string, keysAndValues ...any)

(Logger interface)

func (BackendLogger) Infof

func (self BackendLogger) Infof(format string, args ...any)

(Logger interface)

func (BackendLogger) Log

func (self BackendLogger) Log(level Level, depth int, message string, keysAndValues ...any)

(Logger interface)

func (BackendLogger) Logf

func (self BackendLogger) Logf(level Level, depth int, format string, args ...any)

(Logger interface)

func (BackendLogger) NewMessage

func (self BackendLogger) NewMessage(level Level, depth int, keysAndValues ...any) Message

(Logger interface)

func (BackendLogger) Notice

func (self BackendLogger) Notice(message string, keysAndValues ...any)

(Logger interface)

func (BackendLogger) Noticef

func (self BackendLogger) Noticef(format string, args ...any)

(Logger interface)

func (BackendLogger) SetMaxLevel

func (self BackendLogger) SetMaxLevel(level Level)

(Logger interface)

func (BackendLogger) Warning

func (self BackendLogger) Warning(message string, keysAndValues ...any)

(Logger interface)

func (BackendLogger) Warningf

func (self BackendLogger) Warningf(format string, args ...any)

(Logger interface)

type KeyValueLogger added in v0.2.6

type KeyValueLogger struct {
	// contains filtered or unexported fields
}

Wrapping Logger that calls [Message.Set] with keys and values on all messages.

If we're wrapping another KeyValueLogger then our keys and values will be merged into the wrapped keys and values.

func NewKeyValueLogger added in v0.2.6

func NewKeyValueLogger(logger Logger, keysAndValues ...any) KeyValueLogger

func NewScopeLogger

func NewScopeLogger(logger Logger, scope string) KeyValueLogger

Wrapping Logger that calls [Message.Set] with a "_scope" key on all messages.

If we're wrapping another KeyValueLogger then our "_scope" key will be appended to the wrapped "_scope" key with a "." notation.

func (KeyValueLogger) AllowLevel added in v0.2.6

func (self KeyValueLogger) AllowLevel(level Level) bool

(Logger interface)

func (KeyValueLogger) Critical added in v0.2.6

func (self KeyValueLogger) Critical(message string, keysAndValues ...any)

(Logger interface)

func (KeyValueLogger) Criticalf added in v0.2.6

func (self KeyValueLogger) Criticalf(format string, args ...any)

(Logger interface)

func (KeyValueLogger) Debug added in v0.2.6

func (self KeyValueLogger) Debug(message string, keysAndValues ...any)

(Logger interface)

func (KeyValueLogger) Debugf added in v0.2.6

func (self KeyValueLogger) Debugf(format string, args ...any)

(Logger interface)

func (KeyValueLogger) Error added in v0.2.6

func (self KeyValueLogger) Error(message string, keysAndValues ...any)

(Logger interface)

func (KeyValueLogger) Errorf added in v0.2.6

func (self KeyValueLogger) Errorf(format string, args ...any)

(Logger interface)

func (KeyValueLogger) GetMaxLevel added in v0.2.6

func (self KeyValueLogger) GetMaxLevel() Level

(Logger interface)

func (KeyValueLogger) Info added in v0.2.6

func (self KeyValueLogger) Info(message string, keysAndValues ...any)

(Logger interface)

func (KeyValueLogger) Infof added in v0.2.6

func (self KeyValueLogger) Infof(format string, args ...any)

(Logger interface)

func (KeyValueLogger) Log added in v0.2.6

func (self KeyValueLogger) Log(level Level, depth int, message string, keysAndValues ...any)

(Logger interface)

func (KeyValueLogger) Logf added in v0.2.6

func (self KeyValueLogger) Logf(level Level, depth int, format string, args ...any)

(Logger interface)

func (KeyValueLogger) NewMessage added in v0.2.6

func (self KeyValueLogger) NewMessage(level Level, depth int, keysAndValues ...any) Message

(Logger interface)

func (KeyValueLogger) Notice added in v0.2.6

func (self KeyValueLogger) Notice(message string, keysAndValues ...any)

(Logger interface)

func (KeyValueLogger) Noticef added in v0.2.6

func (self KeyValueLogger) Noticef(format string, args ...any)

(Logger interface)

func (KeyValueLogger) SetMaxLevel added in v0.2.6

func (self KeyValueLogger) SetMaxLevel(level Level)

(Logger interface)

func (KeyValueLogger) Warning added in v0.2.6

func (self KeyValueLogger) Warning(message string, keysAndValues ...any)

(Logger interface)

func (KeyValueLogger) Warningf added in v0.2.6

func (self KeyValueLogger) Warningf(format string, args ...any)

(Logger interface)

type Level

type Level int
const (
	None     Level = 0
	Critical Level = 1
	Error    Level = 2
	Warning  Level = 3
	Notice   Level = 4
	Info     Level = 5
	Debug    Level = 6
)

func GetMaxLevel

func GetMaxLevel(name ...string) Level

Gets the maximum loggable level for the given name on the current backend.

Returns None if no backend was set.

func VerbosityToMaxLevel

func VerbosityToMaxLevel(verbosity int) Level

Translates a verbosity number to a maximum loggable level as follows:

func (Level) String

func (self Level) String() string

(fmt.Stringify interface)

type LinearMessage added in v0.2.17

type LinearMessage struct {
	Scope   string
	Message string
	Values  []LinearMessageValue
	File    string
	Line    int64
	// contains filtered or unexported fields
}

An implementation of Message optimized for representation as a single line of text.

func NewLinearMessage added in v0.2.17

func NewLinearMessage(send SendLinearMessageFunc) *LinearMessage

func (*LinearMessage) LocationString added in v0.2.17

func (self *LinearMessage) LocationString() string

func (*LinearMessage) Prefix added in v0.2.17

func (self *LinearMessage) Prefix(name ...string) string

func (*LinearMessage) Send added in v0.2.17

func (self *LinearMessage) Send()

(Message interface)

func (*LinearMessage) Set added in v0.2.17

func (self *LinearMessage) Set(key string, value any) Message

(Message interface)

func (*LinearMessage) String added in v0.2.17

func (self *LinearMessage) String() string

(fmt.Stringify interface)

func (*LinearMessage) StringWithPrefix added in v0.2.17

func (self *LinearMessage) StringWithPrefix(name ...string) string

func (*LinearMessage) ValuesString added in v0.2.17

func (self *LinearMessage) ValuesString(withLocation bool) string

type LinearMessageValue added in v0.2.17

type LinearMessageValue struct {
	Key   string
	Value string
}

type Logger

type Logger interface {
	// Returns true if a level is loggable for this logger.
	AllowLevel(level Level) bool

	// Sets the maximum loggable level for this logger.
	SetMaxLevel(level Level)

	// Gets the maximum loggable level for this logger.
	GetMaxLevel() Level

	// Creates a new message for this logger. Will return nil if
	// the level is not loggable.
	//
	// The depth argument is used for skipping frames in callstack
	// logging, if supported.
	NewMessage(level Level, depth int, keysAndValues ...any) Message

	// Convenience method to create and send a message with at least
	// the "_message" key. Additional keys can be set by providing
	// a sequence of key-value pairs.
	Log(level Level, depth int, message string, keysAndValues ...any)

	// Convenience method to create and send a message with just
	// the "_message" key, where the message is created via the format
	// and args similarly to fmt.Printf.
	Logf(level Level, depth int, format string, args ...any)

	Critical(message string, keysAndValues ...any)
	Criticalf(format string, args ...any)
	Error(message string, keysAndValues ...any)
	Errorf(format string, args ...any)
	Warning(message string, keysAndValues ...any)
	Warningf(format string, args ...any)
	Notice(message string, keysAndValues ...any)
	Noticef(format string, args ...any)
	Info(message string, keysAndValues ...any)
	Infof(format string, args ...any)
	Debug(message string, keysAndValues ...any)
	Debugf(format string, args ...any)
}

While NewMessage is the "true" API entry point, this interface enables a familiar logger API. Because it's an interface, references can easily replace the implementation, for example setting a reference to MOCK_LOGGER will disable the logger.

See GetLogger.

func GetLogger

func GetLogger(path string) Logger

Provides a BackendLogger instance for the given path. The path is converted to a name using PathToName.

Note that this function will always return a new instance and that instances for the same path are functionally equivalent.

func GetLoggerf

func GetLoggerf(format string, values ...any) Logger

Calls GetLogger with fmt.Sprintf for the path.

type LoggerFIFO added in v0.2.14

type LoggerFIFO struct {
	Path  string
	Log   Logger
	Level Level
}

A Linux FIFO file that forwards all lines written to it to a Logger.

func NewLoggerFIFO added in v0.2.14

func NewLoggerFIFO(prefix string, log Logger, level Level) *LoggerFIFO

func (*LoggerFIFO) Start added in v0.2.14

func (self *LoggerFIFO) Start() error

type LoggerServer added in v0.2.14

type LoggerServer struct {
	IPStack util.IPStack
	Address string
	Port    int
	Log     Logger
	Level   Level

	ClientAddressPorts []string
	// contains filtered or unexported fields
}

A TCP server file that forwards all lines written to it to a Logger.

func NewLoggerServer added in v0.2.14

func NewLoggerServer(ipStack util.IPStack, address string, port int, log Logger, level Level) *LoggerServer

func (*LoggerServer) Start added in v0.2.14

func (self *LoggerServer) Start() error

func (*LoggerServer) Stop added in v0.2.14

func (self *LoggerServer) Stop()

type Message

type Message interface {
	// Sets a value on the message and returns the same message
	// object.
	//
	// These keys are often specially supported:
	//
	// "_message": the base text of the message
	// "_scope": the scope of the message
	// "_file": filename in which the message was created
	// "_line": line number in the "_file"
	Set(key string, value any) Message

	// Sends the message to the backend.
	Send()
}

The entry point into the CommonLog API.

Also see Logger as a more familiar, alternative API.

func NewCriticalMessage added in v0.2.0

func NewCriticalMessage(depth int, name ...string) Message

Calls NewMessage with Critical level.

func NewDebugMessage added in v0.2.0

func NewDebugMessage(depth int, name ...string) Message

Calls NewMessage with Debug level.

func NewErrorMessage added in v0.2.0

func NewErrorMessage(depth int, name ...string) Message

Calls NewMessage with Error level.

func NewInfoMessage added in v0.2.0

func NewInfoMessage(depth int, name ...string) Message

Calls NewMessage with Info level.

func NewMessage

func NewMessage(level Level, depth int, name ...string) Message

Creates a new message for the given name on the current backend. Will return nil if the level is not loggable for the name, is None, or if no backend was set.

The depth argument is used for skipping frames in callstack logging, if supported.

func NewNoticeMessage added in v0.2.0

func NewNoticeMessage(depth int, name ...string) Message

Calls NewMessage with Notice level.

func NewWarningMessage added in v0.2.0

func NewWarningMessage(depth int, name ...string) Message

Calls NewMessage with Warning level.

func TraceMessage added in v0.2.6

func TraceMessage(message Message, depth int) Message

Adds "_file" and "_line" keys to a message if Trace is true. These are taken from the top of the callstack. Provide depth > 0 to skip frames in the callstack.

type MockLogger

type MockLogger struct{}

Logger that does nothing.

var MOCK_LOGGER MockLogger

func (MockLogger) AllowLevel

func (self MockLogger) AllowLevel(level Level) bool

(Logger interface)

func (MockLogger) Critical

func (self MockLogger) Critical(message string, keysAndValues ...any)

(Logger interface)

func (MockLogger) Criticalf

func (self MockLogger) Criticalf(format string, args ...any)

(Logger interface)

func (MockLogger) Debug

func (self MockLogger) Debug(message string, keysAndValues ...any)

(Logger interface)

func (MockLogger) Debugf

func (self MockLogger) Debugf(format string, args ...any)

(Logger interface)

func (MockLogger) Error

func (self MockLogger) Error(message string, keysAndValues ...any)

(Logger interface)

func (MockLogger) Errorf

func (self MockLogger) Errorf(format string, args ...any)

(Logger interface)

func (MockLogger) GetMaxLevel

func (self MockLogger) GetMaxLevel() Level

(Logger interface)

func (MockLogger) Info

func (self MockLogger) Info(message string, keysAndValues ...any)

(Logger interface)

func (MockLogger) Infof

func (self MockLogger) Infof(format string, args ...any)

(Logger interface)

func (MockLogger) Log

func (self MockLogger) Log(level Level, depth int, message string, keysAndValues ...any)

(Logger interface)

func (MockLogger) Logf

func (self MockLogger) Logf(level Level, depth int, format string, args ...any)

(Logger interface)

func (MockLogger) NewMessage

func (self MockLogger) NewMessage(level Level, depth int, keysAndValues ...any) Message

(Logger interface)

func (MockLogger) Notice

func (self MockLogger) Notice(message string, keysAndValues ...any)

(Logger interface)

func (MockLogger) Noticef

func (self MockLogger) Noticef(format string, args ...any)

(Logger interface)

func (MockLogger) SetMaxLevel

func (self MockLogger) SetMaxLevel(level Level)

(Logger interface)

func (MockLogger) Warning

func (self MockLogger) Warning(message string, keysAndValues ...any)

(Logger interface)

func (MockLogger) Warningf

func (self MockLogger) Warningf(format string, args ...any)

(Logger interface)

type NameHierarchy added in v0.2.0

type NameHierarchy struct {
	// contains filtered or unexported fields
}

Convenience type for implementing maximum level per name in backends. Supports level inheritance.

func NewNameHierarchy added in v0.2.0

func NewNameHierarchy() *NameHierarchy

func (*NameHierarchy) AllowLevel added in v0.2.0

func (self *NameHierarchy) AllowLevel(level Level, name ...string) bool

func (*NameHierarchy) GetMaxLevel added in v0.2.0

func (self *NameHierarchy) GetMaxLevel(name ...string) Level

func (*NameHierarchy) SetMaxLevel added in v0.2.0

func (self *NameHierarchy) SetMaxLevel(level Level, name ...string)

type SendLinearMessageFunc added in v0.2.17

type SendLinearMessageFunc func(message *LinearMessage)

Directories

Path Synopsis

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL