Skip to content

Commit 2fb8fbf

Browse files
authored
Eliminate duplicate type switches (#423)
* Eliminate duplicate type switches * Only operate on exported fields * Add test case for unexported
1 parent a95b2f5 commit 2fb8fbf

File tree

2 files changed

+20
-57
lines changed

2 files changed

+20
-57
lines changed

conf/conf.go

Lines changed: 16 additions & 57 deletions
Original file line numberDiff line numberDiff line change
@@ -35,13 +35,17 @@ func Bind(ptr any) error {
3535

3636
func bindValue(objVal reflect.Value) error {
3737
for i := 0; i < objVal.NumField(); i++ {
38+
field := objVal.Type().Field(i)
39+
if !field.IsExported() {
40+
continue
41+
}
42+
3843
fieldVal := objVal.Field(i)
3944
if fieldVal.Kind() == reflect.Struct {
4045
if err := bindValue(fieldVal); err != nil {
4146
return err
4247
}
4348
} else {
44-
field := objVal.Type().Field(i)
4549
if err := setToDefault(field, fieldVal); err != nil {
4650
return err
4751
}
@@ -92,43 +96,42 @@ func setFromEnv(field reflect.StructField, val reflect.Value) {
9296
func set(val reflect.Value, str string) error {
9397
switch val.Type().Kind() {
9498
case reflect.String:
95-
typed, _ := getValue(val.Type(), str)
96-
val.SetString(typed.(string))
99+
val.SetString(str)
97100

98101
case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
99-
typed, err := getValue(val.Type(), str)
102+
typed, err := strconv.ParseInt(str, 10, val.Type().Bits())
100103
if err != nil {
101104
return err
102105
}
103-
val.SetInt(typed.(int64))
106+
val.SetInt(typed)
104107

105108
case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64:
106-
typed, err := getValue(val.Type(), str)
109+
typed, err := strconv.ParseUint(str, 10, val.Type().Bits())
107110
if err != nil {
108111
return err
109112
}
110-
val.SetUint(typed.(uint64))
113+
val.SetUint(typed)
111114

112115
case reflect.Float32, reflect.Float64:
113-
typed, err := getValue(val.Type(), str)
116+
typed, err := strconv.ParseFloat(str, val.Type().Bits())
114117
if err != nil {
115118
return err
116119
}
117-
val.SetFloat(typed.(float64))
120+
val.SetFloat(typed)
118121

119122
case reflect.Complex64, reflect.Complex128:
120-
typed, err := getValue(val.Type(), str)
123+
typed, err := strconv.ParseComplex(str, val.Type().Bits())
121124
if err != nil {
122125
return err
123126
}
124-
val.SetComplex(typed.(complex128))
127+
val.SetComplex(typed)
125128

126129
case reflect.Bool:
127-
typed, err := getValue(val.Type(), str)
130+
typed, err := strconv.ParseBool(str)
128131
if err != nil {
129132
return err
130133
}
131-
val.SetBool(typed.(bool))
134+
val.SetBool(typed)
132135

133136
case reflect.Array, reflect.Slice:
134137
elementType := val.Type().Elem()
@@ -156,47 +159,3 @@ func set(val reflect.Value, str string) error {
156159

157160
return nil
158161
}
159-
160-
func getValue(fieldType reflect.Type, str string) (any, error) {
161-
switch fieldType.Kind() {
162-
case reflect.String:
163-
return str, nil
164-
165-
case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
166-
typed, err := strconv.ParseInt(str, 10, fieldType.Bits())
167-
if err != nil {
168-
return nil, err
169-
}
170-
return typed, nil
171-
172-
case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64:
173-
typed, err := strconv.ParseUint(str, 10, fieldType.Bits())
174-
if err != nil {
175-
return nil, err
176-
}
177-
return typed, nil
178-
179-
case reflect.Float32, reflect.Float64:
180-
typed, err := strconv.ParseFloat(str, fieldType.Bits())
181-
if err != nil {
182-
return nil, err
183-
}
184-
return typed, nil
185-
186-
case reflect.Complex64, reflect.Complex128:
187-
typed, err := strconv.ParseComplex(str, fieldType.Bits())
188-
if err != nil {
189-
return nil, err
190-
}
191-
return typed, nil
192-
193-
case reflect.Bool:
194-
typed, err := strconv.ParseBool(str)
195-
if err != nil {
196-
return nil, err
197-
}
198-
return typed, nil
199-
}
200-
201-
return nil, errUnsupportedType{fieldType}
202-
}

conf/conf_test.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,8 @@ func TestBind_Defaults(t *testing.T) {
1818
TestIntPtr *int `default:"-1"`
1919
}
2020
type allSupportedTypes struct {
21+
unexportedInt int `default:"5"`
22+
2123
TestInts intTypes
2224

2325
TestUint uint `default:"1"`
@@ -46,6 +48,8 @@ func TestBind_Defaults(t *testing.T) {
4648
{
4749
name: "Defaults are set",
4850
want: allSupportedTypes{
51+
unexportedInt: 0, // Should be ignored, not set
52+
4953
TestInts: intTypes{
5054
TestInt: -1,
5155
TestInt8: -2,

0 commit comments

Comments
 (0)