Better debug logging + unit tests

This commit is contained in:
Manu Mtz-Almeida 2015-05-09 03:34:43 +02:00
parent c391520654
commit b690611c38
5 changed files with 99 additions and 16 deletions

View File

@ -15,7 +15,7 @@ func IsDebugging() bool {
return ginMode == debugCode
}
func debugRoute(httpMethod, absolutePath string, handlers HandlersChain) {
func debugPrintRoute(httpMethod, absolutePath string, handlers HandlersChain) {
if IsDebugging() {
nuHandlers := len(handlers)
handlerName := nameOfFunction(handlers[nuHandlers-1])
@ -28,3 +28,13 @@ func debugPrint(format string, values ...interface{}) {
debugLogger.Printf(format, values...)
}
}
func debugPrintWARNING() {
debugPrint("[WARNING] Running in DEBUG mode! Disable it before going production\n")
}
func debugPrintError(err error) {
if err != nil {
debugPrint("[ERROR] %v\n", err)
}
}

View File

@ -5,11 +5,17 @@
package gin
import (
"bytes"
"errors"
"io"
"log"
"testing"
"github.com/stretchr/testify/assert"
)
var cachedDebugLogger *log.Logger = nil
// TODO
// func debugRoute(httpMethod, absolutePath string, handlers HandlersChain) {
// func debugPrint(format string, values ...interface{}) {
@ -22,3 +28,52 @@ func TestIsDebugging(t *testing.T) {
SetMode(TestMode)
assert.False(t, IsDebugging())
}
func TestDebugPrint(t *testing.T) {
var w bytes.Buffer
setup(&w)
defer teardown()
SetMode(ReleaseMode)
debugPrint("DEBUG this!")
SetMode(TestMode)
debugPrint("DEBUG this!")
assert.Empty(t, w.String())
SetMode(DebugMode)
debugPrint("these are %d %s\n", 2, "error messages")
assert.Equal(t, w.String(), "[GIN-debug] these are 2 error messages\n")
}
func TestDebugPrintError(t *testing.T) {
var w bytes.Buffer
setup(&w)
defer teardown()
SetMode(DebugMode)
debugPrintError(nil)
assert.Empty(t, w.String())
debugPrintError(errors.New("this is an error"))
assert.Equal(t, w.String(), "[GIN-debug] [ERROR] this is an error\n")
}
func setup(w io.Writer) {
SetMode(DebugMode)
if cachedDebugLogger == nil {
cachedDebugLogger = debugLogger
debugLogger = log.New(w, debugLogger.Prefix(), 0)
} else {
panic("setup failed")
}
}
func teardown() {
SetMode(TestMode)
if cachedDebugLogger != nil {
debugLogger = cachedDebugLogger
cachedDebugLogger = nil
} else {
panic("teardown failed")
}
}

View File

@ -10,16 +10,19 @@ import (
)
const (
ErrorTypeInternal = 1 << iota
ErrorTypeExternal = 1 << iota
ErrorTypeAll = 0xffffffff
ErrorTypePrivate = 1 << iota
ErrorTypePublic = 1 << iota
)
const (
ErrorMaskAny = 0xffffffff
)
// Used internally to collect errors that occurred during an http request.
type errorMsg struct {
Err string `json:"error"`
Type int `json:"-"`
Meta interface{} `json:"meta"`
Error error `json:"error"`
Type int `json:"-"`
Meta interface{} `json:"meta"`
}
type errorMsgs []errorMsg
@ -37,14 +40,24 @@ func (a errorMsgs) ByType(typ int) errorMsgs {
return result
}
func (a errorMsgs) Errors() []string {
if len(a) == 0 {
return []string{}
}
errors := make([]string, len(a))
for i, err := range a {
errors[i] = err.Error.Error()
}
return errors
}
func (a errorMsgs) String() string {
if len(a) == 0 {
return ""
}
var buffer bytes.Buffer
for i, msg := range a {
text := fmt.Sprintf("Error #%02d: %s\n Meta: %v\n", (i + 1), msg.Err, msg.Meta)
buffer.WriteString(text)
fmt.Fprintf(&buffer, "Error #%02d: %s\n Meta: %v\n", (i + 1), msg.Error, msg.Meta)
}
return buffer.String()
}

17
gin.go
View File

@ -62,6 +62,7 @@ type (
// Returns a new blank Engine instance without any middleware attached.
// The most basic configuration
func New() *Engine {
debugPrintWARNING()
engine := &Engine{
RouterGroup: RouterGroup{
Handlers: nil,
@ -156,16 +157,20 @@ func (engine *Engine) handle(method, path string, handlers HandlersChain) {
root.addRoute(path, handlers)
}
func (engine *Engine) Run(addr string) error {
debugPrint("[WARNING] Running in DEBUG mode! Disable it before going production")
func (engine *Engine) Run(addr string) (err error) {
debugPrint("Listening and serving HTTP on %s\n", addr)
return http.ListenAndServe(addr, engine)
defer debugPrintError(err)
err = http.ListenAndServe(addr, engine)
return
}
func (engine *Engine) RunTLS(addr string, cert string, key string) error {
debugPrint("[WARNING] Running in DEBUG mode! Disable it before going production")
func (engine *Engine) RunTLS(addr string, cert string, key string) (err error) {
debugPrint("Listening and serving HTTPS on %s\n", addr)
return http.ListenAndServeTLS(addr, cert, key, engine)
defer debugPrintError(err)
err = http.ListenAndServe(addr, engine)
return
}
// ServeHTTP makes the router implement the http.Handler interface.

View File

@ -45,7 +45,7 @@ func (group *RouterGroup) Group(relativePath string, handlers ...HandlerFunc) *R
func (group *RouterGroup) Handle(httpMethod, relativePath string, handlers HandlersChain) {
absolutePath := group.calculateAbsolutePath(relativePath)
handlers = group.combineHandlers(handlers)
debugRoute(httpMethod, absolutePath, handlers)
debugPrintRoute(httpMethod, absolutePath, handlers)
group.engine.handle(httpMethod, absolutePath, handlers)
}