mirror of
https://github.com/cloudflare/cloudflared.git
synced 2025-07-28 06:29:59 +00:00
TUN-528: Move cloudflared into a separate repo
This commit is contained in:
21
vendor/github.com/rifflock/lfshook/LICENSE
generated
vendored
Normal file
21
vendor/github.com/rifflock/lfshook/LICENSE
generated
vendored
Normal file
@@ -0,0 +1,21 @@
|
||||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2015 Michael Riffle
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
87
vendor/github.com/rifflock/lfshook/README.md
generated
vendored
Normal file
87
vendor/github.com/rifflock/lfshook/README.md
generated
vendored
Normal file
@@ -0,0 +1,87 @@
|
||||
# Local Filesystem Hook for Logrus
|
||||
|
||||
[](http://godoc.org/github.com/rifflock/lfshook)
|
||||
|
||||
Sometimes developers like to write directly to a file on the filesystem. This is a hook for [`logrus`](https://github.com/sirupsen/logrus) which designed to allow users to do that. The log levels are dynamic at instantiation of the hook, so it is capable of logging at some or all levels.
|
||||
|
||||
## Example
|
||||
```go
|
||||
import (
|
||||
"github.com/rifflock/lfshook"
|
||||
"github.com/sirupsen/logrus"
|
||||
)
|
||||
|
||||
var Log *logrus.Logger
|
||||
|
||||
func NewLogger() *logrus.Logger {
|
||||
if Log != nil {
|
||||
return Log
|
||||
}
|
||||
|
||||
pathMap := lfshook.PathMap{
|
||||
logrus.InfoLevel: "/var/log/info.log",
|
||||
logrus.ErrorLevel: "/var/log/error.log",
|
||||
}
|
||||
|
||||
Log = logrus.New()
|
||||
Log.Hooks.Add(lfshook.NewHook(
|
||||
pathMap,
|
||||
&logrus.JSONFormatter{},
|
||||
))
|
||||
return Log
|
||||
}
|
||||
```
|
||||
|
||||
### Formatters
|
||||
`lfshook` will strip colors from any `TextFormatter` type formatters when writing to local file, because the color codes don't look great in file.
|
||||
|
||||
If no formatter is provided via `lfshook.NewHook`, a default text formatter will be used.
|
||||
|
||||
### Log rotation
|
||||
In order to enable automatic log rotation it's possible to provide an io.Writer instead of the path string of a log file.
|
||||
In combination with packages like [go-file-rotatelogs](https://github.com/lestrrat/go-file-rotatelogs) log rotation can easily be achieved.
|
||||
|
||||
```go
|
||||
package main
|
||||
|
||||
import (
|
||||
"github.com/lestrrat/go-file-rotatelogs"
|
||||
"github.com/rifflock/lfshook"
|
||||
"github.com/sirupsen/logrus"
|
||||
)
|
||||
|
||||
var Log *logrus.Logger
|
||||
|
||||
func NewLogger() *logrus.Logger {
|
||||
if Log != nil {
|
||||
return Log
|
||||
}
|
||||
|
||||
path := "/var/log/go.log"
|
||||
writer := rotatelogs.New(
|
||||
path+".%Y%m%d%H%M",
|
||||
rotatelogs.WithLinkName(path),
|
||||
rotatelogs.WithMaxAge(time.Duration(86400)*time.Second),
|
||||
rotatelogs.WithRotationTime(time.Duration(604800)*time.Second),
|
||||
)
|
||||
|
||||
logrus.Hooks.Add(lfshook.NewHook(
|
||||
lfshook.WriterMap{
|
||||
logrus.InfoLevel: writer,
|
||||
logrus.ErrorLevel: writer,
|
||||
},
|
||||
&logrus.JSONFormatter,
|
||||
))
|
||||
|
||||
Log = logrus.New()
|
||||
Log.Hooks.Add(lfshook.NewHook(
|
||||
pathMap,
|
||||
&logrus.JSONFormatter{},
|
||||
))
|
||||
|
||||
return Log
|
||||
}
|
||||
```
|
||||
|
||||
### Note:
|
||||
User who run the go application must have read/write permissions to the selected log files. If the files do not exists yet, then user must have permission to the target directory.
|
192
vendor/github.com/rifflock/lfshook/lfshook.go
generated
vendored
Normal file
192
vendor/github.com/rifflock/lfshook/lfshook.go
generated
vendored
Normal file
@@ -0,0 +1,192 @@
|
||||
// Package lfshook is hook for sirupsen/logrus that used for writing the logs to local files.
|
||||
package lfshook
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"github.com/sirupsen/logrus"
|
||||
"io"
|
||||
"log"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"reflect"
|
||||
"sync"
|
||||
)
|
||||
|
||||
// We are logging to file, strip colors to make the output more readable.
|
||||
var defaultFormatter = &logrus.TextFormatter{DisableColors: true}
|
||||
|
||||
// PathMap is map for mapping a log level to a file's path.
|
||||
// Multiple levels may share a file, but multiple files may not be used for one level.
|
||||
type PathMap map[logrus.Level]string
|
||||
|
||||
// WriterMap is map for mapping a log level to an io.Writer.
|
||||
// Multiple levels may share a writer, but multiple writers may not be used for one level.
|
||||
type WriterMap map[logrus.Level]io.Writer
|
||||
|
||||
// LfsHook is a hook to handle writing to local log files.
|
||||
type LfsHook struct {
|
||||
paths PathMap
|
||||
writers WriterMap
|
||||
levels []logrus.Level
|
||||
lock *sync.Mutex
|
||||
formatter logrus.Formatter
|
||||
|
||||
defaultPath string
|
||||
defaultWriter io.Writer
|
||||
hasDefaultPath bool
|
||||
hasDefaultWriter bool
|
||||
}
|
||||
|
||||
// NewHook returns new LFS hook.
|
||||
// Output can be a string, io.Writer, WriterMap or PathMap.
|
||||
// If using io.Writer or WriterMap, user is responsible for closing the used io.Writer.
|
||||
func NewHook(output interface{}, formatter logrus.Formatter) *LfsHook {
|
||||
hook := &LfsHook{
|
||||
lock: new(sync.Mutex),
|
||||
}
|
||||
|
||||
hook.SetFormatter(formatter)
|
||||
|
||||
switch output.(type) {
|
||||
case string:
|
||||
hook.SetDefaultPath(output.(string))
|
||||
break
|
||||
case io.Writer:
|
||||
hook.SetDefaultWriter(output.(io.Writer))
|
||||
break
|
||||
case PathMap:
|
||||
hook.paths = output.(PathMap)
|
||||
for level := range output.(PathMap) {
|
||||
hook.levels = append(hook.levels, level)
|
||||
}
|
||||
break
|
||||
case WriterMap:
|
||||
hook.writers = output.(WriterMap)
|
||||
for level := range output.(WriterMap) {
|
||||
hook.levels = append(hook.levels, level)
|
||||
}
|
||||
break
|
||||
default:
|
||||
panic(fmt.Sprintf("unsupported level map type: %v", reflect.TypeOf(output)))
|
||||
}
|
||||
|
||||
return hook
|
||||
}
|
||||
|
||||
// SetFormatter sets the format that will be used by hook.
|
||||
// If using text formatter, this method will disable color output to make the log file more readable.
|
||||
func (hook *LfsHook) SetFormatter(formatter logrus.Formatter) {
|
||||
if formatter == nil {
|
||||
formatter = defaultFormatter
|
||||
} else {
|
||||
switch formatter.(type) {
|
||||
case *logrus.TextFormatter:
|
||||
textFormatter := formatter.(*logrus.TextFormatter)
|
||||
textFormatter.DisableColors = true
|
||||
}
|
||||
}
|
||||
|
||||
hook.formatter = formatter
|
||||
}
|
||||
|
||||
// SetDefaultPath sets default path for levels that don't have any defined output path.
|
||||
func (hook *LfsHook) SetDefaultPath(defaultPath string) {
|
||||
hook.defaultPath = defaultPath
|
||||
hook.hasDefaultPath = true
|
||||
}
|
||||
|
||||
// SetDefaultWriter sets default writer for levels that don't have any defined writer.
|
||||
func (hook *LfsHook) SetDefaultWriter(defaultWriter io.Writer) {
|
||||
hook.defaultWriter = defaultWriter
|
||||
hook.hasDefaultWriter = true
|
||||
}
|
||||
|
||||
// Fire writes the log file to defined path or using the defined writer.
|
||||
// User who run this function needs write permissions to the file or directory if the file does not yet exist.
|
||||
func (hook *LfsHook) Fire(entry *logrus.Entry) error {
|
||||
if hook.writers != nil || hook.hasDefaultWriter {
|
||||
return hook.ioWrite(entry)
|
||||
} else if hook.paths != nil || hook.hasDefaultPath {
|
||||
return hook.fileWrite(entry)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// Write a log line to an io.Writer.
|
||||
func (hook *LfsHook) ioWrite(entry *logrus.Entry) error {
|
||||
var (
|
||||
writer io.Writer
|
||||
msg []byte
|
||||
err error
|
||||
ok bool
|
||||
)
|
||||
|
||||
hook.lock.Lock()
|
||||
defer hook.lock.Unlock()
|
||||
|
||||
if writer, ok = hook.writers[entry.Level]; !ok {
|
||||
if hook.hasDefaultWriter {
|
||||
writer = hook.defaultWriter
|
||||
} else {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
// use our formatter instead of entry.String()
|
||||
msg, err = hook.formatter.Format(entry)
|
||||
|
||||
if err != nil {
|
||||
log.Println("failed to generate string for entry:", err)
|
||||
return err
|
||||
}
|
||||
_, err = writer.Write(msg)
|
||||
return err
|
||||
}
|
||||
|
||||
// Write a log line directly to a file.
|
||||
func (hook *LfsHook) fileWrite(entry *logrus.Entry) error {
|
||||
var (
|
||||
fd *os.File
|
||||
path string
|
||||
msg []byte
|
||||
err error
|
||||
ok bool
|
||||
)
|
||||
|
||||
hook.lock.Lock()
|
||||
defer hook.lock.Unlock()
|
||||
|
||||
if path, ok = hook.paths[entry.Level]; !ok {
|
||||
if hook.hasDefaultPath {
|
||||
path = hook.defaultPath
|
||||
} else {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
dir := filepath.Dir(path)
|
||||
os.MkdirAll(dir, os.ModePerm)
|
||||
|
||||
fd, err = os.OpenFile(path, os.O_WRONLY|os.O_APPEND|os.O_CREATE, 0666)
|
||||
if err != nil {
|
||||
log.Println("failed to open logfile:", path, err)
|
||||
return err
|
||||
}
|
||||
defer fd.Close()
|
||||
|
||||
// use our formatter instead of entry.String()
|
||||
msg, err = hook.formatter.Format(entry)
|
||||
|
||||
if err != nil {
|
||||
log.Println("failed to generate string for entry:", err)
|
||||
return err
|
||||
}
|
||||
fd.Write(msg)
|
||||
return nil
|
||||
}
|
||||
|
||||
// Levels returns configured log levels.
|
||||
func (hook *LfsHook) Levels() []logrus.Level {
|
||||
return logrus.AllLevels
|
||||
}
|
49
vendor/github.com/rifflock/lfshook/lfshook_test.go
generated
vendored
Normal file
49
vendor/github.com/rifflock/lfshook/lfshook_test.go
generated
vendored
Normal file
@@ -0,0 +1,49 @@
|
||||
package lfshook
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"github.com/sirupsen/logrus"
|
||||
"io/ioutil"
|
||||
"os"
|
||||
"testing"
|
||||
)
|
||||
|
||||
const expectedMsg = "This is the expected test message."
|
||||
const unexpectedMsg = "This message should not be logged."
|
||||
|
||||
// Tests that writing to a tempfile log works.
|
||||
// Matches the 'msg' of the output and deletes the tempfile.
|
||||
func TestLogEntryWritten(t *testing.T) {
|
||||
log := logrus.New()
|
||||
// The colors were messing with the regexp so I turned them off.
|
||||
tmpfile, err := ioutil.TempFile("", "test_lfshook")
|
||||
if err != nil {
|
||||
t.Errorf("Unable to generate logfile due to err: %s", err)
|
||||
}
|
||||
fname := tmpfile.Name()
|
||||
defer func() {
|
||||
tmpfile.Close()
|
||||
os.Remove(fname)
|
||||
}()
|
||||
hook := NewHook(PathMap{
|
||||
logrus.InfoLevel: fname,
|
||||
}, nil)
|
||||
log.Hooks.Add(hook)
|
||||
|
||||
log.Info(expectedMsg)
|
||||
log.Warn(unexpectedMsg)
|
||||
|
||||
contents, err := ioutil.ReadAll(tmpfile)
|
||||
if err != nil {
|
||||
t.Errorf("Error while reading from tmpfile: %s", err)
|
||||
}
|
||||
|
||||
if !bytes.Contains(contents, []byte("msg=\""+expectedMsg+"\"")) {
|
||||
t.Errorf("Message read (%s) doesnt match message written (%s) for file: %s", contents, expectedMsg, fname)
|
||||
}
|
||||
|
||||
if bytes.Contains(contents, []byte("msg=\""+unexpectedMsg+"\"")) {
|
||||
t.Errorf("Message read (%s) contains message written (%s) for file: %s", contents, unexpectedMsg, fname)
|
||||
}
|
||||
|
||||
}
|
Reference in New Issue
Block a user