logs

package module
v1.1.1 Latest Latest
Warning

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

Go to latest
Published: May 31, 2023 License: Apache-2.0 Imports: 10 Imported by: 0

README

Logs

Versatile logging for Golang

GoDoc

Usage

go get -u github.com/bigcommerce/logs

Simple loggers only require a level:

logger := logs.NewStdoutLogger(logs.Info)
logger.Info("I'm logging!")

Prints:

16 Nov 2020 02:33:19.402 UTC INFO  I'm logging!

More complex loggers can be composed:

// Use a time.Location to localise log timestamps
location, err := time.LoadLocation("Australia/Sydney")
if err != nil {
	panic(err)
}

// Set a Level using user input
level, err := logs.LevelByName("warn")
if err != nil {
	panic(err)
}

// A TimeFormatter can be used by other Formatters
timeFormatter := logs.NewTimeFormatter(
	"2006-01-02 15:04",
	location,
)

// Make your own Formatter using a simple function
formatter := logs.FormatterFunc(func(event *logs.Event) []byte {
	return append(
		timeFormatter.Format(event),
		[]byte(fmt.Sprintf(" (%s) %s\n",
			event.Level.Abbreviation(),
			event.Message,
		))...,
	)
})

// A Publisher can send logs to several Subscribers
publisher := logs.NewPublisher(
	logs.NewWriterWithFormat(os.Stdout, formatter),
)

// Conditionally add more Subscribers to your publisher
if jsonPath := os.Getenv("JSON_LOG_PATH"); jsonPath != "" {
	jsonFile, err := os.Create(jsonPath)
	if err != nil {
		panic(err)
	}
	var messageID uint64
	
	// JsonFormatter produces Logstash-compatible output
	jsonFormatter := logs.NewJsonFormatter(logs.TagsFunc(func() logs.Tags {
		messageID += 1
		return logs.Tags{{"messageID", messageID}}
	}))
	publisher.Add(logs.NewWriterWithFormat(jsonFile, jsonFormatter))
}

// Use a Buffer to ensure log writing doesn't block on IO
logger := logs.NewLogger(level, logs.NewBuffer(1000, publisher))

See the documentation for the complete API.

Documentation

Index

Constants

This section is empty.

Variables

View Source
var DefaultLogger = NewStdoutLogger(0)

DefaultLogger is an all-levels, TTY-sensing logger that writes to STDOUT.

View Source
var DefaultTimeFormatter = &TimeFormatter{
	TimeFormat: "02 Jan 2006 15:04:05.000 MST",
	Location:   time.UTC,
}

DefaultTimeFormatter is the default TimeFormatter used by various packaged default formatters and Logger recipes.

View Source
var Levels = map[Level]LevelInfo{
	Verbose: {"verbose", "VRBSE", ansi.Blue},
	Trace:   {"trace", "TRACE", ansi.Green},
	Debug:   {"debug", "DEBUG", ansi.Cyan},
	Info:    {"info", "INFO ", 0},
	Warn:    {"warn", "WARN ", ansi.Yellow},
	Error:   {"error", "ERROR", ansi.Red},
	Fatal:   {"fatal", "FATAL", ansi.Magenta},
	Silent:  {"silent", "SILNT", ansi.White},
}

Levels contains default properties of the set levels, which can be used by formatters.

View Source
var NullLogger = NewLogger(0, new(NullSubscriber)) // 0 level avoids making a LevelFilter

NullLogger is a logger that discards events. You can use it as a placeholder in apps that have logging disabled and want calls to Info, Warn, Error etc to no-op.

View Source
var NullProducer = &Producer{Subscriber: new(NullSubscriber)}

NullProducer is a producer that discards all events.

NullWriter is a writer that does not write events to anywhere.

Functions

This section is empty.

Types

type Buffer

type Buffer struct {
	Subscriber
	// contains filtered or unexported fields
}

