golang-samber-slog

bởi samber

Phần mở rộng ghi log có cấu trúc cho Golang sử dụng các gói samber/slog-**** — pipeline xử lý đa handler (slog-multi), lấy mẫu log (slog-sampling), định dạng thuộc tính (slog-formatter), middleware HTTP (slog-fiber, slog-gin, slog-chi, slog-echo), và định tuyến backend (slog-datadog, slog-sentry, slog-loki, slog-syslog, slog-logstash, slog-graylog...). Áp dụng khi sử dụng hoặc áp dụng slog, hoặc khi codebase đã import bất kỳ gói github.com/samber/slog-* nào.

npx skills add https://github.com/samber/cc-skills-golang --skill golang-samber-slog

Persona: You are a Go logging architect. You design log pipelines where every record flows through the right handlers — sampling drops noise early, formatters strip PII before records leave the process, and routers send errors to Sentry while info goes to Loki.

samber/slog-**** — Structured Logging Pipeline for Go

20+ composable slog.Handler packages for Go 1.21+. Three core pipeline libraries plus HTTP middlewares and backend sinks that all implement the standard slog.Handler interface.

Official resources:

This skill is not exhaustive. Please refer to library documentation and code examples for more information. Context7 can help as a discoverability platform.

The Pipeline Model

Every samber/slog pipeline follows a canonical ordering. Records flow left to right — place sampling first to drop early and avoid wasting CPU on records that never reach a sink.

record → [Sampling] → [Pipe: trace/PII] → [Router] → [Sinks]

Order matters: sampling before formatting saves CPU. Formatting before routing ensures all sinks receive clean attributes. Reversing this wastes work on records that get dropped.

Core Libraries

LibraryPurposeKey constructors
slog-multiHandler compositionFanout, Router, FirstMatch, Failover, Pool, Pipe
slog-samplingThroughput controlUniformSamplingOption, ThresholdSamplingOption, AbsoluteSamplingOption, CustomSamplingOption
slog-formatterAttribute transformsPIIFormatter, ErrorFormatter, FormatByType[T], FormatByKey, FlattenFormatterMiddleware

slog-multi — Handler Composition

Six composition patterns, each for a different routing need:

PatternBehaviorLatency impact
Fanout(handlers...)Broadcast to all handlers sequentiallySum of all handler latencies
Router().Add(h, predicate).Handler()Route to ALL matching handlersSum of matching handlers
Router().Add(...).FirstMatch().Handler()Route to FIRST match onlySingle handler latency
Failover()(handlers...)Try sequentially until one succeedsPrimary handler latency (happy path)
Pool()(handlers...)Load-balance: sends each record to ONE handlerSingle handler latency
Pipe(middlewares...).Handler(sink)Middleware chain before sinkMiddleware overhead + sink
// Route errors to Sentry, all logs to stdout
logger := slog.New(
    slogmulti.Router().
        Add(sentryHandler, slogmulti.LevelIs(slog.LevelError)).
        Add(slog.NewJSONHandler(os.Stdout, nil)).
        Handler(),
)

Built-in predicates: LevelIs, LevelIsNot, MessageIs, MessageIsNot, MessageContains, MessageNotContains, AttrValueIs, AttrKindIs.

For full code examples of every pattern, see Pipeline Patterns.

slog-sampling — Throughput Control

StrategyBehaviorBest for
UniformDrop fixed % of all recordsDev/staging noise reduction
ThresholdLog first N per interval, then sample at rate RProduction — preserves initial visibility
AbsoluteCap at N records per interval globallyHard cost control
CustomUser function returns sample rate per recordLevel-aware or time-aware rules

Sampling MUST be the outermost handler in the pipeline — placing it after formatting wastes CPU on records that get dropped.

// Threshold: log first 10 per 5s, then 10% — errors always pass through via Router
logger := slog.New(
    slogmulti.
        Pipe(slogsampling.ThresholdSamplingOption{
            Tick: 5 * time.Second, Threshold: 10, Rate: 0.1,
        }.NewMiddleware()).
        Handler(innerHandler),
)

Matchers group similar records for deduplication: MatchByLevel(), MatchByMessage(), MatchByLevelAndMessage() (default), MatchBySource(), MatchByAttribute(groups, key).

For strategy comparison and configuration details, see Sampling Strategies.

slog-formatter — Attribute Transformation

Apply as a Pipe middleware so all downstream handlers receive clean attributes.

logger := slog.New(
    slogmulti.Pipe(slogformatter.NewFormatterMiddleware(
        slogformatter.PIIFormatter("user"),          // mask PII fields
        slogformatter.ErrorFormatter("error"),       // structured error info
        slogformatter.IPAddressFormatter("client"),  // mask IP addresses
    )).Handler(slog.NewJSONHandler(os.Stdout, nil)),
)

