Go📦Standard Libraryintermediate
log/slog — Structured Logging (Go 1.21+)
Go · Standard Library · Run with go run
Explanation
`log/slog`, added in Go 1.21, provides structured logging with key-value pairs. Logs can be emitted as human-readable text or machine-readable JSON. `slog.Info("message", "key", value)` is the idiomatic call. Custom handlers can route logs to any backend (stdout, file, observability platform).
Real-World Scenario
In production microservices, JSON logs are ingested by log aggregators (Datadog, Loki, Elasticsearch). `slog` with `JSONHandler` produces `{"time":"...","level":"INFO","msg":"request","method":"GET","path":"/api/users","latency_ms":42}` — indexable and filterable without custom parsing.
Quick Snippet
snippet.go
import "log/slog"
// Default text handler (human readable)
slog.Info("server started", "port", 8080)
// time=2024-01-15T10:00:00Z level=INFO msg="server started" port=8080
// JSON handler for production
logger := slog.New(slog.NewJSONHandler(os.Stdout, nil))
logger.Info("request",
"method", r.Method,
"path", r.URL.Path,
"status", 200,
"latency_ms", latency.Milliseconds(),
)
// Logger with persistent attributes
reqLogger := logger.With("request_id", reqID, "user_id", userID)
reqLogger.Info("processing")
reqLogger.Error("failed", "error", err)Full Example
slog_logging.go
// Compile: go run slog_logging.go
// Output (JSON lines, time will vary):
// {"time":"...","level":"INFO","msg":"server started","port":8080}
// {"time":"...","level":"INFO","msg":"request","method":"GET","path":"/api"}
// {"time":"...","level":"ERROR","msg":"failed","request_id":"req-1","error":"timeout"}
package main
import (
"log/slog"
"os"
)
func main() {
logger := slog.New(slog.NewJSONHandler(os.Stdout, nil))
logger.Info("server started", "port", 8080)
logger.Info("request", "method", "GET", "path", "/api")
// Logger with persistent attributes
reqLogger := logger.With("request_id", "req-1")
reqLogger.Error("failed", "error", "timeout")
}
Run command
go run slog_logging.go