温馨提示×

CentOS系统中Golang日志轮转方法

小樊
45
2025-09-05 21:58:58
栏目: 编程语言

在CentOS系统中,Golang日志轮转可以通过使用第三方库或者自定义日志处理程序来实现。这里我们将介绍两种方法:使用第三方库lumberjack和使用Golang内置的log包。

方法一:使用第三方库lumberjack

  1. 首先,需要安装lumberjack库。在终端中运行以下命令:
go get github.com/natefinch/lumberjack
  1. 在你的Golang项目中,引入lumberjack库,并创建一个lumberjack.Logger实例:
package main

import (
	"github.com/natefinch/lumberjack"
	"log"
)

func main() {
	logger := &lumberjack.Logger{
		Filename:   "/var/log/myapp.log", // 日志文件路径
		MaxSize:    10,                 // 每个日志文件的最大尺寸(单位:MB)
		MaxBackups: 3,                  // 保留的最大日志文件数量
		MaxAge:     28,                 // 保留的最大日志文件天数
		Compress:   true,               // 是否压缩旧的日志文件
	}
	defer logger.Close()

	log.SetOutput(logger)

	// 使用log输出日志
	log.Println("This is a log message.")
}

方法二:使用Golang内置的log

  1. 在你的Golang项目中,创建一个自定义的日志处理程序,实现io.Writer接口:
package main

import (
	"io"
	"log"
	"os"
	"time"
)

type RotatingFile struct {
	filename    string
	maxSize     int64
	maxBackups  int
	maxAge      int
	compress    bool
	currentSize int64
}

func NewRotatingFile(filename string, maxSize int64, maxBackups int, maxAge int, compress bool) *RotatingFile {
	return &RotatingFile{
		filename:    filename,
		maxSize:     maxSize,
		maxBackups:  maxBackups,
		maxAge:      maxAge,
		compress:    compress,
		currentSize: 0,
	}
}

func (rf *RotatingFile) Write(p []byte) (n int, err error) {
	n, err = rf.file.Write(p)
	rf.currentSize += int64(n)

	if rf.currentSize >= rf.maxSize {
		rf.rotate()
	}

	return n, err
}

func (rf *RotatingFile) rotate() {
	rf.file.Close()

	for i := rf.maxBackups - 1; i > 0; i-- {
		src := rf.filename + "." + strconv.Itoa(i)
		dst := rf.filename + "." + strconv.Itoa(i+1)

		os.Rename(src, dst)
	}

	if rf.compress {
		src := rf.filename + ".1"
		dst := rf.filename + ".1.gz"

		gzipFile, err := os.Open(src)
		if err != nil {
			log.Println("Error opening gzip file:", err)
			return
		}
		defer gzipFile.Close()

		gzipWriter := gzip.NewWriter(os.Stdout)
		defer gzipWriter.Close()

		io.Copy(gzipWriter, gzipFile)
	}

	os.Rename(rf.filename, rf.filename+".1")

	if _, err := os.Stat(rf.filename); os.IsNotExist(err) {
		os.OpenFile(rf.filename, os.O_CREATE|os.O_WRONLY, 0644)
	}
}

func (rf *RotatingFile) Close() error {
	return rf.file.Close()
}
  1. 在你的Golang项目中,使用自定义的日志处理程序:
package main

import (
	"log"
	"os"
	"time"
)

func main() {
	logFile := NewRotatingFile("/var/log/myapp.log", 10, 3, 28, true)
	defer logFile.Close()

	log.SetOutput(logFile)

	// 使用log输出日志
	log.Println("This is a log message.")
}

这两种方法都可以实现Golang日志轮转。你可以根据自己的需求选择合适的方法。

0