]>
Commit | Line | Data |
---|---|---|
9b12e4fe JC |
1 | package logrus |
2 | ||
3 | import "time" | |
4 | ||
5 | const DefaultTimestampFormat = time.RFC3339 | |
6 | ||
7 | // The Formatter interface is used to implement a custom Formatter. It takes an | |
8 | // `Entry`. It exposes all the fields, including the default ones: | |
9 | // | |
10 | // * `entry.Data["msg"]`. The message passed from Info, Warn, Error .. | |
11 | // * `entry.Data["time"]`. The timestamp. | |
12 | // * `entry.Data["level"]. The level the entry was logged at. | |
13 | // | |
14 | // Any additional fields added with `WithField` or `WithFields` are also in | |
15 | // `entry.Data`. Format is expected to return an array of bytes which are then | |
16 | // logged to `logger.Out`. | |
17 | type Formatter interface { | |
18 | Format(*Entry) ([]byte, error) | |
19 | } | |
20 | ||
21 | // This is to not silently overwrite `time`, `msg` and `level` fields when | |
22 | // dumping it. If this code wasn't there doing: | |
23 | // | |
24 | // logrus.WithField("level", 1).Info("hello") | |
25 | // | |
26 | // Would just silently drop the user provided level. Instead with this code | |
27 | // it'll logged as: | |
28 | // | |
29 | // {"level": "info", "fields.level": 1, "msg": "hello", "time": "..."} | |
30 | // | |
31 | // It's not exported because it's still using Data in an opinionated way. It's to | |
32 | // avoid code duplication between the two default formatters. | |
33 | func prefixFieldClashes(data Fields) { | |
34 | _, ok := data["time"] | |
35 | if ok { | |
36 | data["fields.time"] = data["time"] | |
37 | } | |
38 | ||
39 | _, ok = data["msg"] | |
40 | if ok { | |
41 | data["fields.msg"] = data["msg"] | |
42 | } | |
43 | ||
44 | _, ok = data["level"] | |
45 | if ok { | |
46 | data["fields.level"] = data["level"] | |
47 | } | |
48 | } |