Fix Go1.4 backward compatibility

This commit is contained in:
Unknwon
2016-07-09 01:31:50 +08:00
parent 959d90aa69
commit cf53f9204d
2 changed files with 51 additions and 28 deletions
+42 -23
View File
@@ -270,34 +270,53 @@ func MapTo(v, source interface{}, others ...interface{}) error {
return MapToWithMapper(v, nil, source, others...)
}
// reflectSliceWithProperType does the opposite thing as setSliceWithProperType.
func reflectSliceWithProperType(key *Key, field reflect.Value, delim string) error {
slice := field.Slice(0, field.Len())
if field.Len() == 0 {
return nil
}
var buf bytes.Buffer
sliceOf := field.Type().Elem().Kind()
for i := 0; i < field.Len(); i++ {
switch sliceOf {
case reflect.String:
buf.WriteString(slice.Index(i).String())
case reflect.Int, reflect.Int64:
buf.WriteString(fmt.Sprint(slice.Index(i).Int()))
case reflect.Uint, reflect.Uint64:
buf.WriteString(fmt.Sprint(slice.Index(i).Uint()))
case reflect.Float64:
buf.WriteString(fmt.Sprint(slice.Index(i).Float()))
case reflectTime:
buf.WriteString(slice.Index(i).Interface().(time.Time).Format(time.RFC3339))
default:
return fmt.Errorf("unsupported type '[]%s'", sliceOf)
}
buf.WriteString(delim)
}
key.SetValue(buf.String()[:buf.Len()-1])
return nil
}
// reflectWithProperType does the opposite thing as setWithProperType.
func reflectWithProperType(t reflect.Type, key *Key, field reflect.Value, delim string) error {
switch t.Kind() {
case reflect.String:
key.SetValue(field.String())
case reflect.Bool,
reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64,
reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64,
reflect.Float64,
reflectTime:
key.SetValue(fmt.Sprint(field))
case reflect.Bool:
key.SetValue(fmt.Sprint(field.Bool()))
case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
key.SetValue(fmt.Sprint(field.Int()))
case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64:
key.SetValue(fmt.Sprint(field.Uint()))
case reflect.Float32, reflect.Float64:
key.SetValue(fmt.Sprint(field.Float()))
case reflectTime:
key.SetValue(fmt.Sprint(field.Interface().(time.Time).Format(time.RFC3339)))
case reflect.Slice:
vals := field.Slice(0, field.Len())
if field.Len() == 0 {
return nil
}
var buf bytes.Buffer
isTime := fmt.Sprint(field.Type()) == "[]time.Time"
for i := 0; i < field.Len(); i++ {
if isTime {
buf.WriteString(vals.Index(i).Interface().(time.Time).Format(time.RFC3339))
} else {
buf.WriteString(fmt.Sprint(vals.Index(i)))
}
buf.WriteString(delim)
}
key.SetValue(buf.String()[:buf.Len()-1])
return reflectSliceWithProperType(key, field, delim)
default:
return fmt.Errorf("unsupported type '%s'", t)
}
@@ -325,7 +344,7 @@ func (s *Section) reflectFrom(val reflect.Value) error {
}
if (tpField.Type.Kind() == reflect.Ptr && tpField.Anonymous) ||
(tpField.Type.Kind() == reflect.Struct) {
(tpField.Type.Kind() == reflect.Struct && tpField.Type.Kind() != reflectTime) {
// Note: The only error here is section doesn't exist.
sec, err := s.f.GetSection(fieldName)
if err != nil {
+9 -5
View File
@@ -221,14 +221,16 @@ func Test_Struct(t *testing.T) {
Name string `ini:"NAME"`
Male bool
Age int
Height uint
GPA float64
Date time.Time
NeverMind string `ini:"-"`
*Embeded `ini:"infos"`
}
t, err := time.Parse(time.RFC3339, "1993-10-07T20:17:05Z")
So(err, ShouldBeNil)
a := &Author{"Unknwon", true, 21, 2.8, "",
a := &Author{"Unknwon", true, 21, 100, 2.8, t, "",
&Embeded{
[]time.Time{t, t},
[]string{"HangZhou", "Boston"},
@@ -245,10 +247,12 @@ func Test_Struct(t *testing.T) {
var buf bytes.Buffer
_, err = cfg.WriteTo(&buf)
So(err, ShouldBeNil)
So(buf.String(), ShouldEqual, `NAME = Unknwon
Male = true
Age = 21
GPA = 2.8
So(buf.String(), ShouldEqual, `NAME = Unknwon
Male = true
Age = 21
Height = 100
GPA = 2.8
Date = 1993-10-07T20:17:05Z
[infos]
Dates = 1993-10-07T20:17:05Z|1993-10-07T20:17:05Z