smartcontract: store MapType Parameter as a slice of KV pairs

Fixes #809.

Basically, there are three alternative approaches to fixing it:
 * allowing both []byte and string for ByteArrayType value
   minimal invasion into existing code, but ugly as hell and will probably
   backfire at some point
 * storing string values in ByteArrayType
   incurs quite a number of type conversions (and associated data copying),
   though note that these values are not changed usually, so dynamic
   properties of []byte are almost irrelevant here
 * storing only []byte values in ByteArrayType
   makes it impossible to use them as map keys which can be solved in several
   ways:
   - via an interface (Marshalable)
     which is good, but makes testing and comparing values in general harder,
     because of keys mismatch
   - using serialized Parameter as a key (in a string)
     which will need some additional marshaling/unmarshaling
   - converting MapType from map to a slice of key-value pairs
     not a bad idea as we don't use this map as a map really, the type
     itself is all about input/output for real VM types and this approach is
     also a bit closer to JSON representation of the Map
This commit is contained in:
Roman Khimov 2020-03-30 18:24:06 +03:00
parent b502210ade
commit 3dbe549a61
4 changed files with 79 additions and 87 deletions

View file

@ -72,9 +72,15 @@ var marshalJSONTestCases = []struct {
{
input: Parameter{
Type: MapType,
Value: map[Parameter]Parameter{
{Type: StringType, Value: "key1"}: {Type: IntegerType, Value: int64(1)},
{Type: StringType, Value: "key2"}: {Type: StringType, Value: "two"},
Value: []ParameterPair{
{
Key: Parameter{Type: StringType, Value: "key1"},
Value: Parameter{Type: IntegerType, Value: int64(1)},
},
{
Key: Parameter{Type: StringType, Value: "key2"},
Value: Parameter{Type: StringType, Value: "two"},
},
},
},
result: `{"type":"Map","value":[{"key":{"type":"String","value":"key1"},"value":{"type":"Integer","value":1}},{"key":{"type":"String","value":"key2"},"value":{"type":"String","value":"two"}}]}`,
@ -82,11 +88,14 @@ var marshalJSONTestCases = []struct {
{
input: Parameter{
Type: MapType,
Value: map[Parameter]Parameter{
{Type: StringType, Value: "key1"}: {Type: ArrayType, Value: []Parameter{
{Type: StringType, Value: "str 1"},
{Type: IntegerType, Value: int64(2)},
}},
Value: []ParameterPair{
{
Key: Parameter{Type: StringType, Value: "key1"},
Value: Parameter{Type: ArrayType, Value: []Parameter{
{Type: StringType, Value: "str 1"},
{Type: IntegerType, Value: int64(2)},
}},
},
},
},
result: `{"type":"Map","value":[{"key":{"type":"String","value":"key1"},"value":{"type":"Array","value":[{"type":"String","value":"str 1"},{"type":"Integer","value":2}]}}]}`,
@ -209,9 +218,15 @@ var unmarshalJSONTestCases = []struct {
input: `{"type":"Map","value":[{"key":{"type":"String","value":"key1"},"value":{"type":"Integer","value":1}},{"key":{"type":"String","value":"key2"},"value":{"type":"String","value":"two"}}]}`,
result: Parameter{
Type: MapType,
Value: map[Parameter]Parameter{
{Type: StringType, Value: "key1"}: {Type: IntegerType, Value: int64(1)},
{Type: StringType, Value: "key2"}: {Type: StringType, Value: "two"},
Value: []ParameterPair{
{
Key: Parameter{Type: StringType, Value: "key1"},
Value: Parameter{Type: IntegerType, Value: int64(1)},
},
{
Key: Parameter{Type: StringType, Value: "key2"},
Value: Parameter{Type: StringType, Value: "two"},
},
},
},
},
@ -219,11 +234,14 @@ var unmarshalJSONTestCases = []struct {
input: `{"type":"Map","value":[{"key":{"type":"String","value":"key1"},"value":{"type":"Array","value":[{"type":"String","value":"str 1"},{"type":"Integer","value":2}]}}]}`,
result: Parameter{
Type: MapType,
Value: map[Parameter]Parameter{
{Type: StringType, Value: "key1"}: {Type: ArrayType, Value: []Parameter{
{Type: StringType, Value: "str 1"},
{Type: IntegerType, Value: int64(2)},
}},
Value: []ParameterPair{
{
Key: Parameter{Type: StringType, Value: "key1"},
Value: Parameter{Type: ArrayType, Value: []Parameter{
{Type: StringType, Value: "str 1"},
{Type: IntegerType, Value: int64(2)},
}},
},
},
},
},