github.com/nspcc-dev/neo-go@v0.105.2-0.20240517133400-6be757af3eba/pkg/rpcclient/invoker/invoker_test.go (about) 1 package invoker 2 3 import ( 4 "errors" 5 "testing" 6 7 "github.com/google/uuid" 8 "github.com/nspcc-dev/neo-go/pkg/core/transaction" 9 "github.com/nspcc-dev/neo-go/pkg/neorpc/result" 10 "github.com/nspcc-dev/neo-go/pkg/smartcontract" 11 "github.com/nspcc-dev/neo-go/pkg/util" 12 "github.com/nspcc-dev/neo-go/pkg/vm/stackitem" 13 "github.com/stretchr/testify/require" 14 ) 15 16 type rpcInv struct { 17 resInv *result.Invoke 18 resTrm bool 19 resItm []stackitem.Item 20 err error 21 } 22 23 func (r *rpcInv) InvokeContractVerify(contract util.Uint160, params []smartcontract.Parameter, signers []transaction.Signer, witnesses ...transaction.Witness) (*result.Invoke, error) { 24 return r.resInv, r.err 25 } 26 func (r *rpcInv) InvokeFunction(contract util.Uint160, operation string, params []smartcontract.Parameter, signers []transaction.Signer) (*result.Invoke, error) { 27 return r.resInv, r.err 28 } 29 func (r *rpcInv) InvokeScript(script []byte, signers []transaction.Signer) (*result.Invoke, error) { 30 return r.resInv, r.err 31 } 32 func (r *rpcInv) InvokeContractVerifyAtHeight(height uint32, contract util.Uint160, params []smartcontract.Parameter, signers []transaction.Signer, witnesses ...transaction.Witness) (*result.Invoke, error) { 33 return r.resInv, r.err 34 } 35 func (r *rpcInv) InvokeContractVerifyWithState(stateroot util.Uint256, contract util.Uint160, params []smartcontract.Parameter, signers []transaction.Signer, witnesses ...transaction.Witness) (*result.Invoke, error) { 36 return r.resInv, r.err 37 } 38 func (r *rpcInv) InvokeFunctionAtHeight(height uint32, contract util.Uint160, operation string, params []smartcontract.Parameter, signers []transaction.Signer) (*result.Invoke, error) { 39 return r.resInv, r.err 40 } 41 func (r *rpcInv) InvokeFunctionWithState(stateroot util.Uint256, contract util.Uint160, operation string, params []smartcontract.Parameter, signers []transaction.Signer) (*result.Invoke, error) { 42 return r.resInv, r.err 43 } 44 func (r *rpcInv) InvokeScriptAtHeight(height uint32, script []byte, signers []transaction.Signer) (*result.Invoke, error) { 45 return r.resInv, r.err 46 } 47 func (r *rpcInv) InvokeScriptWithState(stateroot util.Uint256, script []byte, signers []transaction.Signer) (*result.Invoke, error) { 48 return r.resInv, r.err 49 } 50 func (r *rpcInv) TerminateSession(sessionID uuid.UUID) (bool, error) { 51 return r.resTrm, r.err 52 } 53 func (r *rpcInv) TraverseIterator(sessionID, iteratorID uuid.UUID, maxItemsCount int) ([]stackitem.Item, error) { 54 return r.resItm, r.err 55 } 56 57 func TestInvoker(t *testing.T) { 58 resExp := &result.Invoke{State: "HALT"} 59 ri := &rpcInv{resExp, true, nil, nil} 60 61 testInv := func(t *testing.T, inv *Invoker) { 62 res, err := inv.Call(util.Uint160{}, "method") 63 require.NoError(t, err) 64 require.Equal(t, resExp, res) 65 66 res, err = inv.Verify(util.Uint160{}, nil) 67 require.NoError(t, err) 68 require.Equal(t, resExp, res) 69 70 res, err = inv.Run([]byte{1}) 71 require.NoError(t, err) 72 require.Equal(t, resExp, res) 73 74 res, err = inv.Call(util.Uint160{}, "method") 75 require.NoError(t, err) 76 require.Equal(t, resExp, res) 77 78 res, err = inv.Verify(util.Uint160{}, nil, "param") 79 require.NoError(t, err) 80 require.Equal(t, resExp, res) 81 82 res, err = inv.Call(util.Uint160{}, "method", 42) 83 require.NoError(t, err) 84 require.Equal(t, resExp, res) 85 86 _, err = inv.Verify(util.Uint160{}, nil, make(map[int]int)) 87 require.Error(t, err) 88 89 _, err = inv.Call(util.Uint160{}, "method", make(map[int]int)) 90 require.Error(t, err) 91 92 res, err = inv.CallAndExpandIterator(util.Uint160{}, "method", 10, 42) 93 require.NoError(t, err) 94 require.Equal(t, resExp, res) 95 96 _, err = inv.CallAndExpandIterator(util.Uint160{}, "method", 10, make(map[int]int)) 97 require.Error(t, err) 98 } 99 t.Run("standard", func(t *testing.T) { 100 testInv(t, New(ri, nil)) 101 }) 102 t.Run("historic, height", func(t *testing.T) { 103 testInv(t, NewHistoricAtHeight(100500, ri, nil)) 104 }) 105 t.Run("historic, state", func(t *testing.T) { 106 testInv(t, NewHistoricWithState(util.Uint256{}, ri, nil)) 107 }) 108 t.Run("broken historic", func(t *testing.T) { 109 inv := New(&historicConverter{client: ri}, nil) // It's not possible to do this from outside. 110 require.Panics(t, func() { _, _ = inv.Call(util.Uint160{}, "method") }) 111 require.Panics(t, func() { _, _ = inv.Verify(util.Uint160{}, nil, "param") }) 112 require.Panics(t, func() { _, _ = inv.Run([]byte{1}) }) 113 }) 114 t.Run("terminate session", func(t *testing.T) { 115 for _, inv := range []*Invoker{New(ri, nil), NewHistoricWithState(util.Uint256{}, ri, nil)} { 116 ri.err = errors.New("") 117 require.Error(t, inv.TerminateSession(uuid.UUID{})) 118 ri.err = nil 119 ri.resTrm = false 120 require.Error(t, inv.TerminateSession(uuid.UUID{})) 121 ri.resTrm = true 122 require.NoError(t, inv.TerminateSession(uuid.UUID{})) 123 } 124 }) 125 t.Run("traverse iterator", func(t *testing.T) { 126 for _, inv := range []*Invoker{New(ri, nil), NewHistoricWithState(util.Uint256{}, ri, nil)} { 127 res, err := inv.TraverseIterator(uuid.UUID{}, &result.Iterator{ 128 Values: []stackitem.Item{stackitem.Make(42)}, 129 }, 0) 130 require.NoError(t, err) 131 require.Equal(t, []stackitem.Item{stackitem.Make(42)}, res) 132 133 res, err = inv.TraverseIterator(uuid.UUID{}, &result.Iterator{ 134 Values: []stackitem.Item{stackitem.Make(42)}, 135 }, 1) 136 require.NoError(t, err) 137 require.Equal(t, []stackitem.Item{stackitem.Make(42)}, res) 138 139 res, err = inv.TraverseIterator(uuid.UUID{}, &result.Iterator{ 140 Values: []stackitem.Item{stackitem.Make(42)}, 141 }, 2) 142 require.NoError(t, err) 143 require.Equal(t, []stackitem.Item{stackitem.Make(42)}, res) 144 145 ri.err = errors.New("") 146 _, err = inv.TraverseIterator(uuid.UUID{}, &result.Iterator{ 147 ID: &uuid.UUID{}, 148 }, 2) 149 require.Error(t, err) 150 151 ri.err = nil 152 ri.resItm = []stackitem.Item{stackitem.Make(42)} 153 res, err = inv.TraverseIterator(uuid.UUID{}, &result.Iterator{ 154 ID: &uuid.UUID{}, 155 }, 2) 156 require.NoError(t, err) 157 require.Equal(t, []stackitem.Item{stackitem.Make(42)}, res) 158 } 159 }) 160 }