1Go-Log
2======
3
4[![Build Status](https://travis-ci.org/ian-kent/go-log.svg?branch=master)](https://travis-ci.org/ian-kent/go-log)
5
6A logger, for Go!
7
8It's sort of ```log``` and ```code.google.com/p/log4go``` compatible, so in most cases
9can be used without any code changes.
10
11#### Breaking change
12
13go-log was inconsistent with the default Go 'log' package, and log.Fatal calls didn't trigger an os.Exit(1).
14
15This has been fixed in the current release of go-log, which might break backwards compatibility.
16
17You can disable the fix by setting ExitOnFatal to false, e.g.
18
19    log.Logger().ExitOnFatal = false
20
21### Getting started
22
23Install go-log:
24
25```
26go get github.com/ian-kent/go-log/log
27```
28
29Use the logger in your application:
30
31```
32import(
33  "github.com/ian-kent/go-log/log"
34)
35
36// Pass a log message and arguments directly
37log.Debug("Example log message: %s", "example arg")
38
39// Pass a function which returns a log message and arguments
40log.Debug(func(){[]interface{}{"Example log message: %s", "example arg"}})
41log.Debug(func(i ...interface{}){[]interface{}{"Example log message: %s", "example arg"}})
42```
43
44You can also get the logger instance:
45```
46logger := log.Logger()
47logger.Debug("Yey!")
48```
49
50Or get a named logger instance:
51
52```
53logger := log.Logger("foo.bar")
54```
55
56### Log levels
57
58The default log level is DEBUG.
59
60To get the current log level:
61
62```
63level := logger.Level()
64```
65
66Or to set the log level:
67
68```
69// From a LogLevel
70logger.SetLevel(levels.TRACE)
71
72// From a string
73logger.SetLevel(log.Stol("TRACE"))
74```
75
76### Log appenders
77
78The default log appender is ```appenders.Console()```, which logs
79the raw message to STDOUT.
80
81To get the current log appender:
82
83```
84appender := logger.Appender()
85```
86
87If the appender is ```nil```, the parent loggers appender will be used
88instead.
89
90If the appender eventually resolves to ```nil```, log data will be
91silently dropped.
92
93You can set the log appender:
94
95```
96logger.SetAppender(appenders.Console())
97```
98
99#### Rolling file appender
100
101Similar to log4j's rolling file appender, you can use
102
103```
104// Append to (or create) file
105logger.SetAppender(appenders.RollingFile("filename.log", true))
106
107// Truncate (or create) file
108logger.SetAppender(appenders.RollingFile("filename.log", false))
109```
110
111You can also control the number of log files which are kept:
112```
113r := appenders.RollingFile("filename.log", true)
114r.MaxBackupIndex = 2 // filename.log, filename.log.1, filename.log.2
115```
116
117And the maximum log file size (in bytes):
118```
119r := appenders.RollingFile("filename.log", true)
120r.MaxFileSize = 1024 // 1KB, defaults to 100MB
121```
122
123#### Fluentd appender
124
125The fluentd appender lets you write log data directly to fluentd:
126
127```
128logger.SetAppender(appenders.Fluentd(fluent.Config{}))
129```
130
131It uses ```github.com/t-k/fluent-logger-golang```.
132
133The tag is currently fixed to 'go-log', and the data structure sent
134to fluentd is simple:
135
136```
137{
138  message: "<output from layout>"
139}
140
141```
142
143### Layouts
144
145Each appender has its own layout. This allows the log data to be transformed
146as it is written to the appender.
147
148The default layout is ```layout.Basic()```, which passes the log message
149and its arguments through ```fmt.Sprintf```.
150
151To get the current log appender layout:
152```
153appender := logger.Appender()
154layout := appender.Layout()
155```
156
157To set the log appender layout:
158```
159appender.SetLayout(layout.Basic())
160```
161
162You can also use ```layout.Pattern(pattern string)```, which accepts a
163pattern format similar to log4j:
164
165| Code | Description
166| ---- | -----------
167| %c   | The package the log statement is in
168| %C   | Currently also the package the log statement is in
169| %d   | The current date/time, using ```time.Now().String()```
170| %F   | The filename the log statement is in
171| %l   | The location of the log statement, e.g. ```package/somefile.go:12```
172| %L   | The line number the log statement is on
173| %m   | The log message and its arguments formatted with ```fmt.Sprintf```
174| %n   | A new-line character
175| %p   | Priority - the log level
176| %r   | ms since logger was created
177
178### Logger inheritance
179
180Loggers are namespaced with a ```.```, following similar rules to Log4j.
181
182If you create a logger named ```foo```, it will automatically inherit the
183log settings (levels and appender) of the root logger.
184
185If you then create a logger named ```foo.bar```, it will inherit the log
186settings of ```foo```, which in turn inherits the log settings from the
187root logger.
188
189You can break this by setting the log level or setting an appender on
190a child logger, e.g.:
191
192```
193logger := log.Logger("foo.bar")
194logger.SetLevel(levels.TRACE)
195logger.SetAppender(appenders.Console())
196```
197
198If you then created a logger named ```foo.bar.qux```, it would inherit
199the trace level and console appender of the ```foo.bar``` logger.
200
201### Roadmap
202
203* log4j configuration support
204  * .properties
205  * .xml
206  * .json
207* layouts
208  * fixmes/todos in pattern layout
209* appenders
210  * add socket appender
211  * fixmes/todos and tests for fluentd appender
212* optimise logger creation
213  * collapse loggers when parent namespace is unused
214  * reorganise loggers when new child tree is created
215* add godoc documentation
216
217### Contributing
218
219Before submitting a pull request:
220
221  * Format your code: ```go fmt ./...```
222  * Make sure tests pass: ```go test ./...```
223
224### Licence
225
226Copyright ©‎ 2014, Ian Kent (http://www.iankent.eu).
227
228Released under MIT license, see [LICENSE](LICENSE.md) for details.
229