Key formatters: PIIFormatter, ErrorFormatter, TimeFormatter, UnixTimestampFormatter, IPAddressFormatter, HTTPRequestFormatter, HTTPResponseFormatter. Generic formatters: FormatByType[T], FormatByKey, FormatByKind, FormatByGroup, FormatByGroupKey. Flatten nested attributes with FlattenFormatterMiddleware.

HTTP Middlewares

Consistent pattern across frameworks: router.Use(slogXXX.New(logger)).

Available: slog-gin, slog-echo, slog-fiber, slog-chi, slog-http (net/http).

All share a Config struct with: DefaultLevel, ClientErrorLevel, ServerErrorLevel, WithRequestBody, WithResponseBody, WithUserAgent, WithRequestID, WithTraceID, WithSpanID, Filters.

// Gin with filters — skip health checks
router.Use(sloggin.NewWithConfig(logger, sloggin.Config{
    DefaultLevel:     slog.LevelInfo,
    ClientErrorLevel: slog.LevelWarn,
    ServerErrorLevel: slog.LevelError,
    WithRequestBody:  true,
    Filters: []sloggin.Filter{
        sloggin.IgnorePath("/health", "/metrics"),
    },
}))

For framework-specific setup, see HTTP Middlewares.

Backend Sinks

All follow the Option{}.NewXxxHandler() constructor pattern.

CategoryPackages
Cloudslog-datadog, slog-sentry, slog-loki, slog-graylog
Messagingslog-kafka, slog-fluentd, slog-logstash, slog-nats
Notificationslog-slack, slog-telegram, slog-webhook
Storageslog-parquet
Bridgesslog-zap, slog-zerolog, slog-logrus

Batch handlers require graceful shutdownslog-datadog, slog-loki, slog-kafka, and slog-parquet buffer records internally. Flush on shutdown (e.g., handler.Stop(ctx) for Datadog, lokiClient.Stop() for Loki, writer.Close() for Kafka) or buffered logs are lost.

For configuration examples and shutdown patterns, see Backend Handlers.

Common Mistakes

MistakeWhy it failsFix
Sampling after formattingWastes CPU formatting records that get droppedPlace sampling as outermost handler
Fanout to many synchronous handlersBlocks caller — latency is sum of all handlersUse Pool() for concurrent dispatch
Missing shutdown flush on batch handlersBuffered logs lost on shutdowndefer handler.Stop(ctx) (Datadog), defer lokiClient.Stop() (Loki), defer writer.Close() (Kafka)
Router without default/catch-all handlerUnmatched records silently droppedAdd a handler with no predicate as catch-all
AttrFromContext without HTTP middlewareContext has no request attributes to extractInstall slog-gin/echo/fiber/chi middleware first
Using Pipe with no middlewareNo-op wrapper adding per-record overheadRemove Pipe() if no middleware needed

Performance Warnings

  • Fanout latency = sum of all handler latencies (sequential). With 5 handlers at 10ms each, every log call costs 50ms. Use Pool() to reduce to max(latencies)
  • Pipe middleware adds per-record function call overhead — keep chains short (2-4 middlewares)
  • slog-formatter processes attributes sequentially — many formatters compound. For hot-path attribute formatting, prefer implementing slog.LogValuer on your types instead
  • Benchmark your pipeline with go test -bench before production deployment

Diagnose: measure per-record allocation and latency of your pipeline and identify which handler in the chain allocates most.

Best Practices

  1. Sample first, format second, route last — this canonical ordering minimizes wasted work and ensures all sinks see clean data
  2. Use Pipe for cross-cutting concerns — trace ID injection and PII scrubbing belong in middleware, not per-handler logic
  3. Test pipelines with slogmulti.NewHandleInlineHandler — assert on records reaching each stage without real sinks
  4. Use AttrFromContext to propagate request-scoped attributes from HTTP middleware to all handlers
  5. Prefer Router over Fanout when handlers need different record subsets — Router evaluates predicates and skips non-matching handlers

Cross-References

  • → See samber/cc-skills-golang@golang-observability skill for slog fundamentals (levels, context, handler setup, migration)
  • → See samber/cc-skills-golang@golang-error-handling skill for the log-or-return rule
  • → See samber/cc-skills-golang@golang-security skill for PII handling in logs
  • → See samber/cc-skills-golang@golang-samber-oops skill for structured error context with samber/oops

If you encounter a bug or unexpected behavior in any samber/slog-* package, open an issue at the relevant repository (e.g., slog-multi/issues, slog-sampling/issues).

Thêm skills từ samber

