From bb1c27c36ab72f091fd8d8f451ed3b9b24d2990b Mon Sep 17 00:00:00 2001 From: John Date: Wed, 26 Feb 2020 23:26:24 +0800 Subject: [PATCH] add more unit testing cases for glog --- .example/other/test.go | 33 +-- encoding/gbinary/gbinary_be.go | 17 +- encoding/gbinary/gbinary_bits.go | 2 +- encoding/gbinary/gbinary_le.go | 9 +- internal/rwmutex/rwmutex.go | 9 + os/glog/glog.go | 12 - os/glog/glog_logger.go | 7 + os/glog/glog_logger_api.go | 33 +-- os/glog/glog_logger_chaining.go | 2 + os/glog/glog_logger_config.go | 39 +-- os/glog/glog_logger_level.go | 60 +++++ os/glog/glog_z_unit_basic_test.go | 81 ++++++ os/glog/glog_z_unit_chaining_test.go | 243 ++++++++++++++++++ ...nit_test.go => glog_z_unit_config_test.go} | 0 os/glog/glog_z_unit_level_test.go | 59 +++++ 15 files changed, 529 insertions(+), 77 deletions(-) create mode 100644 os/glog/glog_logger_level.go create mode 100644 os/glog/glog_z_unit_basic_test.go create mode 100644 os/glog/glog_z_unit_chaining_test.go rename os/glog/{glog_z_unit_test.go => glog_z_unit_config_test.go} (100%) create mode 100644 os/glog/glog_z_unit_level_test.go diff --git a/.example/other/test.go b/.example/other/test.go index bf9e3530a..6d92a4fd6 100644 --- a/.example/other/test.go +++ b/.example/other/test.go @@ -1,29 +1,18 @@ package main import ( - "github.com/gogf/gf/container/garray" - "github.com/gogf/gf/os/gfile" - "github.com/gogf/gf/text/gstr" + "fmt" + "github.com/gogf/gf/os/glog" ) func main() { - arrayIM := garray.NewStrArraySize(0, 2000000) - arrayNoIM := garray.NewStrArraySize(0, 2000000) - content := gfile.GetContents("/Users/john/Downloads/keys.txt") - for _, line := range gstr.Split(content, "\n") { - if gstr.HasPrefix(line, "up:") || - gstr.HasPrefix(line, "helper") || - gstr.HasPrefix(line, "u5_0_fl") || - gstr.HasPrefix(line, "ubul#") || - gstr.HasPrefix(line, "uf:") || - gstr.HasPrefix(line, "ufr:") || - gstr.HasPrefix(line, "friend:") || - gstr.HasPrefix(line, "ubl:") { - arrayIM.Append(line) - } else { - arrayNoIM.Append(line) - } - } - gfile.PutContents("/Users/john/Downloads/keysIM.txt", arrayIM.Join("\n")) - gfile.PutContents("/Users/john/Downloads/keysNoIM.txt", arrayNoIM.Join("\n")) + fmt.Println(glog.LEVEL_ALL) + fmt.Println(glog.LEVEL_DEV) + fmt.Println(glog.LEVEL_PROD) + fmt.Println(glog.LEVEL_DEBU) + fmt.Println(glog.LEVEL_INFO) + fmt.Println(glog.LEVEL_NOTI) + fmt.Println(glog.LEVEL_WARN) + fmt.Println(glog.LEVEL_ERRO) + fmt.Println(glog.LEVEL_CRIT) } diff --git a/encoding/gbinary/gbinary_be.go b/encoding/gbinary/gbinary_be.go index 41b890c6e..7d5fcbf40 100644 --- a/encoding/gbinary/gbinary_be.go +++ b/encoding/gbinary/gbinary_be.go @@ -13,9 +13,12 @@ import ( "math" ) -// 针对基本类型进行二进制打包,支持的基本数据类型包括: -// int/8/16/32/64、uint/8/16/32/64、float32/64、bool、string、[]byte。 -// 其他未知类型使用 fmt.Sprintf("%v", value) 转换为字符串之后处理。 +// BeEncode encodes one or multiple into bytes using BigEndian. +// It uses type asserting checking the type of each value of and internally +// calls corresponding converting function do the bytes converting. +// +// It supports common variable type asserting, and finally it uses fmt.Sprintf converting +// value to string and then to bytes. func BeEncode(values ...interface{}) []byte { buf := new(bytes.Buffer) for i := 0; i < len(values); i++ { @@ -135,7 +138,7 @@ func BeEncodeInt8(i int8) []byte { } func BeEncodeUint8(i uint8) []byte { - return []byte{byte(i)} + return []byte{i} } func BeEncodeInt16(i int16) []byte { @@ -266,8 +269,10 @@ func BeDecodeToFloat64(b []byte) float64 { return math.Float64frombits(binary.BigEndian.Uint64(BeFillUpSize(b, 8))) } -// 当b位数不够时,进行低位补0。 -// 注意这里为了不影响原有输入参数,是采用的值复制设计。 +// BeFillUpSize fills up the bytes to given length using big BigEndian. +// +// Note that it creates a new bytes slice by copying the original one to avoid changing +// the original parameter bytes. func BeFillUpSize(b []byte, l int) []byte { if len(b) >= l { return b[:l] diff --git a/encoding/gbinary/gbinary_bits.go b/encoding/gbinary/gbinary_bits.go index a61b5fdf7..d477346eb 100644 --- a/encoding/gbinary/gbinary_bits.go +++ b/encoding/gbinary/gbinary_bits.go @@ -46,7 +46,7 @@ func EncodeBitsToBytes(bits []Bit) []byte { // 解析为int func DecodeBits(bits []Bit) int { - v := int(0) + v := 0 for _, i := range bits { v = v<<1 | int(i) } diff --git a/encoding/gbinary/gbinary_le.go b/encoding/gbinary/gbinary_le.go index 07632b3ae..db2cf0439 100644 --- a/encoding/gbinary/gbinary_le.go +++ b/encoding/gbinary/gbinary_le.go @@ -13,9 +13,12 @@ import ( "math" ) -// 针对基本类型进行二进制打包,支持的基本数据类型包括: -// int/8/16/32/64、uint/8/16/32/64、float32/64、bool、string、[]byte。 -// 其他未知类型使用 fmt.Sprintf("%v", value) 转换为字符串之后处理。 +// LeEncode encodes one or multiple into bytes using LittleEndian. +// It uses type asserting checking the type of each value of and internally +// calls corresponding converting function do the bytes converting. +// +// It supports common variable type asserting, and finally it uses fmt.Sprintf converting +// value to string and then to bytes. func LeEncode(values ...interface{}) []byte { buf := new(bytes.Buffer) for i := 0; i < len(values); i++ { diff --git a/internal/rwmutex/rwmutex.go b/internal/rwmutex/rwmutex.go index ecf2c45bf..3f135aab0 100644 --- a/internal/rwmutex/rwmutex.go +++ b/internal/rwmutex/rwmutex.go @@ -28,28 +28,37 @@ func New(safe ...bool) *RWMutex { return mu } +// IsSafe checks and returns whether current mutex is in concurrent-safe usage. func (mu *RWMutex) IsSafe() bool { return mu.safe } +// Lock locks mutex for writing. +// It does nothing if it is not in concurrent-safe usage. func (mu *RWMutex) Lock() { if mu.safe { mu.RWMutex.Lock() } } +// Unlock unlocks mutex for writing. +// It does nothing if it is not in concurrent-safe usage. func (mu *RWMutex) Unlock() { if mu.safe { mu.RWMutex.Unlock() } } +// RLock locks mutex for reading. +// It does nothing if it is not in concurrent-safe usage. func (mu *RWMutex) RLock() { if mu.safe { mu.RWMutex.RLock() } } +// RUnlock unlocks mutex for reading. +// It does nothing if it is not in concurrent-safe usage. func (mu *RWMutex) RUnlock() { if mu.safe { mu.RWMutex.RUnlock() diff --git a/os/glog/glog.go b/os/glog/glog.go index 9dafb97d0..cb3a005d2 100644 --- a/os/glog/glog.go +++ b/os/glog/glog.go @@ -14,18 +14,6 @@ import ( "github.com/gogf/gf/os/grpool" ) -const ( - LEVEL_ALL = LEVEL_DEBU | LEVEL_INFO | LEVEL_NOTI | LEVEL_WARN | LEVEL_ERRO | LEVEL_CRIT - LEVEL_DEV = LEVEL_ALL - LEVEL_PROD = LEVEL_WARN | LEVEL_ERRO | LEVEL_CRIT - LEVEL_DEBU = 1 << iota - LEVEL_INFO - LEVEL_NOTI - LEVEL_WARN - LEVEL_ERRO - LEVEL_CRIT -) - var ( // Default logger object, for package method usage logger = New() diff --git a/os/glog/glog_logger.go b/os/glog/glog_logger.go index 21c82a74b..f990c0057 100644 --- a/os/glog/glog_logger.go +++ b/os/glog/glog_logger.go @@ -55,6 +55,13 @@ func New() *Logger { } } +// NewWithWriter creates and returns a custom logger with io.Writer. +func NewWithWriter(writer io.Writer) *Logger { + l := New() + l.SetWriter(writer) + return l +} + // Clone returns a new logger, which is the clone the current logger. func (l *Logger) Clone() *Logger { logger := Logger{} diff --git a/os/glog/glog_logger_api.go b/os/glog/glog_logger_api.go index 58d3484ef..93aa69cbe 100644 --- a/os/glog/glog_logger_api.go +++ b/os/glog/glog_logger_api.go @@ -23,6 +23,7 @@ func (l *Logger) Printf(format string, v ...interface{}) { l.printStd("", l.format(format, v...)) } +// Println is alias of Print. // See Print. func (l *Logger) Println(v ...interface{}) { l.Print(v...) @@ -30,53 +31,53 @@ func (l *Logger) Println(v ...interface{}) { // Fatal prints the logging content with [FATA] header and newline, then exit the current process. func (l *Logger) Fatal(v ...interface{}) { - l.printErr("[FATA]", v...) + l.printErr(l.getLevelPrefixWithBrackets(LEVEL_FATA), v...) os.Exit(1) } // Fatalf prints the logging content with [FATA] header, custom format and newline, then exit the current process. func (l *Logger) Fatalf(format string, v ...interface{}) { - l.printErr("[FATA]", l.format(format, v...)) + l.printErr(l.getLevelPrefixWithBrackets(LEVEL_FATA), l.format(format, v...)) os.Exit(1) } // Panic prints the logging content with [PANI] header and newline, then panics. func (l *Logger) Panic(v ...interface{}) { - l.printErr("[PANI]", v...) + l.printErr(l.getLevelPrefixWithBrackets(LEVEL_PANI), v...) panic(fmt.Sprint(v...)) } // Panicf prints the logging content with [PANI] header, custom format and newline, then panics. func (l *Logger) Panicf(format string, v ...interface{}) { - l.printErr("[PANI]", l.format(format, v...)) + l.printErr(l.getLevelPrefixWithBrackets(LEVEL_PANI), l.format(format, v...)) panic(l.format(format, v...)) } // Info prints the logging content with [INFO] header and newline. func (l *Logger) Info(v ...interface{}) { if l.checkLevel(LEVEL_INFO) { - l.printStd("[INFO]", v...) + l.printStd(l.getLevelPrefixWithBrackets(LEVEL_INFO), v...) } } // Infof prints the logging content with [INFO] header, custom format and newline. func (l *Logger) Infof(format string, v ...interface{}) { if l.checkLevel(LEVEL_INFO) { - l.printStd("[INFO]", l.format(format, v...)) + l.printStd(l.getLevelPrefixWithBrackets(LEVEL_INFO), l.format(format, v...)) } } // Debug prints the logging content with [DEBU] header and newline. func (l *Logger) Debug(v ...interface{}) { if l.checkLevel(LEVEL_DEBU) { - l.printStd("[DEBU]", v...) + l.printStd(l.getLevelPrefixWithBrackets(LEVEL_DEBU), v...) } } // Debugf prints the logging content with [DEBU] header, custom format and newline. func (l *Logger) Debugf(format string, v ...interface{}) { if l.checkLevel(LEVEL_DEBU) { - l.printStd("[DEBU]", l.format(format, v...)) + l.printStd(l.getLevelPrefixWithBrackets(LEVEL_DEBU), l.format(format, v...)) } } @@ -84,7 +85,7 @@ func (l *Logger) Debugf(format string, v ...interface{}) { // It also prints caller stack info if stack feature is enabled. func (l *Logger) Notice(v ...interface{}) { if l.checkLevel(LEVEL_NOTI) { - l.printStd("[NOTI]", v...) + l.printStd(l.getLevelPrefixWithBrackets(LEVEL_NOTI), v...) } } @@ -92,7 +93,7 @@ func (l *Logger) Notice(v ...interface{}) { // It also prints caller stack info if stack feature is enabled. func (l *Logger) Noticef(format string, v ...interface{}) { if l.checkLevel(LEVEL_NOTI) { - l.printStd("[NOTI]", l.format(format, v...)) + l.printStd(l.getLevelPrefixWithBrackets(LEVEL_NOTI), l.format(format, v...)) } } @@ -100,7 +101,7 @@ func (l *Logger) Noticef(format string, v ...interface{}) { // It also prints caller stack info if stack feature is enabled. func (l *Logger) Warning(v ...interface{}) { if l.checkLevel(LEVEL_WARN) { - l.printStd("[WARN]", v...) + l.printStd(l.getLevelPrefixWithBrackets(LEVEL_WARN), v...) } } @@ -108,7 +109,7 @@ func (l *Logger) Warning(v ...interface{}) { // It also prints caller stack info if stack feature is enabled. func (l *Logger) Warningf(format string, v ...interface{}) { if l.checkLevel(LEVEL_WARN) { - l.printStd("[WARN]", l.format(format, v...)) + l.printStd(l.getLevelPrefixWithBrackets(LEVEL_WARN), l.format(format, v...)) } } @@ -116,7 +117,7 @@ func (l *Logger) Warningf(format string, v ...interface{}) { // It also prints caller stack info if stack feature is enabled. func (l *Logger) Error(v ...interface{}) { if l.checkLevel(LEVEL_ERRO) { - l.printErr("[ERRO]", v...) + l.printErr(l.getLevelPrefixWithBrackets(LEVEL_ERRO), v...) } } @@ -124,7 +125,7 @@ func (l *Logger) Error(v ...interface{}) { // It also prints caller stack info if stack feature is enabled. func (l *Logger) Errorf(format string, v ...interface{}) { if l.checkLevel(LEVEL_ERRO) { - l.printErr("[ERRO]", l.format(format, v...)) + l.printErr(l.getLevelPrefixWithBrackets(LEVEL_ERRO), l.format(format, v...)) } } @@ -132,7 +133,7 @@ func (l *Logger) Errorf(format string, v ...interface{}) { // It also prints caller stack info if stack feature is enabled. func (l *Logger) Critical(v ...interface{}) { if l.checkLevel(LEVEL_CRIT) { - l.printErr("[CRIT]", v...) + l.printErr(l.getLevelPrefixWithBrackets(LEVEL_CRIT), v...) } } @@ -140,7 +141,7 @@ func (l *Logger) Critical(v ...interface{}) { // It also prints caller stack info if stack feature is enabled. func (l *Logger) Criticalf(format string, v ...interface{}) { if l.checkLevel(LEVEL_CRIT) { - l.printErr("[CRIT]", l.format(format, v...)) + l.printErr(l.getLevelPrefixWithBrackets(LEVEL_CRIT), l.format(format, v...)) } } diff --git a/os/glog/glog_logger_chaining.go b/os/glog/glog_logger_chaining.go index 28cf93c68..c9be28480 100644 --- a/os/glog/glog_logger_chaining.go +++ b/os/glog/glog_logger_chaining.go @@ -27,6 +27,8 @@ func (l *Logger) To(writer io.Writer) *Logger { // Path is a chaining function, // which sets the directory path to for current logging content output. +// +// Note that the parameter is a directory path, not a file path. func (l *Logger) Path(path string) *Logger { logger := (*Logger)(nil) if l.parent == nil { diff --git a/os/glog/glog_logger_config.go b/os/glog/glog_logger_config.go index 1e387f225..c66836d9f 100644 --- a/os/glog/glog_logger_config.go +++ b/os/glog/glog_logger_config.go @@ -18,28 +18,33 @@ import ( // Config is the configuration object for logger. type Config struct { - Writer io.Writer // Customized io.Writer. - Flags int // Extra flags for logging output features. - Path string // Logging directory path. - File string // Format for logging file. - Level int // Output level. - Prefix string // Prefix string for every logging content. - StSkip int // Skip count for stack. - StStatus int // Stack status(1: enabled - default; 0: disabled) - StFilter string // Stack string filter. - HeaderPrint bool `c:"header"` // Print header or not(true in default). - StdoutPrint bool `c:"stdout"` // Output to stdout or not(true in default). + Writer io.Writer // Customized io.Writer. + Flags int // Extra flags for logging output features. + Path string // Logging directory path. + File string // Format for logging file. + Level int // Output level. + Prefix string // Prefix string for every logging content. + StSkip int // Skip count for stack. + StStatus int // Stack status(1: enabled - default; 0: disabled) + StFilter string // Stack string filter. + HeaderPrint bool `c:"header"` // Print header or not(true in default). + StdoutPrint bool `c:"stdout"` // Output to stdout or not(true in default). + LevelPrefixes map[int]string // Logging level to its prefix string mapping. } // DefaultConfig returns the default configuration for logger. func DefaultConfig() Config { c := Config{ - File: gDEFAULT_FILE_FORMAT, - Flags: F_TIME_STD, - Level: LEVEL_ALL, - StStatus: 1, - HeaderPrint: true, - StdoutPrint: true, + File: gDEFAULT_FILE_FORMAT, + Flags: F_TIME_STD, + Level: LEVEL_ALL, + StStatus: 1, + HeaderPrint: true, + StdoutPrint: true, + LevelPrefixes: make(map[int]string, len(defaultLevelPrefixes)), + } + for k, v := range defaultLevelPrefixes { + c.LevelPrefixes[k] = v } if !defaultDebug { c.Level = c.Level & ^LEVEL_DEBU diff --git a/os/glog/glog_logger_level.go b/os/glog/glog_logger_level.go new file mode 100644 index 000000000..48560ac40 --- /dev/null +++ b/os/glog/glog_logger_level.go @@ -0,0 +1,60 @@ +// Copyright 2019 gf Author(https://github.com/gogf/gf). All Rights Reserved. +// +// This Source Code Form is subject to the terms of the MIT License. +// If a copy of the MIT was not distributed with this file, +// You can obtain one at https://github.com/gogf/gf. + +package glog + +// Note that the LEVEL_PANI and LEVEL_FATA levels are not used for logging output, +// but for prefix configurations. +const ( + LEVEL_ALL = LEVEL_DEBU | LEVEL_INFO | LEVEL_NOTI | LEVEL_WARN | LEVEL_ERRO | LEVEL_CRIT + LEVEL_DEV = LEVEL_ALL + LEVEL_PROD = LEVEL_WARN | LEVEL_ERRO | LEVEL_CRIT + LEVEL_DEBU = 1 << iota // 8 + LEVEL_INFO // 16 + LEVEL_NOTI // 32 + LEVEL_WARN // 64 + LEVEL_ERRO // 128 + LEVEL_CRIT // 256 + LEVEL_PANI // 512 + LEVEL_FATA // 1024 +) + +// defaultLevelPrefixes defines the default level and its mapping prefix string. +var defaultLevelPrefixes = map[int]string{ + LEVEL_DEBU: "DEBU", + LEVEL_INFO: "INFO", + LEVEL_NOTI: "NOTI", + LEVEL_WARN: "WARN", + LEVEL_ERRO: "ERRO", + LEVEL_CRIT: "CRIT", + LEVEL_PANI: "PANI", + LEVEL_FATA: "FATA", +} + +// SetLevelPrefix sets the prefix string for specified level. +func (l *Logger) SetLevelPrefix(level int, prefix string) { + l.config.LevelPrefixes[level] = prefix +} + +// SetLevelPrefixes sets the level to prefix string mapping for the logger. +func (l *Logger) SetLevelPrefixes(prefixes map[int]string) { + for k, v := range prefixes { + l.config.LevelPrefixes[k] = v + } +} + +// GetLevelPrefix returns the prefix string for specified level. +func (l *Logger) GetLevelPrefix(level int) string { + return l.config.LevelPrefixes[level] +} + +// getLevelPrefixWithBrackets returns the prefix string with brackets for specified level. +func (l *Logger) getLevelPrefixWithBrackets(level int) string { + if s, ok := l.config.LevelPrefixes[level]; ok { + return "[" + s + "]" + } + return "" +} diff --git a/os/glog/glog_z_unit_basic_test.go b/os/glog/glog_z_unit_basic_test.go new file mode 100644 index 000000000..ec26c1cfc --- /dev/null +++ b/os/glog/glog_z_unit_basic_test.go @@ -0,0 +1,81 @@ +// Copyright 2017 gf Author(https://github.com/gogf/gf). All Rights Reserved. +// +// This Source Code Form is subject to the terms of the MIT License. +// If a copy of the MIT was not distributed with this file, +// You can obtain one at https://github.com/gogf/gf. + +package glog + +import ( + "bytes" + "github.com/gogf/gf/test/gtest" + "github.com/gogf/gf/text/gstr" + "testing" +) + +func Test_Print(t *testing.T) { + gtest.Case(t, func() { + w := bytes.NewBuffer(nil) + l := NewWithWriter(w) + l.Print(1, 2, 3) + l.Println(1, 2, 3) + l.Printf("%d %d %d", 1, 2, 3) + gtest.Assert(gstr.Count(w.String(), "["), 0) + gtest.Assert(gstr.Count(w.String(), "1 2 3"), 3) + }) +} + +func Test_Debug(t *testing.T) { + gtest.Case(t, func() { + w := bytes.NewBuffer(nil) + l := NewWithWriter(w) + l.Debug(1, 2, 3) + l.Debugf("%d %d %d", 1, 2, 3) + gtest.Assert(gstr.Count(w.String(), defaultLevelPrefixes[LEVEL_DEBU]), 2) + gtest.Assert(gstr.Count(w.String(), "1 2 3"), 2) + }) +} + +func Test_Info(t *testing.T) { + gtest.Case(t, func() { + w := bytes.NewBuffer(nil) + l := NewWithWriter(w) + l.Info(1, 2, 3) + l.Infof("%d %d %d", 1, 2, 3) + gtest.Assert(gstr.Count(w.String(), defaultLevelPrefixes[LEVEL_INFO]), 2) + gtest.Assert(gstr.Count(w.String(), "1 2 3"), 2) + }) +} + +func Test_Notice(t *testing.T) { + gtest.Case(t, func() { + w := bytes.NewBuffer(nil) + l := NewWithWriter(w) + l.Notice(1, 2, 3) + l.Noticef("%d %d %d", 1, 2, 3) + gtest.Assert(gstr.Count(w.String(), defaultLevelPrefixes[LEVEL_NOTI]), 2) + gtest.Assert(gstr.Count(w.String(), "1 2 3"), 2) + }) +} + +func Test_Warning(t *testing.T) { + gtest.Case(t, func() { + w := bytes.NewBuffer(nil) + l := NewWithWriter(w) + l.Warning(1, 2, 3) + l.Warningf("%d %d %d", 1, 2, 3) + gtest.Assert(gstr.Count(w.String(), defaultLevelPrefixes[LEVEL_WARN]), 2) + gtest.Assert(gstr.Count(w.String(), "1 2 3"), 2) + }) +} + +func Test_Error(t *testing.T) { + gtest.Case(t, func() { + w := bytes.NewBuffer(nil) + l := NewWithWriter(w) + l.Error(1, 2, 3) + l.Errorf("%d %d %d", 1, 2, 3) + gtest.Assert(gstr.Count(w.String(), defaultLevelPrefixes[LEVEL_ERRO]), 2) + gtest.Assert(gstr.Count(w.String(), "1 2 3"), 2) + }) +} diff --git a/os/glog/glog_z_unit_chaining_test.go b/os/glog/glog_z_unit_chaining_test.go new file mode 100644 index 000000000..827f44fbb --- /dev/null +++ b/os/glog/glog_z_unit_chaining_test.go @@ -0,0 +1,243 @@ +// Copyright 2017 gf Author(https://github.com/gogf/gf). All Rights Reserved. +// +// This Source Code Form is subject to the terms of the MIT License. +// If a copy of the MIT was not distributed with this file, +// You can obtain one at https://github.com/gogf/gf. + +package glog + +import ( + "bytes" + "fmt" + "github.com/gogf/gf/os/gfile" + "github.com/gogf/gf/os/gtime" + "github.com/gogf/gf/test/gtest" + "github.com/gogf/gf/text/gstr" + "testing" + "time" +) + +func Test_To(t *testing.T) { + gtest.Case(t, func() { + w := bytes.NewBuffer(nil) + To(w).Error(1, 2, 3) + To(w).Errorf("%d %d %d", 1, 2, 3) + gtest.Assert(gstr.Count(w.String(), defaultLevelPrefixes[LEVEL_ERRO]), 2) + gtest.Assert(gstr.Count(w.String(), "1 2 3"), 2) + }) +} + +func Test_Path(t *testing.T) { + gtest.Case(t, func() { + path := gfile.Join(gfile.TempDir(), gtime.TimestampNanoStr()) + file := fmt.Sprintf(`%d.log`, gtime.TimestampNano()) + + err := gfile.Mkdir(path) + gtest.Assert(err, nil) + defer gfile.Remove(path) + + Path(path).File(file).Stdout(false).Error(1, 2, 3) + Path(path).File(file).Stdout(false).Errorf("%d %d %d", 1, 2, 3) + content := gfile.GetContents(gfile.Join(path, file)) + gtest.Assert(gstr.Count(content, defaultLevelPrefixes[LEVEL_ERRO]), 2) + gtest.Assert(gstr.Count(content, "1 2 3"), 2) + }) +} + +func Test_Cat(t *testing.T) { + gtest.Case(t, func() { + cat := "category" + path := gfile.Join(gfile.TempDir(), gtime.TimestampNanoStr()) + file := fmt.Sprintf(`%d.log`, gtime.TimestampNano()) + + err := gfile.Mkdir(path) + gtest.Assert(err, nil) + defer gfile.Remove(path) + + Path(path).File(file).Cat(cat).Stdout(false).Error(1, 2, 3) + Path(path).File(file).Cat(cat).Stdout(false).Errorf("%d %d %d", 1, 2, 3) + content := gfile.GetContents(gfile.Join(path, cat, file)) + gtest.Assert(gstr.Count(content, defaultLevelPrefixes[LEVEL_ERRO]), 2) + gtest.Assert(gstr.Count(content, "1 2 3"), 2) + }) +} + +func Test_Level(t *testing.T) { + gtest.Case(t, func() { + path := gfile.Join(gfile.TempDir(), gtime.TimestampNanoStr()) + file := fmt.Sprintf(`%d.log`, gtime.TimestampNano()) + + err := gfile.Mkdir(path) + gtest.Assert(err, nil) + defer gfile.Remove(path) + + Path(path).File(file).Level(LEVEL_PROD).Stdout(false).Debug(1, 2, 3) + Path(path).File(file).Level(LEVEL_PROD).Stdout(false).Debug("%d %d %d", 1, 2, 3) + content := gfile.GetContents(gfile.Join(path, file)) + gtest.Assert(gstr.Count(content, defaultLevelPrefixes[LEVEL_DEBU]), 0) + gtest.Assert(gstr.Count(content, "1 2 3"), 0) + }) +} + +func Test_Skip(t *testing.T) { + gtest.Case(t, func() { + path := gfile.Join(gfile.TempDir(), gtime.TimestampNanoStr()) + file := fmt.Sprintf(`%d.log`, gtime.TimestampNano()) + + err := gfile.Mkdir(path) + gtest.Assert(err, nil) + defer gfile.Remove(path) + + Path(path).File(file).Skip(10).Stdout(false).Error(1, 2, 3) + Path(path).File(file).Stdout(false).Errorf("%d %d %d", 1, 2, 3) + content := gfile.GetContents(gfile.Join(path, file)) + gtest.Assert(gstr.Count(content, defaultLevelPrefixes[LEVEL_ERRO]), 2) + gtest.Assert(gstr.Count(content, "1 2 3"), 2) + gtest.Assert(gstr.Count(content, "Stack"), 1) + }) +} + +func Test_Stack(t *testing.T) { + gtest.Case(t, func() { + path := gfile.Join(gfile.TempDir(), gtime.TimestampNanoStr()) + file := fmt.Sprintf(`%d.log`, gtime.TimestampNano()) + + err := gfile.Mkdir(path) + gtest.Assert(err, nil) + defer gfile.Remove(path) + + Path(path).File(file).Stack(false).Stdout(false).Error(1, 2, 3) + Path(path).File(file).Stdout(false).Errorf("%d %d %d", 1, 2, 3) + content := gfile.GetContents(gfile.Join(path, file)) + gtest.Assert(gstr.Count(content, defaultLevelPrefixes[LEVEL_ERRO]), 2) + gtest.Assert(gstr.Count(content, "1 2 3"), 2) + gtest.Assert(gstr.Count(content, "Stack"), 1) + }) +} + +func Test_StackWithFilter(t *testing.T) { + gtest.Case(t, func() { + path := gfile.Join(gfile.TempDir(), gtime.TimestampNanoStr()) + file := fmt.Sprintf(`%d.log`, gtime.TimestampNano()) + + err := gfile.Mkdir(path) + gtest.Assert(err, nil) + defer gfile.Remove(path) + + Path(path).File(file).StackWithFilter("none").Stdout(false).Error(1, 2, 3) + content := gfile.GetContents(gfile.Join(path, file)) + gtest.Assert(gstr.Count(content, defaultLevelPrefixes[LEVEL_ERRO]), 1) + gtest.Assert(gstr.Count(content, "1 2 3"), 1) + gtest.Assert(gstr.Count(content, "Stack"), 1) + }) + gtest.Case(t, func() { + path := gfile.Join(gfile.TempDir(), gtime.TimestampNanoStr()) + file := fmt.Sprintf(`%d.log`, gtime.TimestampNano()) + + err := gfile.Mkdir(path) + gtest.Assert(err, nil) + defer gfile.Remove(path) + + Path(path).File(file).StackWithFilter("gogf").Stdout(false).Error(1, 2, 3) + content := gfile.GetContents(gfile.Join(path, file)) + gtest.Assert(gstr.Count(content, defaultLevelPrefixes[LEVEL_ERRO]), 1) + gtest.Assert(gstr.Count(content, "1 2 3"), 1) + gtest.Assert(gstr.Count(content, "Stack"), 0) + }) +} + +func Test_Header(t *testing.T) { + gtest.Case(t, func() { + path := gfile.Join(gfile.TempDir(), gtime.TimestampNanoStr()) + file := fmt.Sprintf(`%d.log`, gtime.TimestampNano()) + + err := gfile.Mkdir(path) + gtest.Assert(err, nil) + defer gfile.Remove(path) + + Path(path).File(file).Header(true).Stdout(false).Error(1, 2, 3) + content := gfile.GetContents(gfile.Join(path, file)) + gtest.Assert(gstr.Count(content, defaultLevelPrefixes[LEVEL_ERRO]), 1) + gtest.Assert(gstr.Count(content, "1 2 3"), 1) + }) + gtest.Case(t, func() { + path := gfile.Join(gfile.TempDir(), gtime.TimestampNanoStr()) + file := fmt.Sprintf(`%d.log`, gtime.TimestampNano()) + + err := gfile.Mkdir(path) + gtest.Assert(err, nil) + defer gfile.Remove(path) + + Path(path).File(file).Header(false).Stdout(false).Error(1, 2, 3) + content := gfile.GetContents(gfile.Join(path, file)) + gtest.Assert(gstr.Count(content, defaultLevelPrefixes[LEVEL_ERRO]), 0) + gtest.Assert(gstr.Count(content, "1 2 3"), 1) + }) +} + +func Test_Line(t *testing.T) { + gtest.Case(t, func() { + path := gfile.Join(gfile.TempDir(), gtime.TimestampNanoStr()) + file := fmt.Sprintf(`%d.log`, gtime.TimestampNano()) + + err := gfile.Mkdir(path) + gtest.Assert(err, nil) + defer gfile.Remove(path) + + Path(path).File(file).Line(true).Stdout(false).Debug(1, 2, 3) + content := gfile.GetContents(gfile.Join(path, file)) + gtest.Assert(gstr.Count(content, defaultLevelPrefixes[LEVEL_DEBU]), 1) + gtest.Assert(gstr.Count(content, "1 2 3"), 1) + gtest.Assert(gstr.Count(content, ".go"), 1) + gtest.Assert(gstr.Contains(content, gfile.Separator), true) + }) + gtest.Case(t, func() { + path := gfile.Join(gfile.TempDir(), gtime.TimestampNanoStr()) + file := fmt.Sprintf(`%d.log`, gtime.TimestampNano()) + + err := gfile.Mkdir(path) + gtest.Assert(err, nil) + defer gfile.Remove(path) + + Path(path).File(file).Line(false).Stdout(false).Debug(1, 2, 3) + content := gfile.GetContents(gfile.Join(path, file)) + gtest.Assert(gstr.Count(content, defaultLevelPrefixes[LEVEL_DEBU]), 1) + gtest.Assert(gstr.Count(content, "1 2 3"), 1) + gtest.Assert(gstr.Count(content, ".go"), 1) + gtest.Assert(gstr.Contains(content, gfile.Separator), false) + }) +} + +func Test_Async(t *testing.T) { + gtest.Case(t, func() { + path := gfile.Join(gfile.TempDir(), gtime.TimestampNanoStr()) + file := fmt.Sprintf(`%d.log`, gtime.TimestampNano()) + + err := gfile.Mkdir(path) + gtest.Assert(err, nil) + defer gfile.Remove(path) + + Path(path).File(file).Async().Stdout(false).Debug(1, 2, 3) + content := gfile.GetContents(gfile.Join(path, file)) + gtest.Assert(content, "") + time.Sleep(200 * time.Millisecond) + + content = gfile.GetContents(gfile.Join(path, file)) + gtest.Assert(gstr.Count(content, defaultLevelPrefixes[LEVEL_DEBU]), 1) + gtest.Assert(gstr.Count(content, "1 2 3"), 1) + }) + + gtest.Case(t, func() { + path := gfile.Join(gfile.TempDir(), gtime.TimestampNanoStr()) + file := fmt.Sprintf(`%d.log`, gtime.TimestampNano()) + + err := gfile.Mkdir(path) + gtest.Assert(err, nil) + defer gfile.Remove(path) + + Path(path).File(file).Async(false).Stdout(false).Debug(1, 2, 3) + content := gfile.GetContents(gfile.Join(path, file)) + gtest.Assert(gstr.Count(content, defaultLevelPrefixes[LEVEL_DEBU]), 1) + gtest.Assert(gstr.Count(content, "1 2 3"), 1) + }) +} diff --git a/os/glog/glog_z_unit_test.go b/os/glog/glog_z_unit_config_test.go similarity index 100% rename from os/glog/glog_z_unit_test.go rename to os/glog/glog_z_unit_config_test.go diff --git a/os/glog/glog_z_unit_level_test.go b/os/glog/glog_z_unit_level_test.go new file mode 100644 index 000000000..388950519 --- /dev/null +++ b/os/glog/glog_z_unit_level_test.go @@ -0,0 +1,59 @@ +// Copyright 2017 gf Author(https://github.com/gogf/gf). All Rights Reserved. +// +// This Source Code Form is subject to the terms of the MIT License. +// If a copy of the MIT was not distributed with this file, +// You can obtain one at https://github.com/gogf/gf. + +package glog + +import ( + "bytes" + "github.com/gogf/gf/test/gtest" + "github.com/gogf/gf/text/gstr" + "testing" +) + +func Test_LevelPrefix(t *testing.T) { + gtest.Case(t, func() { + l := New() + gtest.Assert(l.GetLevelPrefix(LEVEL_DEBU), defaultLevelPrefixes[LEVEL_DEBU]) + gtest.Assert(l.GetLevelPrefix(LEVEL_INFO), defaultLevelPrefixes[LEVEL_INFO]) + gtest.Assert(l.GetLevelPrefix(LEVEL_NOTI), defaultLevelPrefixes[LEVEL_NOTI]) + gtest.Assert(l.GetLevelPrefix(LEVEL_WARN), defaultLevelPrefixes[LEVEL_WARN]) + gtest.Assert(l.GetLevelPrefix(LEVEL_ERRO), defaultLevelPrefixes[LEVEL_ERRO]) + gtest.Assert(l.GetLevelPrefix(LEVEL_CRIT), defaultLevelPrefixes[LEVEL_CRIT]) + l.SetLevelPrefix(LEVEL_DEBU, "debug") + gtest.Assert(l.GetLevelPrefix(LEVEL_DEBU), "debug") + l.SetLevelPrefixes(map[int]string{ + LEVEL_CRIT: "critical", + }) + gtest.Assert(l.GetLevelPrefix(LEVEL_DEBU), "debug") + gtest.Assert(l.GetLevelPrefix(LEVEL_INFO), defaultLevelPrefixes[LEVEL_INFO]) + gtest.Assert(l.GetLevelPrefix(LEVEL_NOTI), defaultLevelPrefixes[LEVEL_NOTI]) + gtest.Assert(l.GetLevelPrefix(LEVEL_WARN), defaultLevelPrefixes[LEVEL_WARN]) + gtest.Assert(l.GetLevelPrefix(LEVEL_ERRO), defaultLevelPrefixes[LEVEL_ERRO]) + gtest.Assert(l.GetLevelPrefix(LEVEL_CRIT), "critical") + }) + gtest.Case(t, func() { + buffer := bytes.NewBuffer(nil) + l := New() + l.SetWriter(buffer) + l.Debug("test1") + gtest.Assert(gstr.Contains(buffer.String(), defaultLevelPrefixes[LEVEL_DEBU]), true) + + buffer.Reset() + + l.SetLevelPrefix(LEVEL_DEBU, "debug") + l.Debug("test2") + gtest.Assert(gstr.Contains(buffer.String(), defaultLevelPrefixes[LEVEL_DEBU]), false) + gtest.Assert(gstr.Contains(buffer.String(), "debug"), true) + + buffer.Reset() + l.SetLevelPrefixes(map[int]string{ + LEVEL_ERRO: "error", + }) + l.Error("test3") + gtest.Assert(gstr.Contains(buffer.String(), defaultLevelPrefixes[LEVEL_ERRO]), false) + gtest.Assert(gstr.Contains(buffer.String(), "error"), true) + }) +}