1
0

logger.go 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139
  1. package logger
  2. import (
  3. "fmt"
  4. "log"
  5. "os"
  6. "path/filepath"
  7. "strconv"
  8. "time"
  9. )
  10. /*
  11. Zoraxy Logger
  12. This script is designed to make a managed log for the Zoraxy
  13. and replace the ton of log.Println in the system core.
  14. The core logger is based in golang's build-in log package
  15. */
  16. type Logger struct {
  17. Prefix string //Prefix for log files
  18. LogFolder string //Folder to store the log file
  19. CurrentLogFile string //Current writing filename
  20. logger *log.Logger
  21. file *os.File
  22. }
  23. // Create a new logger that log to files
  24. func NewLogger(logFilePrefix string, logFolder string) (*Logger, error) {
  25. err := os.MkdirAll(logFolder, 0775)
  26. if err != nil {
  27. return nil, err
  28. }
  29. thisLogger := Logger{
  30. Prefix: logFilePrefix,
  31. LogFolder: logFolder,
  32. }
  33. //Create the log file if not exists
  34. logFilePath := thisLogger.getLogFilepath()
  35. f, err := os.OpenFile(logFilePath, os.O_CREATE|os.O_APPEND|os.O_WRONLY, 0755)
  36. if err != nil {
  37. return nil, err
  38. }
  39. thisLogger.CurrentLogFile = logFilePath
  40. thisLogger.file = f
  41. //Start the logger
  42. logger := log.New(f, "", log.Flags()&^(log.Ldate|log.Ltime))
  43. logger.SetFlags(0)
  44. logger.SetOutput(f)
  45. thisLogger.logger = logger
  46. return &thisLogger, nil
  47. }
  48. // Create a fmt logger that only log to STDOUT
  49. func NewFmtLogger() (*Logger, error) {
  50. return &Logger{
  51. Prefix: "",
  52. LogFolder: "",
  53. CurrentLogFile: "",
  54. logger: nil,
  55. file: nil,
  56. }, nil
  57. }
  58. func (l *Logger) getLogFilepath() string {
  59. year, month, _ := time.Now().Date()
  60. return filepath.Join(l.LogFolder, l.Prefix+"_"+strconv.Itoa(year)+"-"+strconv.Itoa(int(month))+".log")
  61. }
  62. // PrintAndLog will log the message to file and print the log to STDOUT
  63. func (l *Logger) PrintAndLog(title string, message string, originalError error) {
  64. go func() {
  65. l.Log(title, message, originalError, true)
  66. }()
  67. }
  68. // Println is a fast snap-in replacement for log.Println
  69. func (l *Logger) Println(v ...interface{}) {
  70. //Convert the array of interfaces into string
  71. message := fmt.Sprint(v...)
  72. go func() {
  73. l.Log("internal", string(message), nil, true)
  74. }()
  75. }
  76. func (l *Logger) Log(title string, errorMessage string, originalError error, copyToSTDOUT bool) {
  77. l.ValidateAndUpdateLogFilepath()
  78. if l.logger == nil || copyToSTDOUT {
  79. //Use STDOUT instead of logger
  80. if originalError == nil {
  81. fmt.Println("[" + time.Now().Format("2006-01-02 15:04:05.000000") + "] [" + title + "] [system:info] " + errorMessage)
  82. } else {
  83. fmt.Println("[" + time.Now().Format("2006-01-02 15:04:05.000000") + "] [" + title + "] [system:error] " + errorMessage + ": " + originalError.Error())
  84. }
  85. }
  86. if l.logger != nil {
  87. if originalError == nil {
  88. l.logger.Println("[" + time.Now().Format("2006-01-02 15:04:05.000000") + "] [" + title + "] [system:info] " + errorMessage)
  89. } else {
  90. l.logger.Println("[" + time.Now().Format("2006-01-02 15:04:05.000000") + "] [" + title + "] [system:error] " + errorMessage + ": " + originalError.Error())
  91. }
  92. }
  93. }
  94. // Validate if the logging target is still valid (detect any months change)
  95. func (l *Logger) ValidateAndUpdateLogFilepath() {
  96. if l.file == nil {
  97. return
  98. }
  99. expectedCurrentLogFilepath := l.getLogFilepath()
  100. if l.CurrentLogFile != expectedCurrentLogFilepath {
  101. //Change of month. Update to a new log file
  102. l.file.Close()
  103. l.file = nil
  104. //Create a new log file
  105. f, err := os.OpenFile(expectedCurrentLogFilepath, os.O_CREATE|os.O_APPEND|os.O_WRONLY, 0755)
  106. if err != nil {
  107. log.Println("Unable to create new log. Logging is disabled: ", err.Error())
  108. l.logger = nil
  109. return
  110. }
  111. l.CurrentLogFile = expectedCurrentLogFilepath
  112. l.file = f
  113. //Start a new logger
  114. logger := log.New(f, "", log.Default().Flags())
  115. l.logger = logger
  116. }
  117. }
  118. func (l *Logger) Close() {
  119. l.file.Close()
  120. }