You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

log.go 5.9KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254
  1. // Copyright 2014 The Gogs Authors. All rights reserved.
  2. // Use of this source code is governed by a MIT-style
  3. // license that can be found in the LICENSE file.
  4. package log
  5. import (
  6. "os"
  7. "runtime"
  8. "strings"
  9. "sync"
  10. )
  11. type loggerMap struct {
  12. sync.Map
  13. }
  14. func (m *loggerMap) Load(k string) (*Logger, bool) {
  15. v, ok := m.Map.Load(k)
  16. if !ok {
  17. return nil, false
  18. }
  19. l, ok := v.(*Logger)
  20. return l, ok
  21. }
  22. func (m *loggerMap) Store(k string, v *Logger) {
  23. m.Map.Store(k, v)
  24. }
  25. func (m *loggerMap) Delete(k string) {
  26. m.Map.Delete(k)
  27. }
  28. var (
  29. // DEFAULT is the name of the default logger
  30. DEFAULT = "default"
  31. // NamedLoggers map of named loggers
  32. NamedLoggers loggerMap
  33. prefix string
  34. )
  35. // NewLogger create a logger for the default logger
  36. func NewLogger(bufLen int64, name, provider, config string) *Logger {
  37. err := NewNamedLogger(DEFAULT, bufLen, name, provider, config)
  38. if err != nil {
  39. CriticalWithSkip(1, "Unable to create default logger: %v", err)
  40. panic(err)
  41. }
  42. l, _ := NamedLoggers.Load(DEFAULT)
  43. return l
  44. }
  45. // NewNamedLogger creates a new named logger for a given configuration
  46. func NewNamedLogger(name string, bufLen int64, subname, provider, config string) error {
  47. logger, ok := NamedLoggers.Load(name)
  48. if !ok {
  49. logger = newLogger(name, bufLen)
  50. NamedLoggers.Store(name, logger)
  51. }
  52. return logger.SetLogger(subname, provider, config)
  53. }
  54. // DelNamedLogger closes and deletes the named logger
  55. func DelNamedLogger(name string) {
  56. l, ok := NamedLoggers.Load(name)
  57. if ok {
  58. NamedLoggers.Delete(name)
  59. l.Close()
  60. }
  61. }
  62. // DelLogger removes the named sublogger from the default logger
  63. func DelLogger(name string) error {
  64. logger, _ := NamedLoggers.Load(DEFAULT)
  65. found, err := logger.DelLogger(name)
  66. if !found {
  67. Trace("Log %s not found, no need to delete", name)
  68. }
  69. return err
  70. }
  71. // GetLogger returns either a named logger or the default logger
  72. func GetLogger(name string) *Logger {
  73. logger, ok := NamedLoggers.Load(name)
  74. if ok {
  75. return logger
  76. }
  77. logger, _ = NamedLoggers.Load(DEFAULT)
  78. return logger
  79. }
  80. // GetLevel returns the minimum logger level
  81. func GetLevel() Level {
  82. l, _ := NamedLoggers.Load(DEFAULT)
  83. return l.GetLevel()
  84. }
  85. // GetStacktraceLevel returns the minimum logger level
  86. func GetStacktraceLevel() Level {
  87. l, _ := NamedLoggers.Load(DEFAULT)
  88. return l.GetStacktraceLevel()
  89. }
  90. // Trace records trace log
  91. func Trace(format string, v ...interface{}) {
  92. Log(1, TRACE, format, v...)
  93. }
  94. // IsTrace returns true if at least one logger is TRACE
  95. func IsTrace() bool {
  96. return GetLevel() <= TRACE
  97. }
  98. // Debug records debug log
  99. func Debug(format string, v ...interface{}) {
  100. Log(1, DEBUG, format, v...)
  101. }
  102. // IsDebug returns true if at least one logger is DEBUG
  103. func IsDebug() bool {
  104. return GetLevel() <= DEBUG
  105. }
  106. // Info records info log
  107. func Info(format string, v ...interface{}) {
  108. Log(1, INFO, format, v...)
  109. }
  110. // IsInfo returns true if at least one logger is INFO
  111. func IsInfo() bool {
  112. return GetLevel() <= INFO
  113. }
  114. // Warn records warning log
  115. func Warn(format string, v ...interface{}) {
  116. Log(1, WARN, format, v...)
  117. }
  118. // IsWarn returns true if at least one logger is WARN
  119. func IsWarn() bool {
  120. return GetLevel() <= WARN
  121. }
  122. // Error records error log
  123. func Error(format string, v ...interface{}) {
  124. Log(1, ERROR, format, v...)
  125. }
  126. // ErrorWithSkip records error log from "skip" calls back from this function
  127. func ErrorWithSkip(skip int, format string, v ...interface{}) {
  128. Log(skip+1, ERROR, format, v...)
  129. }
  130. // IsError returns true if at least one logger is ERROR
  131. func IsError() bool {
  132. return GetLevel() <= ERROR
  133. }
  134. // Critical records critical log
  135. func Critical(format string, v ...interface{}) {
  136. Log(1, CRITICAL, format, v...)
  137. }
  138. // CriticalWithSkip records critical log from "skip" calls back from this function
  139. func CriticalWithSkip(skip int, format string, v ...interface{}) {
  140. Log(skip+1, CRITICAL, format, v...)
  141. }
  142. // IsCritical returns true if at least one logger is CRITICAL
  143. func IsCritical() bool {
  144. return GetLevel() <= CRITICAL
  145. }
  146. // Fatal records fatal log and exit process
  147. func Fatal(format string, v ...interface{}) {
  148. Log(1, FATAL, format, v...)
  149. Close()
  150. os.Exit(1)
  151. }
  152. // FatalWithSkip records fatal log from "skip" calls back from this function
  153. func FatalWithSkip(skip int, format string, v ...interface{}) {
  154. Log(skip+1, FATAL, format, v...)
  155. Close()
  156. os.Exit(1)
  157. }
  158. // IsFatal returns true if at least one logger is FATAL
  159. func IsFatal() bool {
  160. return GetLevel() <= FATAL
  161. }
  162. // Close closes all the loggers
  163. func Close() {
  164. l, ok := NamedLoggers.Load(DEFAULT)
  165. if !ok {
  166. return
  167. }
  168. NamedLoggers.Delete(DEFAULT)
  169. l.Close()
  170. }
  171. // Log a message with defined skip and at logging level
  172. // A skip of 0 refers to the caller of this command
  173. func Log(skip int, level Level, format string, v ...interface{}) {
  174. l, ok := NamedLoggers.Load(DEFAULT)
  175. if ok {
  176. l.Log(skip+1, level, format, v...)
  177. }
  178. }
  179. // LoggerAsWriter is a io.Writer shim around the gitea log
  180. type LoggerAsWriter struct {
  181. ourLoggers []*Logger
  182. level Level
  183. }
  184. // NewLoggerAsWriter creates a Writer representation of the logger with setable log level
  185. func NewLoggerAsWriter(level string, ourLoggers ...*Logger) *LoggerAsWriter {
  186. if len(ourLoggers) == 0 {
  187. l, _ := NamedLoggers.Load(DEFAULT)
  188. ourLoggers = []*Logger{l}
  189. }
  190. l := &LoggerAsWriter{
  191. ourLoggers: ourLoggers,
  192. level: FromString(level),
  193. }
  194. return l
  195. }
  196. // Write implements the io.Writer interface to allow spoofing of macaron
  197. func (l *LoggerAsWriter) Write(p []byte) (int, error) {
  198. for _, logger := range l.ourLoggers {
  199. // Skip = 3 because this presumes that we have been called by log.Println()
  200. // If the caller has used log.Output or the like this will be wrong
  201. logger.Log(3, l.level, string(p))
  202. }
  203. return len(p), nil
  204. }
  205. // Log takes a given string and logs it at the set log-level
  206. func (l *LoggerAsWriter) Log(msg string) {
  207. for _, logger := range l.ourLoggers {
  208. // Set the skip to reference the call just above this
  209. _ = logger.Log(1, l.level, msg)
  210. }
  211. }
  212. func init() {
  213. _, filename, _, _ := runtime.Caller(0)
  214. prefix = strings.TrimSuffix(filename, "modules/log/log.go")
  215. }