Skip to content

Commit

Permalink
chore: switch to slog for logging (#253)
Browse files Browse the repository at this point in the history
  • Loading branch information
verbotenj authored Sep 24, 2024
1 parent 82c08a7 commit 4604e48
Show file tree
Hide file tree
Showing 10 changed files with 107 additions and 121 deletions.
30 changes: 14 additions & 16 deletions cmd/adder/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -86,22 +86,14 @@ func main() {
// Configure logging
logging.Configure()
logger := logging.GetLogger()
// Sync logger on exit
defer func() {
if err := logger.Sync(); err != nil {
// We don't actually care about the error here, but we have to do something
// to appease the linter
return
}
}()

// Start debug listener
if cfg.Debug.ListenPort > 0 {
logger.Infof(
logger.Info(fmt.Sprintf(
"starting debug listener on %s:%d",
cfg.Debug.ListenAddress,
cfg.Debug.ListenPort,
)
))
go func() {
err := http.ListenAndServe(
fmt.Sprintf(
Expand All @@ -112,7 +104,8 @@ func main() {
nil,
)
if err != nil {
logger.Fatalf("failed to start debug listener: %s", err)
logger.Error(fmt.Sprintf("failed to start debug listener: %s", err))
os.Exit(1)
}
}()
}
Expand All @@ -129,7 +122,8 @@ func main() {
// Configure input
input := plugin.GetPlugin(plugin.PluginTypeInput, cfg.Input)
if input == nil {
logger.Fatalf("unknown input: %s", cfg.Input)
logger.Error(fmt.Sprintf("unknown input: %s", cfg.Input))
os.Exit(1)
}
pipe.AddInput(input)

Expand All @@ -142,7 +136,8 @@ func main() {
// Configure output
output := plugin.GetPlugin(plugin.PluginTypeOutput, cfg.Output)
if output == nil {
logger.Fatalf("unknown output: %s", cfg.Output)
logger.Error(fmt.Sprintf("unknown output: %s", cfg.Output))
os.Exit(1)
}
// Check if output plugin implements APIRouteRegistrar
if registrar, ok := interface{}(output).(api.APIRouteRegistrar); ok {
Expand All @@ -152,15 +147,18 @@ func main() {

// Start API after plugins are configured
if err := apiInstance.Start(); err != nil {
logger.Fatalf("failed to start API: %s", err)
logger.Error(fmt.Sprintf("failed to start API: %s", err))
os.Exit(1)
}

// Start pipeline and wait for error
if err := pipe.Start(); err != nil {
logger.Fatalf("failed to start pipeline: %s", err)
logger.Error(fmt.Sprintf("failed to start pipeline: %s", err))
os.Exit(1)
}
err, ok := <-pipe.ErrorChan()
if ok {
logger.Fatalf("pipeline failed: %s", err)
logger.Error(fmt.Sprintf("pipeline failed: %s", err))
os.Exit(1)
}
}
4 changes: 3 additions & 1 deletion fcm/message.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import (
"fmt"
"io"
"net/http"
"os"

"github.com/blinklabs-io/adder/internal/logging"
)
Expand Down Expand Up @@ -45,7 +46,8 @@ func WithNotification(title string, body string) MessageOption {

func NewMessage(token string, opts ...MessageOption) *Message {
if token == "" {
logging.GetLogger().Fatalf("Token is mandatory for FCM message")
logging.GetLogger().Error("Token is mandatory for FCM message")
os.Exit(1)
}

msg := &Message{
Expand Down
2 changes: 0 additions & 2 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ require (
github.com/swaggo/gin-swagger v1.6.0
github.com/swaggo/swag v1.16.3
go.uber.org/automaxprocs v1.5.3
go.uber.org/zap v1.27.0
golang.org/x/oauth2 v0.23.0
gopkg.in/yaml.v2 v2.4.0
)
Expand Down Expand Up @@ -62,7 +61,6 @@ require (
github.com/ugorji/go/codec v1.2.12 // indirect
github.com/utxorpc/go-codegen v0.9.0 // indirect
github.com/x448/float16 v0.8.4 // indirect
go.uber.org/multierr v1.10.0 // indirect
golang.org/x/arch v0.8.0 // indirect
golang.org/x/crypto v0.27.0 // indirect
golang.org/x/net v0.25.0 // indirect
Expand Down
4 changes: 0 additions & 4 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -145,10 +145,6 @@ go.uber.org/automaxprocs v1.5.3 h1:kWazyxZUrS3Gs4qUpbwo5kEIMGe/DAvi5Z4tl2NW4j8=
go.uber.org/automaxprocs v1.5.3/go.mod h1:eRbA25aqJrxAbsLO0xy5jVwPt7FQnRgjW+efnwa1WM0=
go.uber.org/goleak v1.3.0 h1:2K3zAYmnTNqV73imy9J1T3WC+gmCePx2hEGkimedGto=
go.uber.org/goleak v1.3.0/go.mod h1:CoHD4mav9JJNrW/WLlf7HGZPjdw8EucARQHekz1X6bE=
go.uber.org/multierr v1.10.0 h1:S0h4aNzvfcFsC3dRF1jLoaov7oRaKqRGC/pUEJ2yvPQ=
go.uber.org/multierr v1.10.0/go.mod h1:20+QtiLqy0Nd6FdQB9TLXag12DsQkrbs3htMFfDN80Y=
go.uber.org/zap v1.27.0 h1:aJMhYGrd5QSmlpLMr2MftRKl7t8J8PTZPA732ud/XR8=
go.uber.org/zap v1.27.0/go.mod h1:GB2qFLM7cTU87MWRP2mPIjqfIDnGu+VIO4V/SdhGo2E=
golang.org/x/arch v0.0.0-20210923205945-b76863e36670/go.mod h1:5om86z9Hs0C8fWVUuoMHwpExlXzs5Tkyp9hOrfG7pp8=
golang.org/x/arch v0.8.0 h1:3wRIsP3pM4yUptoR96otTUOXI367OS0+c9eeRi9doIc=
golang.org/x/arch v0.8.0/go.mod h1:FEVrYAQjsQXMVJ1nsMoVVXPZg6p2JE2mx8psSWTDQys=
Expand Down
18 changes: 9 additions & 9 deletions input/chainsync/chainsync.go
Original file line number Diff line number Diff line change
Expand Up @@ -216,7 +216,7 @@ func (c *ChainSync) setupConnection() error {
return err
}
if c.logger != nil {
c.logger.Infof("connected to node at %s", c.dialAddress)
c.logger.Info(fmt.Sprintf("connected to node at %s", c.dialAddress))
}
// Start async error handler
go func() {
Expand All @@ -225,18 +225,18 @@ func (c *ChainSync) setupConnection() error {
if c.autoReconnect {
c.autoReconnectDelay = 0
if c.logger != nil {
c.logger.Infof(
c.logger.Info(fmt.Sprintf(
"reconnecting to %s due to error: %s",
c.dialAddress,
err,
)
))
}
for {
if c.autoReconnectDelay > 0 {
c.logger.Infof(
c.logger.Info(fmt.Sprintf(
"waiting %s to reconnect",
c.autoReconnectDelay,
)
))
time.Sleep(c.autoReconnectDelay)
// Double current reconnect delay up to maximum
c.autoReconnectDelay = min(
Expand All @@ -250,10 +250,10 @@ func (c *ChainSync) setupConnection() error {
// Shutdown current connection
if err := c.oConn.Close(); err != nil {
if c.logger != nil {
c.logger.Warnf(
c.logger.Warn(fmt.Sprintf(
"failed to properly close connection: %s",
err,
)
))
}
}
// Set the intersect points from the cursor cache
Expand All @@ -263,11 +263,11 @@ func (c *ChainSync) setupConnection() error {
// Restart the connection
if err := c.Start(); err != nil {
if c.logger != nil {
c.logger.Infof(
c.logger.Info(fmt.Sprintf(
"reconnecting to %s due to error: %s",
c.dialAddress,
err,
)
))
}
continue
}
Expand Down
72 changes: 31 additions & 41 deletions internal/logging/logging.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,59 +15,49 @@
package logging

import (
"log"
"log/slog"
"os"
"time"

"github.com/blinklabs-io/adder/internal/config"

"go.uber.org/zap"
"go.uber.org/zap/zapcore"
)

type Logger = zap.SugaredLogger

var globalLogger *Logger
var globalLogger *slog.Logger

func Configure() {
cfg := config.GetConfig()
// Build our custom logging config
loggerConfig := zap.NewProductionConfig()
// Change timestamp key name
loggerConfig.EncoderConfig.TimeKey = "timestamp"
// Use a human readable time format
loggerConfig.EncoderConfig.EncodeTime = zapcore.TimeEncoderOfLayout(
time.RFC3339,
)

// Set level
if cfg.Logging.Level != "" {
level, err := zapcore.ParseLevel(cfg.Logging.Level)
if err != nil {
log.Fatalf("error configuring logger: %s", err)
}
loggerConfig.Level.SetLevel(level)
var level slog.Level
switch cfg.Logging.Level {
case "debug":
level = slog.LevelDebug
case "info":
level = slog.LevelInfo
case "warn":
level = slog.LevelWarn
case "error":
level = slog.LevelError
default:
level = slog.LevelInfo
}

// Create the logger
l, err := loggerConfig.Build()
if err != nil {
log.Fatal(err)
}
handler := slog.NewJSONHandler(os.Stdout, &slog.HandlerOptions{
ReplaceAttr: func(groups []string, a slog.Attr) slog.Attr {
if a.Key == slog.TimeKey {
// Format the time attribute to use RFC3339 or your custom format
// Rename the time key to timestamp
return slog.String("timestamp", a.Value.Time().Format(time.RFC3339))
}
return a
},
Level: level,
})
globalLogger = slog.New(handler).With("component", "main")

// Store the "sugared" version of the logger
globalLogger = l.Sugar()
}

func GetLogger() *zap.SugaredLogger {
func GetLogger() *slog.Logger {
if globalLogger == nil {
Configure()
}
return globalLogger
}

func GetDesugaredLogger() *zap.Logger {
return globalLogger.Desugar()
}

func GetAccessLogger() *zap.Logger {
return globalLogger.Desugar().
With(zap.String("type", "access")).
WithOptions(zap.WithCaller(false))
}
27 changes: 13 additions & 14 deletions output/log/log.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@
package log

import (
"log/slog"

"github.com/blinklabs-io/adder/event"
"github.com/blinklabs-io/adder/internal/logging"
"github.com/blinklabs-io/adder/plugin"
Expand All @@ -24,7 +26,7 @@ type LogOutput struct {
errorChan chan error
eventChan chan event.Event
logger plugin.Logger
outputLogger *logging.Logger
outputLogger *slog.Logger
level string
}

Expand All @@ -40,16 +42,13 @@ func New(options ...LogOptionFunc) *LogOutput {
if l.logger == nil {
l.logger = logging.GetLogger()
}
// Determine if we can use the provided logger or need our own
// This is necessary because this plugin uses logger functions that aren't part
// of the plugin.Logger interface
switch v := l.logger.(type) {
case *logging.Logger:
l.outputLogger = v
default:
l.outputLogger = logging.GetLogger()

// Use the provided *slog.Logger if available, otherwise fall back to global logger
if providedLogger, ok := l.logger.(*slog.Logger); ok {
l.outputLogger = providedLogger.With("type", "event")
} else {
l.outputLogger = logging.GetLogger().With("type", "event")
}
l.outputLogger = l.outputLogger.With("type", "event")
return l
}

Expand All @@ -64,14 +63,14 @@ func (l *LogOutput) Start() error {
}
switch l.level {
case "info":
l.outputLogger.Infow("", "event", evt)
l.outputLogger.Info("", "event", evt)
case "warn":
l.outputLogger.Warnw("", "event", evt)
l.outputLogger.Warn("", "event", evt)
case "error":
l.outputLogger.Errorw("", "event", evt)
l.outputLogger.Error("", "event", evt)
default:
// Use INFO level if log level isn't recognized
l.outputLogger.Infow("", "event", evt)
l.outputLogger.Info("", "event", evt)
}
}
}()
Expand Down
Loading

0 comments on commit 4604e48

Please sign in to comment.