http urls monitor.

logger.go 8.2KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338
  1. package logrus
  2. import (
  3. "io"
  4. "os"
  5. "sync"
  6. "sync/atomic"
  7. "time"
  8. )
  9. type Logger struct {
  10. // The logs are `io.Copy`'d to this in a mutex. It's common to set this to a
  11. // file, or leave it default which is `os.Stderr`. You can also set this to
  12. // something more adventorous, such as logging to Kafka.
  13. Out io.Writer
  14. // Hooks for the logger instance. These allow firing events based on logging
  15. // levels and log entries. For example, to send errors to an error tracking
  16. // service, log to StatsD or dump the core on fatal errors.
  17. Hooks LevelHooks
  18. // All log entries pass through the formatter before logged to Out. The
  19. // included formatters are `TextFormatter` and `JSONFormatter` for which
  20. // TextFormatter is the default. In development (when a TTY is attached) it
  21. // logs with colors, but to a file it wouldn't. You can easily implement your
  22. // own that implements the `Formatter` interface, see the `README` or included
  23. // formatters for examples.
  24. Formatter Formatter
  25. // The logging level the logger should log at. This is typically (and defaults
  26. // to) `logrus.Info`, which allows Info(), Warn(), Error() and Fatal() to be
  27. // logged.
  28. Level Level
  29. // Used to sync writing to the log. Locking is enabled by Default
  30. mu MutexWrap
  31. // Reusable empty entry
  32. entryPool sync.Pool
  33. }
  34. type MutexWrap struct {
  35. lock sync.Mutex
  36. disabled bool
  37. }
  38. func (mw *MutexWrap) Lock() {
  39. if !mw.disabled {
  40. mw.lock.Lock()
  41. }
  42. }
  43. func (mw *MutexWrap) Unlock() {
  44. if !mw.disabled {
  45. mw.lock.Unlock()
  46. }
  47. }
  48. func (mw *MutexWrap) Disable() {
  49. mw.disabled = true
  50. }
  51. // Creates a new logger. Configuration should be set by changing `Formatter`,
  52. // `Out` and `Hooks` directly on the default logger instance. You can also just
  53. // instantiate your own:
  54. //
  55. // var log = &Logger{
  56. // Out: os.Stderr,
  57. // Formatter: new(JSONFormatter),
  58. // Hooks: make(LevelHooks),
  59. // Level: logrus.DebugLevel,
  60. // }
  61. //
  62. // It's recommended to make this a global instance called `log`.
  63. func New() *Logger {
  64. return &Logger{
  65. Out: os.Stderr,
  66. Formatter: new(TextFormatter),
  67. Hooks: make(LevelHooks),
  68. Level: InfoLevel,
  69. }
  70. }
  71. func (logger *Logger) newEntry() *Entry {
  72. entry, ok := logger.entryPool.Get().(*Entry)
  73. if ok {
  74. return entry
  75. }
  76. return NewEntry(logger)
  77. }
  78. func (logger *Logger) releaseEntry(entry *Entry) {
  79. logger.entryPool.Put(entry)
  80. }
  81. // Adds a field to the log entry, note that it doesn't log until you call
  82. // Debug, Print, Info, Warn, Error, Fatal or Panic. It only creates a log entry.
  83. // If you want multiple fields, use `WithFields`.
  84. func (logger *Logger) WithField(key string, value interface{}) *Entry {
  85. entry := logger.newEntry()
  86. defer logger.releaseEntry(entry)
  87. return entry.WithField(key, value)
  88. }
  89. // Adds a struct of fields to the log entry. All it does is call `WithField` for
  90. // each `Field`.
  91. func (logger *Logger) WithFields(fields Fields) *Entry {
  92. entry := logger.newEntry()
  93. defer logger.releaseEntry(entry)
  94. return entry.WithFields(fields)
  95. }
  96. // Add an error as single field to the log entry. All it does is call
  97. // `WithError` for the given `error`.
  98. func (logger *Logger) WithError(err error) *Entry {
  99. entry := logger.newEntry()
  100. defer logger.releaseEntry(entry)
  101. return entry.WithError(err)
  102. }
  103. // Overrides the time of the log entry.
  104. func (logger *Logger) WithTime(t time.Time) *Entry {
  105. entry := logger.newEntry()
  106. defer logger.releaseEntry(entry)
  107. return entry.WithTime(t)
  108. }
  109. func (logger *Logger) Debugf(format string, args ...interface{}) {
  110. if logger.level() >= DebugLevel {
  111. entry := logger.newEntry()
  112. entry.Debugf(format, args...)
  113. logger.releaseEntry(entry)
  114. }
  115. }
  116. func (logger *Logger) Infof(format string, args ...interface{}) {
  117. if logger.level() >= InfoLevel {
  118. entry := logger.newEntry()
  119. entry.Infof(format, args...)
  120. logger.releaseEntry(entry)
  121. }
  122. }
  123. func (logger *Logger) Printf(format string, args ...interface{}) {
  124. entry := logger.newEntry()
  125. entry.Printf(format, args...)
  126. logger.releaseEntry(entry)
  127. }
  128. func (logger *Logger) Warnf(format string, args ...interface{}) {
  129. if logger.level() >= WarnLevel {
  130. entry := logger.newEntry()
  131. entry.Warnf(format, args...)
  132. logger.releaseEntry(entry)
  133. }
  134. }
  135. func (logger *Logger) Warningf(format string, args ...interface{}) {
  136. if logger.level() >= WarnLevel {
  137. entry := logger.newEntry()
  138. entry.Warnf(format, args...)
  139. logger.releaseEntry(entry)
  140. }
  141. }
  142. func (logger *Logger) Errorf(format string, args ...interface{}) {
  143. if logger.level() >= ErrorLevel {
  144. entry := logger.newEntry()
  145. entry.Errorf(format, args...)
  146. logger.releaseEntry(entry)
  147. }
  148. }
  149. func (logger *Logger) Fatalf(format string, args ...interface{}) {
  150. if logger.level() >= FatalLevel {
  151. entry := logger.newEntry()
  152. entry.Fatalf(format, args...)
  153. logger.releaseEntry(entry)
  154. }
  155. Exit(1)
  156. }
  157. func (logger *Logger) Panicf(format string, args ...interface{}) {
  158. if logger.level() >= PanicLevel {
  159. entry := logger.newEntry()
  160. entry.Panicf(format, args...)
  161. logger.releaseEntry(entry)
  162. }
  163. }
  164. func (logger *Logger) Debug(args ...interface{}) {
  165. if logger.level() >= DebugLevel {
  166. entry := logger.newEntry()
  167. entry.Debug(args...)
  168. logger.releaseEntry(entry)
  169. }
  170. }
  171. func (logger *Logger) Info(args ...interface{}) {
  172. if logger.level() >= InfoLevel {
  173. entry := logger.newEntry()
  174. entry.Info(args...)
  175. logger.releaseEntry(entry)
  176. }
  177. }
  178. func (logger *Logger) Print(args ...interface{}) {
  179. entry := logger.newEntry()
  180. entry.Info(args...)
  181. logger.releaseEntry(entry)
  182. }
  183. func (logger *Logger) Warn(args ...interface{}) {
  184. if logger.level() >= WarnLevel {
  185. entry := logger.newEntry()
  186. entry.Warn(args...)
  187. logger.releaseEntry(entry)
  188. }
  189. }
  190. func (logger *Logger) Warning(args ...interface{}) {
  191. if logger.level() >= WarnLevel {
  192. entry := logger.newEntry()
  193. entry.Warn(args...)
  194. logger.releaseEntry(entry)
  195. }
  196. }
  197. func (logger *Logger) Error(args ...interface{}) {
  198. if logger.level() >= ErrorLevel {
  199. entry := logger.newEntry()
  200. entry.Error(args...)
  201. logger.releaseEntry(entry)
  202. }
  203. }
  204. func (logger *Logger) Fatal(args ...interface{}) {
  205. if logger.level() >= FatalLevel {
  206. entry := logger.newEntry()
  207. entry.Fatal(args...)
  208. logger.releaseEntry(entry)
  209. }
  210. Exit(1)
  211. }
  212. func (logger *Logger) Panic(args ...interface{}) {
  213. if logger.level() >= PanicLevel {
  214. entry := logger.newEntry()
  215. entry.Panic(args...)
  216. logger.releaseEntry(entry)
  217. }
  218. }
  219. func (logger *Logger) Debugln(args ...interface{}) {
  220. if logger.level() >= DebugLevel {
  221. entry := logger.newEntry()
  222. entry.Debugln(args...)
  223. logger.releaseEntry(entry)
  224. }
  225. }
  226. func (logger *Logger) Infoln(args ...interface{}) {
  227. if logger.level() >= InfoLevel {
  228. entry := logger.newEntry()
  229. entry.Infoln(args...)
  230. logger.releaseEntry(entry)
  231. }
  232. }
  233. func (logger *Logger) Println(args ...interface{}) {
  234. entry := logger.newEntry()
  235. entry.Println(args...)
  236. logger.releaseEntry(entry)
  237. }
  238. func (logger *Logger) Warnln(args ...interface{}) {
  239. if logger.level() >= WarnLevel {
  240. entry := logger.newEntry()
  241. entry.Warnln(args...)
  242. logger.releaseEntry(entry)
  243. }
  244. }
  245. func (logger *Logger) Warningln(args ...interface{}) {
  246. if logger.level() >= WarnLevel {
  247. entry := logger.newEntry()
  248. entry.Warnln(args...)
  249. logger.releaseEntry(entry)
  250. }
  251. }
  252. func (logger *Logger) Errorln(args ...interface{}) {
  253. if logger.level() >= ErrorLevel {
  254. entry := logger.newEntry()
  255. entry.Errorln(args...)
  256. logger.releaseEntry(entry)
  257. }
  258. }
  259. func (logger *Logger) Fatalln(args ...interface{}) {
  260. if logger.level() >= FatalLevel {
  261. entry := logger.newEntry()
  262. entry.Fatalln(args...)
  263. logger.releaseEntry(entry)
  264. }
  265. Exit(1)
  266. }
  267. func (logger *Logger) Panicln(args ...interface{}) {
  268. if logger.level() >= PanicLevel {
  269. entry := logger.newEntry()
  270. entry.Panicln(args...)
  271. logger.releaseEntry(entry)
  272. }
  273. }
  274. //When file is opened with appending mode, it's safe to
  275. //write concurrently to a file (within 4k message on Linux).
  276. //In these cases user can choose to disable the lock.
  277. func (logger *Logger) SetNoLock() {
  278. logger.mu.Disable()
  279. }
  280. func (logger *Logger) level() Level {
  281. return Level(atomic.LoadUint32((*uint32)(&logger.Level)))
  282. }
  283. func (logger *Logger) SetLevel(level Level) {
  284. atomic.StoreUint32((*uint32)(&logger.Level), uint32(level))
  285. }
  286. func (logger *Logger) SetOutput(out io.Writer) {
  287. logger.mu.Lock()
  288. defer logger.mu.Unlock()
  289. logger.Out = out
  290. }
  291. func (logger *Logger) AddHook(hook Hook) {
  292. logger.mu.Lock()
  293. defer logger.mu.Unlock()
  294. logger.Hooks.Add(hook)
  295. }