-
Notifications
You must be signed in to change notification settings - Fork 1
/
logger.go
121 lines (105 loc) · 2.54 KB
/
logger.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
package logger
import (
"io"
"os"
"runtime"
"strconv"
"strings"
"time"
"github.com/sirupsen/logrus"
"golang.org/x/crypto/ssh/terminal"
)
type Fields logrus.Fields
type Logger struct {
logrus *logrus.Logger
counters map[string]*counter
file bool
gauge map[string]interface{}
metricPrinter bool
metricsDelay time.Duration
}
type counter struct {
value *int64
lastValue int64
lastObserved time.Time
}
type Options struct {
File bool
Delay time.Duration
}
func New(o ...*Options) *Logger {
l := &Logger{
logrus: logrus.New(),
metricsDelay: time.Second * 60,
}
for _, option := range o {
l.file = option.File
if option.Delay != 0 {
l.metricsDelay = option.Delay
}
}
logLevel := strings.ToLower(os.Getenv("LOG_LEVEL"))
if logLevel == "warn" {
l.logrus.SetLevel(logrus.WarnLevel)
} else if logLevel == "info" {
l.logrus.SetLevel(logrus.InfoLevel)
} else if logLevel == "error" {
l.logrus.SetLevel(logrus.ErrorLevel)
} else {
l.logrus.SetLevel(logrus.DebugLevel)
}
l.logrus.Out = os.Stderr
if terminal.IsTerminal(int(os.Stdin.Fd())) {
l.logrus.SetFormatter(&logrus.TextFormatter{})
} else {
l.logrus.SetFormatter(&logrus.JSONFormatter{})
}
l.gauge = make(map[string]interface{})
l.counters = make(map[string]*counter)
return l
}
func (l *Logger) Profile(then time.Time) {
l.prepFields(1, l.Field("duration", time.Now().Sub(then))).Debug("Profile")
}
type FieldPair struct {
key string
value interface{}
}
func (l *Logger) Field(key string, value interface{}) FieldPair {
return FieldPair{
key: key,
value: value,
}
}
func (l *Logger) prepFields(caller int, fps ...FieldPair) *logrus.Entry {
e := logrus.NewEntry(l.logrus)
pc, filename, linenumber, ok := runtime.Caller(caller + 2)
if !ok {
panic("How did you get here?")
}
if l.file {
e = e.WithField("file", filename+":"+strconv.FormatInt(int64(linenumber), 10))
}
e = e.WithField("method", runtime.FuncForPC(pc).Name())
for _, fp := range fps {
e = e.WithField(fp.key, fp.value)
}
return e
}
func (l *Logger) Debug(msg string, fps ...FieldPair) {
l.prepFields(0, fps...).Debug(msg)
}
func (l *Logger) Info(msg string, fps ...FieldPair) {
l.prepFields(0, fps...).Info(msg)
}
func (l *Logger) Finfo(w io.Writer, msg string, fps ...FieldPair) {
l.logrus.Out = w
l.prepFields(0, fps...).Info(msg)
l.logrus.Out = os.Stderr
}
func (l *Logger) Error(msg string, fps ...FieldPair) {
l.prepFields(0, fps...).Error(msg)
}
func (l *Logger) Warn(msg string, fps ...FieldPair) {
l.prepFields(0, fps...).Warn(msg)
}