|
|
@ -78,6 +78,10 @@ func New(e error) *Error { |
|
|
|
// Trace records the point at which it is invoked. Stack traces are important for
|
|
|
|
// Trace records the point at which it is invoked. Stack traces are important for
|
|
|
|
// debugging purposes.
|
|
|
|
// debugging purposes.
|
|
|
|
func (e *Error) Trace(fields ...string) *Error { |
|
|
|
func (e *Error) Trace(fields ...string) *Error { |
|
|
|
|
|
|
|
if e == nil { |
|
|
|
|
|
|
|
return nil |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
e.lock.Lock() |
|
|
|
e.lock.Lock() |
|
|
|
defer e.lock.Unlock() |
|
|
|
defer e.lock.Unlock() |
|
|
|
|
|
|
|
|
|
|
@ -103,6 +107,9 @@ func (e *Error) trace(fields ...string) *Error { |
|
|
|
|
|
|
|
|
|
|
|
// Untrace erases last trace entry.
|
|
|
|
// Untrace erases last trace entry.
|
|
|
|
func (e *Error) Untrace() { |
|
|
|
func (e *Error) Untrace() { |
|
|
|
|
|
|
|
if e == nil { |
|
|
|
|
|
|
|
return |
|
|
|
|
|
|
|
} |
|
|
|
e.lock.Lock() |
|
|
|
e.lock.Lock() |
|
|
|
defer e.lock.Unlock() |
|
|
|
defer e.lock.Unlock() |
|
|
|
|
|
|
|
|
|
|
@ -116,35 +123,48 @@ func (e *Error) Untrace() { |
|
|
|
|
|
|
|
|
|
|
|
// Error returns error string.
|
|
|
|
// Error returns error string.
|
|
|
|
func (e *Error) Error() string { |
|
|
|
func (e *Error) Error() string { |
|
|
|
|
|
|
|
if e == nil { |
|
|
|
|
|
|
|
return "<nil>" |
|
|
|
|
|
|
|
} |
|
|
|
return e.String() |
|
|
|
return e.String() |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
// String returns error message.
|
|
|
|
// String returns error message.
|
|
|
|
func (e *Error) String() string { |
|
|
|
func (e *Error) String() string { |
|
|
|
|
|
|
|
if e == nil { |
|
|
|
|
|
|
|
return "<nil>" |
|
|
|
|
|
|
|
} |
|
|
|
e.lock.RLock() |
|
|
|
e.lock.RLock() |
|
|
|
defer e.lock.RUnlock() |
|
|
|
defer e.lock.RUnlock() |
|
|
|
|
|
|
|
|
|
|
|
trace := e.e.Error() + "\n" |
|
|
|
if e.e != nil { |
|
|
|
for i, tp := range e.tracePoints { |
|
|
|
trace := e.e.Error() + "\n" |
|
|
|
if len(tp.Env) > 0 { |
|
|
|
for i, tp := range e.tracePoints { |
|
|
|
trace += fmt.Sprintf(" (%d) %s:%d %s(..) Tags: [%s]\n", i, tp.Filename, tp.Line, tp.Function, strings.Join(tp.Env["Tags"], ", ")) |
|
|
|
if len(tp.Env) > 0 { |
|
|
|
} else { |
|
|
|
trace += fmt.Sprintf(" (%d) %s:%d %s(..) Tags: [%s]\n", i, tp.Filename, tp.Line, tp.Function, strings.Join(tp.Env["Tags"], ", ")) |
|
|
|
trace += fmt.Sprintf(" (%d) %s:%d %s(..)\n", i, tp.Filename, tp.Line, tp.Function) |
|
|
|
} else { |
|
|
|
|
|
|
|
trace += fmt.Sprintf(" (%d) %s:%d %s(..)\n", i, tp.Filename, tp.Line, tp.Function) |
|
|
|
|
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
trace += " Host:" + e.sysInfo["host.name"] + " | " |
|
|
|
trace += " Host:" + e.sysInfo["host.name"] + " | " |
|
|
|
trace += "OS:" + e.sysInfo["host.os"] + " | " |
|
|
|
trace += "OS:" + e.sysInfo["host.os"] + " | " |
|
|
|
trace += "Arch:" + e.sysInfo["host.arch"] + " | " |
|
|
|
trace += "Arch:" + e.sysInfo["host.arch"] + " | " |
|
|
|
trace += "Lang:" + e.sysInfo["host.lang"] + " | " |
|
|
|
trace += "Lang:" + e.sysInfo["host.lang"] + " | " |
|
|
|
trace += "Mem:" + e.sysInfo["mem.used"] + "/" + e.sysInfo["mem.total"] + " | " |
|
|
|
trace += "Mem:" + e.sysInfo["mem.used"] + "/" + e.sysInfo["mem.total"] + " | " |
|
|
|
trace += "Heap:" + e.sysInfo["mem.heap.used"] + "/" + e.sysInfo["mem.heap.total"] |
|
|
|
trace += "Heap:" + e.sysInfo["mem.heap.used"] + "/" + e.sysInfo["mem.heap.total"] |
|
|
|
|
|
|
|
|
|
|
|
return trace |
|
|
|
return trace |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
return "<nil>" |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
// JSON returns JSON formated error trace.
|
|
|
|
// JSON returns JSON formated error trace.
|
|
|
|
func (e *Error) JSON() string { |
|
|
|
func (e *Error) JSON() string { |
|
|
|
|
|
|
|
if e == nil { |
|
|
|
|
|
|
|
return "<nil>" |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
e.lock.RLock() |
|
|
|
e.lock.RLock() |
|
|
|
defer e.lock.RUnlock() |
|
|
|
defer e.lock.RUnlock() |
|
|
|
|
|
|
|
|
|
|
|