226 lines
4.6 KiB
Go
226 lines
4.6 KiB
Go
package loghandler
|
|
|
|
import (
|
|
"bufio"
|
|
"encoding/json"
|
|
"fmt"
|
|
"jannex/log-manager/modules/cache"
|
|
"jannex/log-manager/modules/config"
|
|
"jannex/log-manager/modules/structs"
|
|
"jannex/log-manager/modules/utils"
|
|
"os"
|
|
"path/filepath"
|
|
"sort"
|
|
"strconv"
|
|
"strings"
|
|
"sync"
|
|
"time"
|
|
)
|
|
|
|
var FileMutexMap = make(map[string]*sync.Mutex)
|
|
var FileMutexMapLock sync.Mutex
|
|
|
|
func getFileMutex(filePath string) *sync.Mutex {
|
|
FileMutexMapLock.Lock()
|
|
defer FileMutexMapLock.Unlock()
|
|
|
|
mutex, ok := FileMutexMap[filePath]
|
|
|
|
if !ok {
|
|
mutex = &sync.Mutex{}
|
|
FileMutexMap[filePath] = mutex
|
|
}
|
|
|
|
return mutex
|
|
}
|
|
|
|
func AddLog(body structs.LogBody) {
|
|
year, month, day := time.Now().Date()
|
|
date := strconv.Itoa(day) + "-" + strconv.Itoa(int(month)) + "-" + strconv.Itoa(year)
|
|
logFolder := config.Cfg.LogFolder
|
|
|
|
utils.CreateDirectoryIfNotExists(logFolder + body.Type)
|
|
|
|
path := logFolder + body.Type + "/" + date + ".log"
|
|
|
|
// get the mutex for this file
|
|
mutex := getFileMutex(path)
|
|
|
|
// lock the mutex to ensure the file is only opened once at a time
|
|
mutex.Lock()
|
|
defer mutex.Unlock()
|
|
|
|
file, err := os.OpenFile(path, os.O_APPEND|os.O_CREATE|os.O_WRONLY, 0644)
|
|
|
|
if err != nil {
|
|
fmt.Println(err)
|
|
return
|
|
}
|
|
|
|
defer file.Close()
|
|
|
|
for _, log := range body.Logs {
|
|
if _, err := fmt.Fprintln(file, log); err != nil {
|
|
fmt.Println(err)
|
|
}
|
|
}
|
|
|
|
for clientId, sseClient := range cache.SSEClients {
|
|
if sseClient.LogType == body.Type && sseClient.Date == date {
|
|
fmt.Println("Sending message to client", clientId)
|
|
|
|
marshaledLogs, err := json.Marshal(body.Logs)
|
|
|
|
if err != nil {
|
|
fmt.Println(err)
|
|
return
|
|
}
|
|
|
|
sseClient.MessageChannel <- structs.SSEClientChannelMessage{
|
|
ClientId: clientId,
|
|
Message: marshaledLogs,
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
func GetAvailableLogFiles(logType string) ([]string, error) {
|
|
var availableLogs []string
|
|
|
|
path := config.Cfg.LogFolder + logType
|
|
|
|
files, err := os.ReadDir(path)
|
|
|
|
if err != nil {
|
|
fmt.Println(err)
|
|
return []string{}, err
|
|
}
|
|
|
|
// sort the files by date
|
|
sort.Slice(files, func(i, j int) bool {
|
|
dateFormat := "2-1-2006"
|
|
dateA, _ := time.Parse(dateFormat, strings.Split(files[i].Name(), ".")[0])
|
|
dateB, _ := time.Parse(dateFormat, strings.Split(files[j].Name(), ".")[0])
|
|
return dateA.After(dateB)
|
|
})
|
|
|
|
for _, file := range files {
|
|
availableLogs = append(availableLogs, strings.Split(file.Name(), ".")[0])
|
|
}
|
|
|
|
return availableLogs, nil
|
|
}
|
|
|
|
func GetLogByDate(logType string, date string) ([]string, error) {
|
|
var logs []string
|
|
|
|
path := config.Cfg.LogFolder + logType + "/" + date + ".log"
|
|
|
|
// get the mutex for this file
|
|
mutex := getFileMutex(path)
|
|
|
|
// lock the mutex to ensure the file is only opened once at a time
|
|
mutex.Lock()
|
|
defer mutex.Unlock()
|
|
|
|
file, err := os.Open(path)
|
|
if err != nil {
|
|
fmt.Println(err)
|
|
return []string{}, err
|
|
}
|
|
defer file.Close()
|
|
|
|
scanner := bufio.NewScanner(file)
|
|
|
|
for scanner.Scan() {
|
|
logs = append(logs, scanner.Text())
|
|
}
|
|
|
|
if len(logs) == 0 {
|
|
return []string{}, nil
|
|
}
|
|
|
|
return logs, nil
|
|
}
|
|
|
|
func GetAvailableLogTypes() []string {
|
|
var availableLogTypes []string
|
|
|
|
files, err := os.ReadDir(config.Cfg.LogFolder)
|
|
|
|
if err != nil {
|
|
fmt.Println(err)
|
|
return []string{}
|
|
}
|
|
|
|
for _, file := range files {
|
|
availableLogTypes = append(availableLogTypes, file.Name())
|
|
}
|
|
|
|
if len(availableLogTypes) == 0 {
|
|
return []string{}
|
|
}
|
|
|
|
return availableLogTypes
|
|
}
|
|
|
|
func StartBackgroundLogDeleter() {
|
|
ticker := time.NewTicker(24 * time.Hour)
|
|
|
|
for range ticker.C {
|
|
CheckForDeletableLogs()
|
|
}
|
|
}
|
|
|
|
func CheckForDeletableLogs() {
|
|
daysToKeepLogs := config.Cfg.DaysToKeepLogs
|
|
|
|
logFolder := config.Cfg.LogFolder
|
|
|
|
err := filepath.Walk(logFolder, func(path string, info os.FileInfo, err error) error {
|
|
if err != nil {
|
|
fmt.Println(err)
|
|
return err
|
|
}
|
|
|
|
if !info.IsDir() {
|
|
// check if the file is older than the daysToKeepLogs
|
|
// get the date from the file name
|
|
date := strings.Split(info.Name(), ".")[0]
|
|
|
|
dateFormat := "2-1-2006"
|
|
|
|
fileDate, err := time.Parse(dateFormat, date)
|
|
|
|
if err != nil {
|
|
fmt.Println(err)
|
|
return err
|
|
}
|
|
|
|
// get the date from the daysToKeepLogs
|
|
daysToKeepLogsDate := time.Now().AddDate(0, 0, -daysToKeepLogs)
|
|
|
|
// compare the dates
|
|
if fileDate.Before(daysToKeepLogsDate) {
|
|
// delete the file
|
|
err := os.Remove(path)
|
|
|
|
if err != nil {
|
|
fmt.Println(err)
|
|
return err
|
|
}
|
|
|
|
AddLog(structs.LogBody{
|
|
Type: "system",
|
|
Logs: []string{"I "+ utils.GetTime() + "LogManager: Deleted log file " + path + " because it was older than " + strconv.Itoa(daysToKeepLogs) + " days."},
|
|
})
|
|
}
|
|
}
|
|
|
|
return nil
|
|
})
|
|
|
|
if err != nil {
|
|
fmt.Println(err)
|
|
}
|
|
} |