Skip to content

Commit 4f4816e

Browse files
committed
add advanced info about source and dest types to errors
Signed-off-by: Dmitrii Aleksandrov <goodmobiledevices@gmail.com>
1 parent b932123 commit 4f4816e

2 files changed

Lines changed: 37 additions & 15 deletions

File tree

mapper.go

Lines changed: 35 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -5,15 +5,14 @@ import (
55
"reflect"
66
)
77

8-
const RouteNotFoundError = "route does not exist in route map"
9-
108
func validateSource(source any) error {
11-
sValueOf := reflect.ValueOf(source)
12-
if source == nil || (sValueOf.Kind() == reflect.Ptr && sValueOf.IsNil()) {
13-
return fmt.Errorf("source value cant't be nil")
9+
sourceTypeName := getTypeName(source)
10+
if source == nil {
11+
return fmt.Errorf("source value can't be nil, source type: %s", sourceTypeName)
1412
}
15-
if sValueOf.Kind() == reflect.Ptr && sValueOf.Elem().Kind() == reflect.Ptr {
16-
return fmt.Errorf("source can have a pointer type, but not a pointer to pointer")
13+
typeOf := reflect.TypeOf(source)
14+
if typeOf.Kind() == reflect.Ptr && typeOf.Elem().Kind() == reflect.Ptr {
15+
return fmt.Errorf("source can have a pointer type, but not a pointer to pointer, source type: %s", sourceTypeName)
1716
}
1817
return nil
1918
}
@@ -27,16 +26,37 @@ func prepareSource(source any) any {
2726
return sourceToMap
2827
}
2928

29+
func getTypeNameRecursive(target reflect.Type, typeName string) string {
30+
if target.Kind() == reflect.Ptr || target.Kind() == reflect.Slice {
31+
newTarget := target.Elem()
32+
newTypeName := "*" + typeName
33+
if target.Kind() == reflect.Slice {
34+
newTypeName = "[]" + typeName
35+
}
36+
return getTypeNameRecursive(newTarget, newTypeName)
37+
}
38+
return fmt.Sprintf("%s%s.%s", typeName, target.PkgPath(), target.Name())
39+
}
40+
41+
func getTypeName(target any) string {
42+
tt := reflect.TypeOf(target)
43+
if target != nil || tt != nil {
44+
return getTypeNameRecursive(tt, "")
45+
}
46+
return "undefined"
47+
}
48+
3049
func validateDest(dest any) error {
3150
dValueOf := reflect.ValueOf(dest)
51+
dTypeName := getTypeName(dest)
3252
if dValueOf.Kind() != reflect.Ptr {
33-
return fmt.Errorf("destenation value should have a pointer type")
53+
return fmt.Errorf("destenation value should have a pointer type, but has %s type", dTypeName)
3454
}
3555
if dest == nil || dValueOf.IsNil() {
36-
return fmt.Errorf("destenation value can't be nil")
56+
return fmt.Errorf("destenation value can't be nil, destenation type: %s", dTypeName)
3757
}
38-
if dValueOf.Elem().Kind() == reflect.Ptr {
39-
return fmt.Errorf("destenation value should have a pointer type, not a pointer to pointer")
58+
if dValueOf.Kind() == reflect.Ptr && dValueOf.Elem().Kind() == reflect.Ptr {
59+
return fmt.Errorf("destenation value should have a pointer type, not a pointer to pointer, but has %s type", dTypeName)
4060
}
4161
return nil
4262
}
@@ -54,11 +74,13 @@ func Map(source interface{}, dest interface{}) error {
5474
}
5575
route, ok := routes[reflect.TypeOf(sourceForMap)]
5676
if !ok {
57-
return fmt.Errorf(RouteNotFoundError)
77+
return fmt.Errorf("route not found for type %s to type %s",
78+
getTypeName(sourceForMap), getTypeName(dest))
5879
}
5980
mapFunc, ok := route[reflect.TypeOf(dest)]
6081
if !ok {
61-
return fmt.Errorf(RouteNotFoundError)
82+
return fmt.Errorf("route not found for type %s to type %s",
83+
getTypeName(sourceForMap), getTypeName(dest))
6284
}
6385
return mapFunc(sourceForMap, dest)
6486
}

routes.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -63,11 +63,11 @@ func AddRoute[TSource, TDest any | []any](mapFunc func(source TSource, dest *TDe
6363
dest := *new(TDest)
6464
destValueOf := reflect.ValueOf(dest)
6565
if destValueOf.Kind() == reflect.Ptr {
66-
return fmt.Errorf("destination type can't be reference type")
66+
return fmt.Errorf("destination type can't be reference type, route: %s -> %s", getTypeName(source), getTypeName(dest))
6767
}
6868
sourceValueOf := reflect.ValueOf(source)
6969
if sourceValueOf.Kind() == reflect.Ptr {
70-
return fmt.Errorf("source type can't be reference type")
70+
return fmt.Errorf("source type can't be reference type, route: %s -> %s", getTypeName(source), getTypeName(dest))
7171
}
7272
var route map[reflect.Type]func(source interface{}, dest interface{}) error
7373
route, ok := routes[reflect.TypeOf(source)]

0 commit comments

Comments
 (0)