Buffer uses a goroutine to consume events from a buffered channel, ensuring publication doesn't block on writing (at least until the buffer is full). A zero Buffer will not work. Use NewBuffer instead.

func NewBuffer

func NewBuffer(size int, subscriber Subscriber) (b *Buffer)

NewBuffer wraps the given Subscriber in a buffer with the given size.

func (*Buffer) Close

func (b *Buffer) Close()

Close closes the buffer's underlying channel. Calls made to Log after Close is called will panic.

func (*Buffer) Log

func (b *Buffer) Log(event *Event)

type Err

type Err string

Err represents most of the errors generated by the package.

const (
	// InvalidLevelName occurs when LevelByName is called with an invalid name.
	InvalidLevelName Err = "invalid level name"
)

func (Err) Error

func (e Err) Error() string

type Event

type Event struct {
	Time    time.Time
	Level   Level
	Message fmt.Stringer
	Tags    Tags
}

Event represents a single log message.

type Formatter

type Formatter interface {
	Format(event *Event) []byte
}

Formatter can format a given Event for writing to a log device. Formatters should normally include a trailing newline.

var DefaultColoredTextFormatter Formatter = FormatterFunc(func(event *Event) []byte {
	return append(DefaultTimeFormatter.Format(event), []byte(fmt.Sprintf(
		" %s %s\n",
		event.Level.Color().Bold().Wrap(event.Level.Abbreviation()),
		event.Message,
	))...)
})

DefaultColoredTextFormatter is the same as DefaultPlainTextFormatter, but adds color to the Level component to help messages of different severities stand out.

var DefaultPlainTextFormatter Formatter = FormatterFunc(func(event *Event) []byte {
	return append(DefaultTimeFormatter.Format(event), []byte(fmt.Sprintf(
		" %s %s\n",
		event.Level.Abbreviation(),
		event.Message,
	))...)
})

DefaultPlainTextFormatter formats events as the time (using DefaultTimeFormatter), the Level abbreviation, and the message. Tags are not included.

var MessageOnlyFormatter Formatter = FormatterFunc(func(event *Event) []byte {
	return append([]byte(event.Message.String()), '\n')
})

MessageOnlyFormatter is a simple formatter that returns an event's message followed by a newline.

type FormatterFunc

type FormatterFunc func(event *Event) []byte

FormatterFunc creates a Formatter using the given function.

func (FormatterFunc) Format

func (f FormatterFunc) Format(event *Event) (formatted []byte)

type JsonFormatter

type JsonFormatter struct {
	Tags TagSet
}

JsonFormatter is a JSON log formatter compatible with Logstash.

func NewJsonFormatter

func NewJsonFormatter(tags TagSet) *JsonFormatter

NewJsonFormatter creates a new JsonFormatter with the given TagSet.

func (*JsonFormatter) Format

func (j *JsonFormatter) Format(event *Event) []byte

type LazyMessage

type LazyMessage struct {
	Message string
	Args    []interface{}
}

LazyMessage is used by Producer to delay formatting of messages, in case an event is to be discarded by a LevelFilter.

func (*LazyMessage) String

func (m *LazyMessage) String() string

type Level

type Level uint8

Level represents log message severity. Levels are preset as the seven constants Verbose, Trace, Debug, Info, Warn, Error, and Fatal.

const (
	Verbose Level = 1 << iota
	Trace
	Debug
	Info
	Warn
	Error
	Fatal
	Silent
)

func LevelByName

func LevelByName(name string) (Level, error)

LevelByName returns a Level if one case-insensitively matches the given name. If none match, InvalidLevelName is returned.

func (Level) Abbreviation

func (l Level) Abbreviation() string

Abbreviation returns a five-character uppercase string representing the receiving Level.

func (Level) Color

func (l Level) Color() ansi.EscapeSequence

Color returns the Color of the receiving Level, based on the Levels map.

func (Level) Name

func (l Level) Name() string

Name returns the lowercase name of a Level.

type LevelFilter

