From dbdb3e56a5e332b0478e0a8e8522e53a49fb7dcd Mon Sep 17 00:00:00 2001 From: infixint943 <45997896+infixint943@users.noreply.github.com> Date: Mon, 10 Aug 2020 22:23:57 +0530 Subject: [PATCH] Write OptionAnswer value to non interface{} map (#293) * write OptionAnswer to non interface map * Fix stupid mistake * add tests --- core/write.go | 20 +++++++++++++++++++- core/write_test.go | 33 +++++++++++++++++++++++++++------ 2 files changed, 46 insertions(+), 7 deletions(-) diff --git a/core/write.go b/core/write.go index 258c1940..47d0e498 100644 --- a/core/write.go +++ b/core/write.go @@ -86,7 +86,25 @@ func WriteAnswer(t interface{}, name string, v interface{}) (err error) { return copy(field, value) case reflect.Map: mapType := reflect.TypeOf(t).Elem() - if mapType.Key().Kind() != reflect.String || mapType.Elem().Kind() != reflect.Interface { + if mapType.Key().Kind() != reflect.String { + return errors.New("answer maps key must be of type string") + } + + // copy only string value/index value to map if, + // map is not of type interface and is 'OptionAnswer' + if value.Type().Name() == "OptionAnswer" { + if kval := mapType.Elem().Kind(); kval == reflect.String { + mt := *t.(*map[string]string) + mt[name] = value.FieldByName("Value").String() + return nil + } else if kval == reflect.Int { + mt := *t.(*map[string]int) + mt[name] = int(value.FieldByName("Index").Int()) + return nil + } + } + + if mapType.Elem().Kind() != reflect.Interface { return errors.New("answer maps must be of type map[string]interface") } mt := *t.(*map[string]interface{}) diff --git a/core/write_test.go b/core/write_test.go index f02a500b..87e902ed 100644 --- a/core/write_test.go +++ b/core/write_test.go @@ -59,6 +59,28 @@ func TestWrite_canWriteSlice(t *testing.T) { assert.Equal(t, []string{"hello", "world"}, ptr) } +func TestWrite_canWriteMapString(t *testing.T) { + // a map to hold the values + ptr := map[string]string{} + + // copy in a value + WriteAnswer(&ptr, "test", OptionAnswer{Value: "hello", Index: 5}) + + // make sure only string value is written + assert.Equal(t, map[string]string{"test": "hello"}, ptr) +} + +func TestWrite_canWriteMapInt(t *testing.T) { + // a map to hold the values + ptr := map[string]int{} + + // copy in a value + WriteAnswer(&ptr, "test", OptionAnswer{Value: "hello", Index: 5}) + + // make sure only string value is written + assert.Equal(t, map[string]int{"test": 5}, ptr) +} + func TestWrite_recoversInvalidReflection(t *testing.T) { // a variable to mutate ptr := false @@ -108,7 +130,7 @@ func TestWriteAnswer_canMutateStruct(t *testing.T) { } func TestWriteAnswer_optionAnswer(t *testing.T) { - t.Run("writes index for ints", func (t *testing.T) { + t.Run("writes index for ints", func(t *testing.T) { val := 0 // write a value to an existing field @@ -128,7 +150,7 @@ func TestWriteAnswer_optionAnswer(t *testing.T) { } }) - t.Run("writes OptionAnswer for OptionAnswer", func (t *testing.T) { + t.Run("writes OptionAnswer for OptionAnswer", func(t *testing.T) { val := OptionAnswer{} // write a value to an existing field @@ -148,7 +170,7 @@ func TestWriteAnswer_optionAnswer(t *testing.T) { } }) - t.Run("writes value for strings", func (t *testing.T) { + t.Run("writes value for strings", func(t *testing.T) { val := "" // write a value to an existing field @@ -168,7 +190,7 @@ func TestWriteAnswer_optionAnswer(t *testing.T) { } }) - t.Run("writes slice of indices for slice of ints", func (t *testing.T) { + t.Run("writes slice of indices for slice of ints", func(t *testing.T) { val := []int{} // write a value to an existing field @@ -190,7 +212,7 @@ func TestWriteAnswer_optionAnswer(t *testing.T) { } }) - t.Run("writes slice of values for slice of strings", func (t *testing.T) { + t.Run("writes slice of values for slice of strings", func(t *testing.T) { val := []string{} // write a value to an existing field @@ -206,7 +228,6 @@ func TestWriteAnswer_optionAnswer(t *testing.T) { return } - if len(val) != 1 || val[0] != "string value" { t.Errorf("Wrong value written. Wanted [string value], got %v", val) return