golang-code-style
samber
Golang code style conventions — line length and breaking, variable declarations, control flow clarity, when comments help vs hurt. Use when writing or reviewing Go code, asking about style or clarity, or establishing project coding standards. Not for naming conventions (→ See `samber/cc-skills-golang@golang-naming` skill), linter configuration (→ See `samber/cc-skills-golang@golang-lint` skill), or doc comments (→ See `samber/cc-skills-golang@golang-documentation` skill).
developmentcode-review
golang-testing
samber
Production-ready Golang tests — table-driven tests, testify suites and mocks, parallel tests, fuzzing, fixtures, goroutine leak detection with goleak, snapshot testing, code coverage, integration tests, idiomatic test naming. Use when writing or reviewing Go tests, choosing a testing approach, setting up Go test CI, or debugging flaky/slow tests. For testify-specific APIs see `samber/cc-skills-golang@golang-stretchr-testify`; for measurement methodology see...
developmenttestingcode-review
golang-design-patterns
samber
Các mẫu thiết kế Golang theo phong cách bản địa — tùy chọn hàm, hàm khởi tạo, luồng lỗi và xếp tầng, quản lý tài nguyên và vòng đời, tắt máy an toàn, khả năng phục hồi, kiến trúc, tiêm phụ thuộc, xử lý dữ liệu, truyền phát, v.v. Áp dụng khi lựa chọn rõ ràng giữa các mẫu kiến trúc, triển khai tùy chọn hàm, thiết kế API hàm khởi tạo, thiết lập tắt máy an toàn, áp dụng các mẫu phục hồi, hoặc hỏi mẫu Go bản địa nào phù hợp với một vấn đề cụ thể.
developmentdesigncode-review
golang-error-handling
samber
Idiomatic Golang error handling — creation, wrapping with %w, errors.Is/As, errors.Join, custom error types, sentinel errors, panic/recover, the single handling rule, structured logging with slog, HTTP request logging middleware, and samber/oops for production errors. Built to make logs usable at scale with log aggregation 3rd-party tools. Apply when creating, wrapping, inspecting, or logging errors in Go code. For samber/oops specifics → See `samber/cc-skills-golang@golang-samber-oops`...
developmentcode-review
golang-performance
samber
Các mẫu và phương pháp tối ưu hiệu năng Golang - nếu X là điểm nghẽn, thì áp dụng Y. Bao gồm giảm cấp phát, hiệu quả CPU, bố trí bộ nhớ, tinh chỉnh GC, pooling, caching, và tối ưu đường dẫn nóng. Sử dụng khi profiling hoặc benchmark đã xác định được điểm nghẽn và bạn cần mẫu tối ưu phù hợp để khắc phục. Cũng sử dụng khi thực hiện đánh giá mã hiệu năng để đề xuất cải tiến hoặc benchmark có thể giúp xác định các cải thiện hiệu năng nhanh chóng. Không dành cho phương pháp đo lường (→...
developmentcode-review
golang-security
samber
Các phương pháp bảo mật tốt nhất và phòng ngừa lỗ hổng cho Golang. Bao gồm injection (SQL, lệnh, XSS), mật mã học, an toàn hệ thống tệp, bảo mật mạng, cookie, quản lý bí mật, an toàn bộ nhớ và ghi nhật ký. Áp dụng khi viết, xem xét hoặc kiểm tra mã Go về bảo mật, hoặc khi làm việc trên bất kỳ mã rủi ro nào liên quan đến mật mã, I/O, quản lý bí mật, xử lý đầu vào người dùng hoặc xác thực. Bao gồm cấu hình các công cụ bảo mật.
securitycode-reviewdevelopment
golang-database
samber
Hướng dẫn toàn diện về truy cập cơ sở dữ liệu Go — truy vấn tham số hóa, quét struct, cột NULL, giao dịch, mức cô lập, SELECT FOR UPDATE, connection pool, xử lý hàng loạt, truyền context và công cụ migration. Sử dụng khi viết, xem xét hoặc gỡ lỗi mã Golang tương tác với PostgreSQL, MariaDB, MySQL hoặc SQLite; để kiểm thử cơ sở dữ liệu; hoặc cho các câu hỏi về database/sql, sqlx hoặc pgx. KHÔNG tạo lược đồ cơ sở dữ liệu hoặc SQL migration.
developmentdatabase
golang-lint
samber
Các phương pháp linting tốt nhất và cấu hình golangci-lint cho các dự án Golang — chạy linters, cấu hình .golangci.yml, loại bỏ cảnh báo bằng chỉ thị nolint, diễn giải đầu ra lint, và lựa chọn linters. Sử dụng khi cấu hình golangci-lint, hỏi về cảnh báo lint hoặc loại bỏ nolint, thiết lập công cụ chất lượng mã, hoặc chọn linters. Cũng sử dụng khi người dùng đề cập đến golangci-lint, go vet, staticcheck, hoặc revive.
developmentcode-reviewtesting