()
| 100 | } |
| 101 | |
| 102 | func Example_advancedConfiguration() { |
| 103 | // The bundled Config struct only supports the most common configuration |
| 104 | // options. More complex needs, like splitting logs between multiple files |
| 105 | // or writing to non-file outputs, require use of the zapcore package. |
| 106 | // |
| 107 | // In this example, imagine we're both sending our logs to Kafka and writing |
| 108 | // them to the console. We'd like to encode the console output and the Kafka |
| 109 | // topics differently, and we'd also like special treatment for |
| 110 | // high-priority logs. |
| 111 | |
| 112 | // First, define our level-handling logic. |
| 113 | highPriority := zap.LevelEnablerFunc(func(lvl zapcore.Level) bool { |
| 114 | return lvl >= zapcore.ErrorLevel |
| 115 | }) |
| 116 | lowPriority := zap.LevelEnablerFunc(func(lvl zapcore.Level) bool { |
| 117 | return lvl < zapcore.ErrorLevel |
| 118 | }) |
| 119 | |
| 120 | // Assume that we have clients for two Kafka topics. The clients implement |
| 121 | // zapcore.WriteSyncer and are safe for concurrent use. (If they only |
| 122 | // implement io.Writer, we can use zapcore.AddSync to add a no-op Sync |
| 123 | // method. If they're not safe for concurrent use, we can add a protecting |
| 124 | // mutex with zapcore.Lock.) |
| 125 | topicDebugging := zapcore.AddSync(io.Discard) |
| 126 | topicErrors := zapcore.AddSync(io.Discard) |
| 127 | |
| 128 | // High-priority output should also go to standard error, and low-priority |
| 129 | // output should also go to standard out. |
| 130 | consoleDebugging := zapcore.Lock(os.Stdout) |
| 131 | consoleErrors := zapcore.Lock(os.Stderr) |
| 132 | |
| 133 | // Optimize the Kafka output for machine consumption and the console output |
| 134 | // for human operators. |
| 135 | kafkaEncoder := zapcore.NewJSONEncoder(zap.NewProductionEncoderConfig()) |
| 136 | consoleEncoder := zapcore.NewConsoleEncoder(zap.NewDevelopmentEncoderConfig()) |
| 137 | |
| 138 | // Join the outputs, encoders, and level-handling functions into |
| 139 | // zapcore.Cores, then tee the four cores together. |
| 140 | core := zapcore.NewTee( |
| 141 | zapcore.NewCore(kafkaEncoder, topicErrors, highPriority), |
| 142 | zapcore.NewCore(consoleEncoder, consoleErrors, highPriority), |
| 143 | zapcore.NewCore(kafkaEncoder, topicDebugging, lowPriority), |
| 144 | zapcore.NewCore(consoleEncoder, consoleDebugging, lowPriority), |
| 145 | ) |
| 146 | |
| 147 | // From a zapcore.Core, it's easy to construct a Logger. |
| 148 | logger := zap.New(core) |
| 149 | defer logger.Sync() |
| 150 | logger.Info("constructed a logger") |
| 151 | } |
| 152 | |
| 153 | func ExampleNamespace() { |
| 154 | logger := zap.NewExample() |
nothing calls this directly
no test coverage detected