156 lines
3.5 KiB
Go
156 lines
3.5 KiB
Go
|
package oceanlogger
|
||
|
|
||
|
import (
|
||
|
"fmt"
|
||
|
"os"
|
||
|
"path"
|
||
|
"time"
|
||
|
)
|
||
|
|
||
|
//定义文件日志对象
|
||
|
|
||
|
type FileLogger struct {
|
||
|
lvl LogLevel
|
||
|
fileObj *os.File
|
||
|
fileName string
|
||
|
filepath string
|
||
|
fileMaxSize int64
|
||
|
creatTime time.Time
|
||
|
}
|
||
|
|
||
|
//new文件日志对象
|
||
|
|
||
|
func NewFileLogger(lvLel string, filename, filepath string, filemaxsize int64) *FileLogger {
|
||
|
lvl := getLogStruct(lvLel)
|
||
|
fl := &FileLogger{
|
||
|
lvl: lvl,
|
||
|
filepath: filepath,
|
||
|
fileMaxSize: filemaxsize,
|
||
|
fileName: filename,
|
||
|
creatTime: time.Now(),
|
||
|
}
|
||
|
|
||
|
fileObj, err := fl.conStructFd()
|
||
|
if err != nil {
|
||
|
fmt.Printf("new filelogger failed,error:%v", err)
|
||
|
}
|
||
|
fl.fileObj = fileObj //组装完整结构体对象
|
||
|
return fl
|
||
|
}
|
||
|
|
||
|
//打开一个文件句柄,用于组成结构体
|
||
|
|
||
|
func (f *FileLogger) conStructFd() (*os.File, error) {
|
||
|
fullFilePath := path.Join(f.filepath, f.fileName)
|
||
|
fileObj, err := os.OpenFile(fullFilePath, os.O_APPEND|os.O_CREATE|os.O_WRONLY, 0644)
|
||
|
if err != nil {
|
||
|
fmt.Printf("construct newfilelogger failed,error:%v", err)
|
||
|
return nil, err
|
||
|
}
|
||
|
return fileObj, nil
|
||
|
}
|
||
|
|
||
|
// 校验文件大小
|
||
|
func (f *FileLogger) checkFileSize(file *os.File) bool {
|
||
|
fileInfo, err := file.Stat()
|
||
|
if err != nil {
|
||
|
fmt.Printf("check filesize func failed,err:%v", err)
|
||
|
}
|
||
|
if f.fileMaxSize <= fileInfo.Size() {
|
||
|
return true
|
||
|
} else {
|
||
|
return false
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// 校验创建时间
|
||
|
func (f *FileLogger) checkCreateTime(duration time.Duration) bool {
|
||
|
now := time.Now() //现在的东八区时间
|
||
|
if now.Sub(f.creatTime) >= duration {
|
||
|
return true
|
||
|
} else {
|
||
|
return false
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// 分割日志文件
|
||
|
func (f *FileLogger) splitFile() error {
|
||
|
//根据老日志对象获取信息
|
||
|
fullLogPath := path.Join(f.filepath, f.fileName)
|
||
|
timeStr := time.Now().Format("2006150405000")
|
||
|
newLogFileName := fmt.Sprintf("%s.bak_%s", fullLogPath, timeStr)
|
||
|
//关闭原有的文件句柄
|
||
|
f.close()
|
||
|
//重命名原来的文件
|
||
|
err := os.Rename(fullLogPath, newLogFileName)
|
||
|
if err != nil {
|
||
|
return err
|
||
|
}
|
||
|
//创建一个新的文件
|
||
|
fileObj, err := os.OpenFile(fullLogPath, os.O_APPEND|os.O_CREATE|os.O_WRONLY, 0644)
|
||
|
if err != nil {
|
||
|
fmt.Printf("create newfile failed,error:%v", err)
|
||
|
return err
|
||
|
}
|
||
|
//把新文件的句柄赋值给结构体对象
|
||
|
f.fileObj = fileObj
|
||
|
f.creatTime = time.Now() //创建时间
|
||
|
return nil
|
||
|
|
||
|
}
|
||
|
|
||
|
// 文件日志对象的级别校验
|
||
|
func (f *FileLogger) checkLevel(l LogLevel) bool {
|
||
|
if f.lvl <= l {
|
||
|
return true
|
||
|
} else {
|
||
|
return false
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// 总体实现,下面分别调用
|
||
|
func (f *FileLogger) logPrintOverAll(lvl LogLevel, format string, i ...interface{}) {
|
||
|
if f.checkLevel(lvl) {
|
||
|
msg := fmt.Sprintf(format, i...)
|
||
|
funcName, fileName, line, _ := getInfo(3)
|
||
|
if f.checkFileSize(f.fileObj) {
|
||
|
err := f.splitFile()
|
||
|
if err != nil {
|
||
|
return
|
||
|
}
|
||
|
}
|
||
|
if f.checkCreateTime(time.Second * 10) {
|
||
|
err := f.splitFile()
|
||
|
if err != nil {
|
||
|
return
|
||
|
}
|
||
|
}
|
||
|
|
||
|
fmt.Fprintf(f.fileObj, "[%s][%s][line:%d,funcname:%s filename:%s] %s\n", getNowTimeStr(), getLogStr(f.lvl), line, funcName, fileName, msg)
|
||
|
}
|
||
|
}
|
||
|
|
||
|
//日志输出实现
|
||
|
|
||
|
func (f *FileLogger) Debug(format string, i ...interface{}) {
|
||
|
f.logPrintOverAll(DEBUG, format, i...)
|
||
|
}
|
||
|
|
||
|
func (f *FileLogger) Info(format string, i ...interface{}) {
|
||
|
f.logPrintOverAll(INFO, format, i...)
|
||
|
}
|
||
|
func (f *FileLogger) Error(format string, i ...interface{}) {
|
||
|
f.logPrintOverAll(ERROR, format, i...)
|
||
|
}
|
||
|
func (f *FileLogger) Fatal(format string, i ...interface{}) {
|
||
|
f.logPrintOverAll(FATAL, format, i...)
|
||
|
}
|
||
|
|
||
|
func (f *FileLogger) close() {
|
||
|
err := f.fileObj.Close()
|
||
|
if err != nil {
|
||
|
fmt.Printf("failed close file!,error:%v", err)
|
||
|
}
|
||
|
return
|
||
|
}
|