type LevelFilter struct {
	Subscriber
	LevelMask Level
}

LevelFilter wraps a Subscriber, swallowing events that do not match LevelMask.

func NewLevelFilter

func NewLevelFilter(level Level, subscriber Subscriber) *LevelFilter

NewLevelFilter creates a new LevelFilter that will swallow events with severity lower than the given Level.

func (*LevelFilter) Log

func (l *LevelFilter) Log(event *Event)

type LevelInfo

type LevelInfo struct {
	Name         string
	Abbreviation string
	Color        ansi.EscapeSequence
}

LevelInfo represents the default properties of a Level.

type Logger

type Logger struct {
	*Producer
	Tags Tags
	// contains filtered or unexported fields
}

Logger is a full-featured logging utility.

func NewColoredTextLogger

func NewColoredTextLogger(level Level, writer io.Writer) *Logger

NewColoredTextLogger creates a new Logger with the given Level for the given io.Writer, using DefaultColoredTextFormatter as its formatter.

func NewFormattedLogger

func NewFormattedLogger(level Level, writer io.Writer, formatter Formatter) *Logger

NewFormattedLogger creates a new Logger with the given Level for the given io.Writer, using the given Formatter as its formatter.

func NewLogger

func NewLogger(level Level, subscriber Subscriber) (logger *Logger)

NewLogger creates a new Logger with the given Level, which publishes synchronously to the given Subscriber.

func NewPlainTextLogger

func NewPlainTextLogger(level Level, writer io.Writer) *Logger

NewPlainTextLogger creates a new Logger with the given Level for the given io.Writer, using DefaultPlainTextFormatter as its formatter.

func NewStderrLogger

func NewStderrLogger(level Level) *Logger

NewStderrLogger creates a new Logger with the given Level for STDERR, using either DefaultPlainTextFormatter or DefaultColoredTextFormatter as its formatter, depending on whether it senses a TTY.

func NewStdoutLogger

func NewStdoutLogger(level Level) *Logger

NewStdoutLogger creates a new Logger with the given Level for STDOUT, using either DefaultPlainTextFormatter or DefaultColoredTextFormatter as its formatter, depending on whether it senses a TTY.

func NewTextLogger

func NewTextLogger(level Level, file *os.File) *Logger

NewTextLogger creates a new Logger with the given Level for the given os.File, using either DefaultPlainTextFormatter or DefaultColoredTextFormatter as its formatter, depending on whether it senses a TTY.

func (*Logger) Extend

func (l *Logger) Extend(tags TagSet) (extended *Logger)

Extend returns a copy of the receiving Logger that has the given TagSet added to its Tags list. The TagSet is evaluated at call time, so Loggers depending on changing TagSet implementations should be discarded after use.

func (*Logger) Log

func (l *Logger) Log(event *Event)

func (*Logger) SetLevel

func (l *Logger) SetLevel(level Level)

SetLevel changes the Level of the receiving Logger. The function is not concurrency-safe, so care should be taken not to race any log calls.

type NullFormatter

type NullFormatter struct{}

NullFormatter is an implementation of Formatter that formats every message as an empty byte slice.

func (*NullFormatter) Format

func (n *NullFormatter) Format(*Event) []byte

type NullSubscriber

type NullSubscriber struct{}

NullSubscriber is an implementation of Subscriber that discards messages. It is used chiefly by NullLogger.

func (*NullSubscriber) Log

func (n *NullSubscriber) Log(*Event)

type Producer

type Producer struct {
	Subscriber
	Clock func() time.Time // Function used to timestamp events created by the receiver
}

Producer provides the per-level functions of Logger, but can also be wrapped around any Subscriber when composing custom loggers.

func (*Producer) Debug

func (p *Producer) Debug(message string, a ...interface{})

func (*Producer) Error

func (p *Producer) Error(message string, a ...interface{})

func (*Producer) Fatal

func (p *Producer) Fatal(message string, a ...interface{})

