exception/exception.go
2025-08-11 23:05:16 +02:00

77 lines
1.4 KiB
Go

package exception
import (
"bytes"
"fmt"
"os"
"reflect"
"strings"
)
type Custom interface {
error
At(source any) Custom
With(innerErr ...error) Custom
IsSameAs(err error) bool
}
func NewCustom(message string, innerErr ...error) Custom {
return &custom{
message: message,
innerErrors: innerErr,
}
}
type custom struct {
message string
innerErrors []error
}
func (ex *custom) With(innerErr ...error) Custom {
ex.innerErrors = append(ex.innerErrors, innerErr...)
return ex
}
func (ex *custom) At(source any) Custom {
if source != nil {
ex.message = fmt.Sprintf("%s in %s", ex.message, getType(source))
}
return ex
}
func (ex *custom) IsSameAs(err error) bool {
if err == nil {
return false
}
return strings.HasPrefix(err.Error(), fmt.Sprintf("[%s]:", ex.message))
}
func (ex *custom) Error() string {
buf := bytes.NewBufferString("")
if len(ex.innerErrors) > 0 {
for _, innerE := range ex.innerErrors {
buf.WriteString(getOsNewLine())
buf.WriteString(innerE.Error())
}
}
return fmt.Sprintf("[%s]:%s", ex.message, buf.String())
}
func getOsNewLine() string {
if fmt.Sprintf("%v", os.PathSeparator) != "/" {
return "\n"
}
return "\r\n"
}
func getType[T any](source T) string {
typeName := ""
typeOf := reflect.TypeOf(source)
if typeOf != nil {
typeName = typeOf.String()
} else {
typeName = reflect.TypeOf((*T)(nil)).Elem().String()
}
return typeName
}