GoLang 异步日志库实现

编程入门 行业动态 更新时间:2024-10-08 06:18:34

GoLang 异步<a href=https://www.elefans.com/category/jswz/34/1770796.html style=日志库实现"/>

GoLang 异步日志库实现

GoLang 异步日志库实现

  • 公共的方法
type LogLevel uint8const (L_DEBUG LogLevel = iotaL_WARNINGL_ERROR
)func getLogLevel(level LogLevel) string {switch level {case L_DEBUG:return "DEBUG"case L_WARNING:return "WARNING"case L_ERROR:return "ERROR"default:return "nil"}
}func getLogInfo(skip int) (fileName, funcName string, l int) {pc, file, line, ok := runtime.Caller(skip)if !ok {fmt.Println("runtime.Caller Error")return}fileName = path.Base(file)funcName = runtime.FuncForPC(pc).Name()l = linereturn
}
  • 结构体方法
    使用结构体指针作为通道传输信息,而不使用string字符串传递可以节省性能开销
    在该程序中使用select语句中的defult可以避免因接收不了通道的信息而阻塞正常程序的运行
type FileLogger struct {level         LogLevellogFilePath   stringlogFileName   stringmaxFileSize   int64fileWriter    *os.FileerrFileWriter *os.FilelogChan       chan *logPack
}
type logPack struct {level    LogLeveltime     stringfileName stringfuncName stringline     intmsg      stringfile     *os.File
}func NewFileLogger(level LogLevel, path, name string, maxSize int64) *FileLogger {logger := &FileLogger{level:       level,logFilePath: path,logFileName: name,maxFileSize: maxSize,logChan:     make(chan *logPack, 50000),}logger.initWriter()go logger.writeLog()return logger
}func (f *FileLogger) Debug(format string, a ...any) {f.createInfo(L_DEBUG, format, a...)
}
func (f *FileLogger) Warning(format string, a ...any) {f.createInfo(L_WARNING, format, a...)
}
func (f *FileLogger) Error(format string, a ...any) {f.createInfo(L_ERROR, format, a...)
}
func (f *FileLogger) createInfo(targetLogLevel LogLevel, format string, a ...any) {if f.level <= targetLogLevel {f.makeAndWriteInfo(f.fileWriter, targetLogLevel, format, a...)}//当错误等级大于等于ERROR时,需要将错误单独写到一个文件中去if targetLogLevel >= L_ERROR {f.makeAndWriteInfo(f.errFileWriter, targetLogLevel, format, a...)}
}
func (f *FileLogger) makeAndWriteInfo(file *os.File, targetLogLevel LogLevel, format string, a ...any) {msg := fmt.Sprintf(format, a...)fileName, funcName, line := getLogInfo(4)pack := &logPack{level:    targetLogLevel,time:     time.Now().Format("2006-01-02 15:04:05"),fileName: fileName,funcName: funcName,line:     line,msg:      msg,file:     file,}select {case f.logChan <- pack:default:}
}
func (f *FileLogger) checkSize(file *os.File) bool {fileInfo, err := file.Stat()if err != nil {fmt.Println(err)panic("checkSize Error:")}size := fileInfo.Size()return size >= f.maxFileSize
}
func (f *FileLogger) writeLog() {for true {select {case pack := <-f.logChan:file := pack.fileif f.checkSize(file) {//需要切割//1.关闭旧的文件写入oldPath := path.Join(f.logFilePath, file.Name())newPath := oldPath + ".ok" + strconv.FormatInt(time.Now().UnixNano(), 10)err := file.Close()if err != nil {fmt.Println(err)return}//2.重命名旧的文件err = os.Rename(oldPath, newPath)if err != nil {fmt.Println(err)return}//3.创建新的文件写入newFile, err := os.OpenFile(oldPath, os.O_WRONLY|os.O_CREATE|os.O_APPEND, os.ModePerm)if err != nil {fmt.Println(err)return}//4.设置新的fileif *file == *f.fileWriter {f.fileWriter = newFile} else {f.errFileWriter = newFile}}_, err := fmt.Fprintf(file, "[%s][%s][%s:%s:%d]:%s\n",getLogLevel(pack.level),pack.time,pack.fileName,pack.funcName,pack.line,pack.msg)if err != nil {fmt.Println(err)return}default:time.Sleep(time.Millisecond * 500)}}
}
func (f *FileLogger) initWriter() {p := path.Join(f.logFilePath, f.logFileName)file, err := os.OpenFile(p, os.O_WRONLY|os.O_CREATE|os.O_APPEND, os.ModePerm)if err != nil {fmt.Println(err)return}errFile, err := os.OpenFile(p+".err", os.O_WRONLY|os.O_CREATE|os.O_APPEND, os.ModePerm)if err != nil {fmt.Println(err)return}f.fileWriter = filef.errFileWriter = errFile
}
func (f *FileLogger) Close() {err := f.fileWriter.Close()if err != nil {fmt.Println(err)}err = f.errFileWriter.Close()if err != nil {fmt.Println(err)}f.fileWriter = nilf.errFileWriter = nil
}

更多推荐

GoLang 异步日志库实现

本文发布于:2024-02-25 06:17:16,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1698073.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:日志   GoLang

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!