logx

package module
v1.5.2 Latest Latest
Warning

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

Go to latest
Published: Aug 13, 2026 License: MIT Imports: 2 Imported by: 0

README

logx

Go Version License Zero Dependencies

工业级 · 零依赖 · 极致性能 · 可插拔 的 Go 语言结构化日志库。

logx 兼具 Zap 的极致性能与 Logrus 的易用性,通过链式 Builder API 实现业务与底层日志逻辑的完美解耦。纯标准库实现,不引入任何第三方依赖。

指标统一外置:NewBuilder().WithMetrics(metricsx 实例) 即可把 日志记录/文件写入/轮转/压缩/清理事件转发到家族 metricsx 底座。


快速开始

安装
go get github.com/lcylpzls/logx
最小示例
package main

import "github.com/lcylpzls/logx"

func main() {
    logger, _ := logx.NewBuilder().
        EnableConsole(logx.InfoLevel).
        Build()

    logger.Info("服务启动成功", logx.Fields(logx.Int("port", 8080)))
}

输出:

2026-06-06 15:04:05.000 INFO   服务启动成功  {port=8080}

核心特性

  • 全链路零分配 — 2MB 缓冲池 + Entry 池化 + 内联字段容器 + 异步槽位复用,控制台/同步文件/异步文件路径均实测 0 allocs/op
  • 🔌 可插拔架构 — Encoder / Appender 接口完全解耦,支持自定义扩展
  • 📝 双模式 API — 同时支持结构化字段(Info("msg", logx.Fields(logx.Int("k", v))))和传统格式化(Infof("k=%d", v)
  • 🎨 控制台色彩 — 按级别高亮(Debug 蓝 / Info 绿 / Warn 黄 / Error 红),落盘自动剥离
  • 📁 工业级文件管理 — 原子切割(大小+时间)、Symlink 软链接、Gzip 压缩、自动清理
  • ⚙️ 双引擎写入 — 异步批量(高吞吐)与绝对同步(强可靠)随意切换
  • 🧾 JSON 编码器 — 单行 JSON 输出,无缝对接 ELK / Loki 等日志采集系统
  • 🎛️ 动态级别 — 运行时热更新日志级别,无需重启服务
  • 🧯 采样与脱敏 — 每秒限流防故障风暴,敏感字段自动打码
  • 🔌 自定义 Writer — 任意 io.Writer 输出通道(网络、消息队列等)
  • 📊 可观测指标 — 写入/丢弃/轮转/压缩计数,Metrics() 一键获取
  • 🛡️ 统一错误回调 — 轮转、清理、压缩失败不再静默吞掉
  • 🛡️ 默认静默 — 所有通道/级别默认关闭,必须显式传入级别参数,避免隐式开销
  • 🔗 零外部依赖 — 纯 Go 标准库,不引入任何第三方模块
  • 📍 调用者追踪 — 一键 WithCaller() 定位日志源码位置,零性能开销

使用指南

1. 链式 Builder 配置

logx 强制使用 Builder 模式初始化,支持多通道精细化控制。所有输出默认静默,必须显式开启。

logger, err := logx.NewBuilder().
    WithCaller(). // 开启调用者追踪
    // -------- 控制台通道 --------
    EnableConsole(logx.DebugLevel, logx.WithColor()).
    // -------- 文件通道 --------
    EnableFileLog(
        logx.WithLogDir("/var/log/myapp"),
        logx.WithFilename("app.log"),
        logx.WithMaxSize(100),       // 单文件最大 100MB
        logx.WithMaxAge(180),        // 保留 180 天
        logx.WithCompressAfter(7),   // 7 天后 gzip 压缩
        logx.WithWriteMode(logx.AsyncWriteMode),
        logx.WithLevels(logx.InfoLevel),
    ).
    Build()
if err != nil {
    panic(err)
}
defer logger.Close()
2. 日志输出
// 结构化 API(零反射,推荐)
logger.Info("用户登录", logx.Fields(logx.String("user", "admin"), logx.Int("attempt", 3)))
logger.Debug("SQL 查询", logx.Fields(logx.String("sql", "SELECT * FROM users"), logx.Int64("elapsed_ms", 12)))
logger.Error("连接失败", logx.Fields(logx.Err(err)))

// 格式化 API
logger.Infof("第 %d 次重试", retry)
logger.Errorf("处理失败:%v", err)

// 特殊级别
logger.Panic("不可恢复的错误", logx.FieldGroup{})  // 刷盘后触发 panic
logger.Fatal("致命错误", logx.FieldGroup{})       // 刷盘后 os.Exit(1)
3. 结构化字段
logx.String("key", "value")      // 字符串
logx.Int("count", 42)            // int
logx.Int64("id", 123456789)      // int64
logx.Bool("enabled", true)       // 布尔
logx.Err(err)                    // 错误(key 固定为 "error")
logx.Any("data", myStruct)       // 任意类型(后备方案)
4. 延迟求值 Lazy

当 Debug 未开启时,避免执行昂贵的计算:

logger.Debug("用户详情", logx.Fields(logx.Lazy("info", func() any {
    return expensiveDBQuery()  // 仅在 Debug 启用时才执行
})))
5. 派生 Logger
// 携带链路上下文
ctx := context.WithValue(context.Background(), "trace_id", "abc123")
traceLogger := logger.WithContext(ctx)

// 固定字段
userLogger := logger.WithField("user_id", "10086")
userLogger.Info("操作成功", logx.FieldGroup{}) // 自动携带 user_id=10086
6. 写入模式
模式 吞吐 可靠性 适用场景
AsyncWriteMode(默认) 极高 进程崩溃可能丢失少量 高并发 API、微服务
SyncWriteMode 受限于磁盘 强保证,不会丢失 金融、审计、核心事务
EnableFileLog(
    logx.WithWriteMode(logx.SyncWriteMode),
    logx.WithLevels(logx.InfoLevel),
)
7. 优雅退出 SafeExit

在异步模式下,os.Exit 会导致缓冲日志丢失。使用 SafeExit 确保临终日志落盘:

// ❌ 错误:异步日志会丢失
os.Exit(1)

// ✅ 正确:先刷盘再退出
logger.SafeExit(func() {
    os.Exit(1)
})

FatalPanic 级别内部已集成刷盘逻辑,无需额外处理。

8. 调用者追踪 WithCaller

开启后自动在日志中追加源文件名和行号:

logger, _ := logx.NewBuilder().
    WithCaller().                    // 开启调用者追踪
    EnableFileLog(
        logx.WithLogDir("./logs"),
        logx.WithFilename("app.log"),
        logx.WithLevels(logx.InfoLevel),
    ).
    Build()

logger.Info("服务启动", logx.FieldGroup{})
// 输出:2026-06-06 15:04:05.000 INFO  main.go:15  服务启动

路径格式为 Zap TrimmedPath() 同款——保留包目录/文件名两级,零额外内存分配。

9. 劫持标准库 log

一行代码将老项目中所有的 log.Println 路由到 logx:

logx.ReplaceStdLogger(logger)
defer logx.RestoreStdLogger()

// 标准库调用自动流经 logx 引擎
log.Println("这条日志由 logx 接管")
10. Hook 扩展

注册 Hook 实现告警、监控等自定义逻辑:

type AlertHook struct{}

func (h *AlertHook) OnLog(e *logx.Entry) {
    if e.Level >= logx.ErrorLevel {
        sendAlert(e.Message) // 飞书/钉钉/邮件...
    }
}

logger.(logx.HookedLogger).AddHook(&AlertHook{})

Hook 以异步 goroutine 执行,内置 panic recovery,绝不阻塞日志主路径。

11. JSON 编码

文件/自定义通道可通过 WithEncoder 切换为单行 JSON:

logger, _ := logx.NewBuilder().
    WithEncoder(logx.NewJSONEncoder()).
    EnableFileLog(
        logx.WithLogDir("/var/log/myapp"),
        logx.WithFilename("app.log"),
        logx.WithLevels(logx.InfoLevel),
    ).
    Build()

输出示例:

{"time":"2026-06-06 15:04:05.000","level":"info","caller":"main.go:15","message":"服务启动成功","port":8080}
12. 动态级别热更新

运行时调整日志级别,无需重建 Logger(默认实现支持 LevelUpdater 可选接口):

if lu, ok := logger.(logx.LevelUpdater); ok {
    lu.SetLevel(logx.DebugLevel) // 热切换为 Debug
}
13. 采样与脱敏
logger, _ := logx.NewBuilder().
    WithSampling(1000).               // 每秒最多输出 1000 条,超出丢弃
    WithRedact("password", "token").  // 匹配字段自动替换为 ***
    EnableConsole(logx.InfoLevel).
    Build()
14. 自定义 io.Writer 通道
logger, _ := logx.NewBuilder().
    EnableWriter(myNetworkWriter, logx.InfoLevel).
    Build()
15. 错误处理与运行指标

文件通道内部错误(轮转/清理/压缩失败)统一交给回调,不再静默吞掉:

EnableFileLog(
    logx.WithErrorHandler(func(err error) { monitor.Report(err) }),
)

通过可选接口 MetricProvider 获取原子计数:

if mp, ok := logger.(logx.MetricProvider); ok {
    m := mp.Metrics() // Writes / WriteBytes / Rotations / Compressions / Cleanups
}
16. 信号与优雅退出

SafeExit 之外,生产环境推荐配合系统信号使用(完整示例见 examples/graceful_shutdown):

ctx, stop := signal.NotifyContext(context.Background(), os.Interrupt, syscall.SIGTERM)
defer stop()
<-ctx.Done()
logger.Sync() // 先刷盘再退出

性能基准

实测环境:AMD Ryzen 5 7600 / Windows / Go 1.26.5;单条日志含时间 + 级别 + 消息 + 3 个字段

微基准
指标 logx 说明
TextEncoder 简单日志(编码路径) 22.1 ns/op, 0 B, 0 allocs 零分配纯字节拼接
TextEncoder 含字段(编码路径) 54.2 ns/op, 0 B, 0 allocs 强类型字段分发
端到端(io.Discard,3 字段) 122.8 ns/op, 0 B, 0 allocs Entry 池化 + 内联字段容器
文件异步写入(3 字段) 230.6 ns/op, 0 allocs 槽位复用 + 有界背压
文件同步写入(3 字段) 2927 ns/op, 0 allocs 直接落盘
未启用级别过滤 55.9 ns/op, 0 allocs 仅级别判断开销
吞吐量(examples/bench
场景 吞吐量
文件异步写入 4,952,640 条/s
文件同步写入 370,622 条/s
文件异步 + 3 字段 3,787,414 条/s
未启用级别过滤 20,118,049 条/s

设计原则

原则 说明
默认静默 所有通道和级别默认关闭,必须显式指定启用的日志级别
链式构建 通过 Builder 模式实现声明式、类型安全的配置
通道隔离 Console / File 通道级别独立控制
零依赖 纯标准库,零外部 import
绝不 panic Panic() 级别方法外,库内部绝不允许 panic
原子切割 单条日志绝不跨文件,切割前预判边界
并发安全 所有共享状态由 sync.Mutex 保护

日志格式

控制台(纯文本 + 色彩)
2026-06-06 15:04:05.000 INFO   服务启动成功  {port=8080}
2026-06-06 15:04:05.001 DEBUG  SQL 查询  {sql=SELECT ..., elapsed_ms=12}
2026-06-06 15:04:05.002 ERROR  连接失败  {error=connection refused}
控制台 + WithCaller
2026-06-06 15:04:05.000 INFO   main.go:15  服务启动成功  {port=8080}
2026-06-06 15:04:05.001 DEBUG  service/handler.go:42  SQL 查询  {sql=SELECT ...}
2026-06-06 15:04:05.002 ERROR  db/conn.go:108  连接失败  {error=connection refused}
文件(纯文本,无 ANSI)
2026-06-06 15:04:05.000 INFO   服务启动成功  {port=8080}
文件物理布局
/var/log/myapp/
├── app.log                           → app-2026-06-06T15-04-05.000.log  (Symlink)
├── app-2026-06-06T15-04-05.000.log   ← 当前写入文件
├── app-2026-06-05T00-00-00.000.log   ← 历史归档
├── app-2026-05-30T00-00-00.000.log.gz ← 已压缩归档
└── ...

项目结构

logx/
├── logger.go             # Logger 顶层接口
├── level.go              # 7 级日志级别
├── field.go              # 结构化字段 + Lazy 延迟求值
├── entry.go              # 日志条目
├── encoder.go            # Encoder 接口
├── appender.go           # Appender 接口
├── core.go               # 核心引擎(级别过滤 + 编码 + 写入)
├── builder.go            # Builder 链式构造器
├── text_encoder.go       # 零分配纯文本编码器
├── json_encoder.go       # 单行 JSON 编码器
├── console_appender.go   # 控制台输出器(stdout/stderr 分流)
├── file_appender.go      # 文件输出器(同步/异步 + 轮转)
├── writer_appender.go    # io.Writer 输出器
├── buffer.go             # 2MB sync.Pool 缓冲池
├── time_cache.go         # 100ms 时间缓存
├── color.go              # ANSI 色彩常量
├── stdlog.go             # 标准库 log 劫持
├── hook.go               # Hook 扩展接口
├── sampler.go            # 按秒限流采样器
├── metrics.go            # 运行指标
└── *_test.go             # 测试与 Benchmark(按组件拆分)

示例

完整可运行的示例位于 examples/ 目录:

示例 说明
basic 最简控制台输出
file_output 文件输出 + 轮转 + 压缩
advanced 完整功能:双通道 + 色彩 + Hook
stdlog 劫持标准库 log
bench 压力测试:吞吐量测量
bench_compare 与 Zap / Logrus 的微基准对比
graceful_shutdown 信号监听 + 优雅刷盘退出
竞品微基准

examples/bench_compare 中与 Zap / Logrus 对比(同环境、同消息、同 3 字段、纯文本输出到 io.Discard):

cd examples/bench_compare
go test -bench=. -benchmem ./...

基准结果与机器环境强相关,请以本机实测为准。

平台与精度说明

  • 时间缓存:格式化时间由后台协程每 100ms 更新一次,日志时间精度约 100ms,换取零分配输出;
  • Windows Symlink:Windows 创建软链接需要特殊权限,文件通道自动跳过 app.log 软链,物理文件命名不受影响;
  • 竞态检测:Windows 本地执行 go test -race 需要 gcc(如 mingw-w64);CI 已在 Linux 上覆盖竞态检测。

开发与发布

质量门禁命令:

go vet ./...                              # 静态检查,必须零告警
staticcheck ./...                         # 深度静态检查,必须零告警
go test -race -coverprofile=coverage.out ./...  # 测试 + 竞态 + 覆盖率
go tool cover -func coverage.out          # 覆盖率目标 100%
go test -bench=. -benchmem ./...          # 微基准
  • API 兼容性:家族约定破坏性变更统一走 minor 版本(不强制主版本升级), 直至另行调整版本规范;
  • 发布流程:推送形如 v1.5.2 的 tag(使用 PowerShell 执行 git push origin v1.5.2), GitHub Actions 自动测试并生成 Release;
  • 本地开发:仓库提供 go.work,可在根目录直接联调所有 examples。

License

MIT © lcylpzls

Documentation

Overview

Package logx 提供高性能结构化日志基座: 构建器、字段、编码器、文件/控制台输出、指标与 stdlog 桥接。 实现主体位于 internal/core,本包仅暴露稳定公开 API。

Index

Constants

View Source
const (
	AsyncWriteMode = core.AsyncWriteMode
	SyncWriteMode  = core.SyncWriteMode
)
View Source
const (
	OffLevel   = core.OffLevel
	DebugLevel = core.DebugLevel
	InfoLevel  = core.InfoLevel
	WarnLevel  = core.WarnLevel
	ErrorLevel = core.ErrorLevel
	PanicLevel = core.PanicLevel
	FatalLevel = core.FatalLevel
)
View Source
const (
	CodeInvalidConfig = core.CodeInvalidConfig
	CodeIOFailed      = core.CodeIOFailed
	CodeClosed        = core.CodeClosed
)

Variables

This section is empty.

Functions

func ReplaceStdLogger

func ReplaceStdLogger(l Logger)

func RestoreStdLogger

func RestoreStdLogger()

Types

type Appender

type Appender = core.Appender

类型别名(实现见 internal/core)。

type Buffer

type Buffer = core.Buffer

类型别名(实现见 internal/core)。

type Builder

type Builder = core.Builder

类型别名(实现见 internal/core)。

func NewBuilder

func NewBuilder() *Builder

type ConsoleOption

type ConsoleOption = core.ConsoleOption

类型别名(实现见 internal/core)。

func WithColor

func WithColor() ConsoleOption

type CounterSink added in v1.1.0

type CounterSink = core.CounterSink

类型别名(实现见 internal/core)。

type Encoder

type Encoder = core.Encoder

类型别名(实现见 internal/core)。

func NewJSONEncoder

func NewJSONEncoder() Encoder

type Entry

type Entry = core.Entry

类型别名(实现见 internal/core)。

type Field

type Field = core.Field

类型别名(实现见 internal/core)。

func Any

func Any(key string, val any) Field

func Bool

func Bool(key string, val bool) Field

func Err

func Err(err error) Field

func Int

func Int(key string, val int) Field

func Int64

func Int64(key string, val int64) Field

func Lazy

func Lazy(key string, fn func() any) Field

func String

func String(key string, val string) Field

type FieldGroup

type FieldGroup = core.FieldGroup

类型别名(实现见 internal/core)。

func Fields

func Fields(fs ...Field) FieldGroup

func FieldsFromError added in v1.4.0

func FieldsFromError(err error) FieldGroup

type FileConfig

type FileConfig = core.FileConfig

类型别名(实现见 internal/core)。

type FileOption

type FileOption = core.FileOption

类型别名(实现见 internal/core)。

func WithBufferSize

func WithBufferSize(size int) FileOption

func WithCompressAfter

func WithCompressAfter(days int) FileOption

func WithErrorHandler

func WithErrorHandler(fn func(error)) FileOption

func WithFilename

func WithFilename(name string) FileOption

func WithFlushInterval

func WithFlushInterval(d time.Duration) FileOption

func WithLevels

func WithLevels(levels ...Level) FileOption

func WithLogDir

func WithLogDir(dir string) FileOption

func WithMaxAge

func WithMaxAge(days int) FileOption

func WithMaxBackups

func WithMaxBackups(n int) FileOption

func WithMaxSize

func WithMaxSize(mb int) FileOption

func WithWriteMode

func WithWriteMode(mode WriteMode) FileOption

type Hook

type Hook = core.Hook

类型别名(实现见 internal/core)。

type HookedLogger

type HookedLogger = core.HookedLogger

类型别名(实现见 internal/core)。

type Level

type Level = core.Level

类型别名(实现见 internal/core)。

type LevelUpdater

type LevelUpdater = core.LevelUpdater

类型别名(实现见 internal/core)。

type Logger

type Logger = core.Logger

类型别名(实现见 internal/core)。

func NewNopLogger added in v1.5.2

func NewNopLogger() Logger

NewNopLogger 返回一个不产生任何输出与副作用的 Logger。 Panic/Fatal 静默;SafeExit 保留退出回调语义。

type MetricProvider

type MetricProvider = core.MetricProvider

类型别名(实现见 internal/core)。

type MetricSink added in v1.1.0

type MetricSink = core.MetricSink

类型别名(实现见 internal/core)。

type Metrics

type Metrics = core.Metrics

类型别名(实现见 internal/core)。

type WriteMode

type WriteMode = core.WriteMode

类型别名(实现见 internal/core)。

Directories

Path Synopsis
internal
core
Package logx 是工业级零依赖高性能 Go 结构化日志库。
Package logx 是工业级零依赖高性能 Go 结构化日志库。

Jump to

Keyboard shortcuts

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