func (*Producer) Info

func (p *Producer) Info(message string, a ...interface{})

func (*Producer) Log

func (p *Producer) Log(level Level, message string, a []interface{})

func (*Producer) Trace

func (p *Producer) Trace(message string, a ...interface{})

func (*Producer) Verbose

func (p *Producer) Verbose(message string, a ...interface{})

func (*Producer) Warn

func (p *Producer) Warn(message string, a ...interface{})

type Publisher

type Publisher []Subscriber

Publisher relays each Event it receives to as many Subscriber implementations as are in its slice.

func NewPublisher

func NewPublisher(subscribers ...Subscriber) Publisher

NewPublisher creates a new Publisher that relays events to the given Subscriber slice.

func (*Publisher) Add

func (p *Publisher) Add(subscriber Subscriber)

Add appends an additional Subscriber to the receiving Publisher.

func (Publisher) Log

func (p Publisher) Log(event *Event)

type Subscriber

type Subscriber interface {
	Log(event *Event)
}

Subscriber represents anything that can receive Log events.

type Tag

type Tag struct {
	Name  string
	Value interface{}
}

type TagSet

type TagSet interface {
	Tags() []*Tag
}

type Tags

type Tags []*Tag

Tags can be attached to log events to provide additional information, particularly for JSON and other structured log formatters.

func (Tags) Join

func (t Tags) Join(other ...*Tag) Tags

Join creates a new Tags by appending the given tags to the receiver. Tags towards the end of the slice take precedence, meaning the joined tags will override those in the receiver with the same name.

func (Tags) Map

func (t Tags) Map() (m map[string]interface{})

Map returns a map of tag keys to values. Overridden tags are excluded from the returned map.

func (Tags) MarshalJSON

func (t Tags) MarshalJSON() (encoded []byte, err error)

MarshalJSON causes the receiver to be marshaled to JSON as an object with ordered keys.

func (Tags) QueryEncode

func (t Tags) QueryEncode() []byte

QueryEncode formats tags as a percent-encoded URL query string. Tags are positioned in the string in the order they first appear, with later values taking precedence.

func (Tags) Tags

func (t Tags) Tags() []*Tag

func (Tags) Unique

func (t Tags) Unique() (unique Tags)

type TagsFunc

type TagsFunc func() Tags

TagsFunc creates a TagSet implementation from the given function.

func (TagsFunc) Tags

func (t TagsFunc) Tags() []*Tag

type TimeFormatter

type TimeFormatter struct {
	TimeFormat string
	Location   *time.Location
}

TimeFormatter is a Formatter implementation that formats the Time of an Event using the time package's formatter.

func NewTimeFormatter

func NewTimeFormatter(format string, location *time.Location) *TimeFormatter

NewTimeFormatter creates a new TimeFormatter with the given format and time.Location.

func (*TimeFormatter) Format

func (t *TimeFormatter) Format(event *Event) []byte

type Writer

type Writer struct {
	Formatter
	Writer io.Writer

	// OnWriteFail is called when the Writer is unable to write an Event to the underlying
	// io.Writer. If OnWriteFail is nil, write failures will cause a Writer to panic.
	OnWriteFail func(error)
	// contains filtered or unexported fields
}

Writer is a Subscriber implementation that writes events to an io.Writer using a Formatter to convert events into byte slices.

func NewWriter

func NewWriter(writer io.Writer) *Writer

NewWriter makes a new Writer for the given io.Writer, using MessageOnlyFormatter as its formatter.

func NewWriterWithFormat

func NewWriterWithFormat(writer io.Writer, format Formatter) *Writer

NewWriterWithFormat makes a new Writer for the given io.Writer, using the given Formatter.

func (*Writer) Log

func (w *Writer) Log(event *Event)

Directories

Path Synopsis
Package testing provides simple assertion tools for writing unit tests.
Package testing provides simple assertion tools for writing unit tests.

Jump to

Keyboard shortcuts

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