Logging - Writer Interface - 图1tip

The Writer interface is the lowest-level IO writing interface. If your business needs to customize the log content printing, it is recommended to use the Handler feature. Refer to the section: Logging - Handler

Custom Writer Interface

The glog module implements log content printing for both standard output and file output. Of course, developers can also implement custom log content output by customizing the io.Writer interface. io.Writer is a content output interface provided by the standard library, defined as follows:

  1. type Writer interface {
  2. Write(p []byte) (n int, err error)
  3. }

We can implement custom Writer output using the SetWriter method or the chaining method To. Developers can define operations in this Writer, and they can also integrate other module functions within it.

Additionally, the glog.Logger object has already implemented the io.Writer interface, making it very convenient for developers to integrate glog into other modules.

Example 1: Implementing Log HOOK

In this example, we implement a custom Writer object MyWriter. In the Writer interface implementation of this object, we evaluate the log content. If a PANI or FATA error occurs, it indicates a severe error, and the interface will first notify the Monitor monitoring service through an HTTP interface. Then, the log content is written to files and standard output using the glog module according to the configuration.

  1. package main
  2. import (
  3. "context"
  4. "fmt"
  5. "github.com/gogf/gf/v2/frame/g"
  6. "github.com/gogf/gf/v2/net/ghttp"
  7. "github.com/gogf/gf/v2/os/glog"
  8. "github.com/gogf/gf/v2/text/gregex"
  9. )
  10. type MyWriter struct {
  11. logger *glog.Logger
  12. }
  13. func (w *MyWriter) Write(p []byte) (n int, err error) {
  14. var (
  15. s = string(p)
  16. ctx = context.Background()
  17. )
  18. if gregex.IsMatchString(`PANI|FATA`, s) {
  19. fmt.Println("SERIOUS ISSUE OCCURRED!! I'd better tell monitor in first time!")
  20. g.Client().PostContent(ctx, "http://monitor.mydomain.com", s)
  21. }
  22. return w.logger.Write(p)
  23. }
  24. func main() {
  25. var ctx = context.Background()
  26. glog.SetWriter(&MyWriter{
  27. logger: glog.New(),
  28. })
  29. glog.Fatal(ctx, "FATAL ERROR")
  30. }

After execution, the output result is:

  1. SERIOUS ISSUE OCCURRED!! I'd better tell monitor in first time!
  2. 2019-05-23 20:14:49.374 [FATA] FATAL ERROR
  3. Stack:
  4. 1. /Users/john/Workspace/Go/GOPATH/src/github.com/gogf/gf/v2/geg/os/glog/glog_writer_hook.go:27

Example 2: Integrating with Graylog

Suppose we need to output logs to both files and standard output, and simultaneously output logs to Graylog. Clearly, this can only be achieved by customizing the Writer. Similarly, we can customize the output to other log collection components or databases.

Graylog is a centralized log management solution comparable to ELK, supporting data collection, retrieval, and visualized Dashboards.

Example code:

  1. package main
  2. import (
  3. "context"
  4. "github.com/gogf/gf/v2/os/glog"
  5. "github.com/robertkowalski/graylog-golang"
  6. )
  7. type MyGrayLogWriter struct {
  8. gelf *gelf.Gelf
  9. logger *glog.Logger
  10. }
  11. func (w *MyGrayLogWriter) Write(p []byte) (n int, err error) {
  12. w.gelf.Send(p)
  13. return w.logger.Write(p)
  14. }
  15. func main() {
  16. var ctx = context.Background()
  17. glog.SetWriter(&MyGrayLogWriter{
  18. logger : glog.New(),
  19. gelf : gelf.New(gelf.Config{
  20. GraylogPort : 80,
  21. GraylogHostname : "graylog-host.com",
  22. Connection : "wan",
  23. MaxChunkSizeWan : 42,
  24. MaxChunkSizeLan : 1337,
  25. }),
  26. })
  27. glog.Println(ctx, "test log")
  28. }