From 5e8ce45a842bea4c774c439e3e173e3ea3636845 Mon Sep 17 00:00:00 2001 From: Anna Shaleva Date: Thu, 27 Aug 2020 11:44:40 +0300 Subject: [PATCH] rpc: allow to use arrays in expandArrayIntoScript Should be done together with #1363. Also removed CreateInvocationScript function as we don't have `Invoke` RPC-call anymore. --- pkg/rpc/request/txBuilder.go | 25 +++++++++----------- pkg/rpc/request/tx_builder_test.go | 37 ++++++++++++++++++++++++++++++ 2 files changed, 48 insertions(+), 14 deletions(-) diff --git a/pkg/rpc/request/txBuilder.go b/pkg/rpc/request/txBuilder.go index 64b1ad1ed..82d8507d8 100644 --- a/pkg/rpc/request/txBuilder.go +++ b/pkg/rpc/request/txBuilder.go @@ -97,6 +97,17 @@ func expandArrayIntoScript(script *io.BinWriter, slice []Param) error { default: return errors.New("wrong boolean value") } + case smartcontract.ArrayType: + val, err := fp.Value.GetArray() + if err != nil { + return err + } + err = expandArrayIntoScript(script, val) + if err != nil { + return err + } + emit.Int(script, int64(len(val))) + emit.Opcode(script, opcode.PACK) default: return fmt.Errorf("parameter type %v is not supported", fp.Type) } @@ -135,17 +146,3 @@ func CreateFunctionInvocationScript(contract util.Uint160, params Params) ([]byt emit.AppCall(script.BinWriter, contract) return script.Bytes(), nil } - -// CreateInvocationScript creates a script to invoke given contract with -// given parameters. It differs from CreateFunctionInvocationScript in that it -// expects one array of FuncParams and expands it onto the stack as independent -// elements. -func CreateInvocationScript(contract util.Uint160, funcParams []Param) ([]byte, error) { - script := io.NewBufBinWriter() - err := expandArrayIntoScript(script.BinWriter, funcParams) - if err != nil { - return nil, err - } - emit.AppCall(script.BinWriter, contract) - return script.Bytes(), nil -} diff --git a/pkg/rpc/request/tx_builder_test.go b/pkg/rpc/request/tx_builder_test.go index dd849da0f..6c1f1587e 100644 --- a/pkg/rpc/request/tx_builder_test.go +++ b/pkg/rpc/request/tx_builder_test.go @@ -4,8 +4,10 @@ import ( "encoding/hex" "testing" + "github.com/nspcc-dev/neo-go/pkg/io" "github.com/nspcc-dev/neo-go/pkg/smartcontract" "github.com/nspcc-dev/neo-go/pkg/util" + "github.com/nspcc-dev/neo-go/pkg/vm/opcode" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" ) @@ -88,3 +90,38 @@ func TestInvocationScriptCreationBad(t *testing.T) { assert.NotNil(t, err) } } + +func TestExpandArrayIntoScript(t *testing.T) { + testCases := []struct { + Input []Param + Expected []byte + }{ + { + Input: []Param{{Type: FuncParamT, Value: FuncParam{Type: smartcontract.StringType, Value: Param{Value: "a"}}}}, + Expected: []byte{byte(opcode.PUSHDATA1), 1, byte('a')}, + }, + { + Input: []Param{{Type: FuncParamT, Value: FuncParam{Type: smartcontract.ArrayType, Value: Param{Value: []Param{{Type: FuncParamT, Value: FuncParam{Type: smartcontract.StringType, Value: Param{Value: "a"}}}}}}}}, + Expected: []byte{byte(opcode.PUSHDATA1), 1, byte('a'), byte(opcode.PUSH1), byte(opcode.PACK)}, + }, + } + for _, c := range testCases { + script := io.NewBufBinWriter() + err := expandArrayIntoScript(script.BinWriter, c.Input) + require.NoError(t, err) + require.Equal(t, c.Expected, script.Bytes()) + } + errorCases := [][]Param{ + { + {Type: FuncParamT, Value: FuncParam{Type: smartcontract.ArrayType, Value: Param{Value: "a"}}}, + }, + { + {Type: FuncParamT, Value: FuncParam{Type: smartcontract.ArrayType, Value: Param{Value: []Param{{Type: FuncParamT, Value: nil}}}}}, + }, + } + for _, c := range errorCases { + script := io.NewBufBinWriter() + err := expandArrayIntoScript(script.BinWriter, c) + require.Error(t, err) + } +}