Skip to content

Commit

Permalink
[abi analyzer] add unit tests
Browse files Browse the repository at this point in the history
  • Loading branch information
Andrew7234 committed Mar 1, 2024
1 parent 8571414 commit 6e241bf
Showing 1 changed file with 297 additions and 0 deletions.
297 changes: 297 additions & 0 deletions analyzer/evmabibackfill/evm_abi_backfill_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,297 @@
package evmabibackfill

import (
"encoding/base64"
"encoding/json"
"testing"

ethCommon "github.com/ethereum/go-ethereum/common"

"github.com/oasisprotocol/nexus/analyzer/evmabi"
"github.com/oasisprotocol/nexus/common"
"github.com/oasisprotocol/nexus/log"
"github.com/oasisprotocol/oasis-sdk/client-sdk/go/modules/evm"
"github.com/stretchr/testify/require"
)

// TODO: Update WROSE source and add tests for more txs, mismatched txs, and custom errors

type mockParsedEvent struct {
Name *string
Args []*abiEncodedArg
Sig *ethCommon.Hash
}

type mockParsedTxCall struct {
Name *string
Args []*abiEncodedArg
}

func unmarshalEvmEvent(t *testing.T, body []byte) *abiEncodedEvent {
var ev evm.Event
err := json.Unmarshal(body, &ev)
require.Nil(t, err)
return &abiEncodedEvent{
Round: 0,
TxIndex: nil,
EventBody: ev,
}
}

func unmarshalEvmTx(t *testing.T, body string, error_message *string) *abiEncodedTx {
txData, err := base64.StdEncoding.DecodeString(body)
require.Nil(t, err)
return &abiEncodedTx{
TxHash: "", // not relevant for current unit tests
TxData: txData,
TxRevertReason: error_message,
}
}

func TestParseEvent(t *testing.T) {
abi := evmabi.WROSE
p := &processor{
runtime: common.RuntimeSapphire,
target: nil,
logger: log.NewDefaultLogger("testing"),
}
evs := []*abiEncodedEvent{
unmarshalEvmEvent(t, []byte(`{"data": "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAADCopscuTr4A=", "topics": ["3fJSrRviyJtpwrBo/DeNqpUrp/FjxKEWKPVaTfUjs+8=", "AAAAAAAAAAAAAAAAw3+DQaxuSpRTgwK81NSc8IUtMMA=", "AAAAAAAAAAAAAAAAWZiaj7/4vj0d6v/ytGtmtjrLeX4="], "address": "i8KwMLKZlk7vteHgs2mRNS5W0tM="}`)),
unmarshalEvmEvent(t, []byte(`{"data": "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAxT0Gl9KwCAA=", "topics": ["f89TLBXwptsL1tDgOL6nHTDYCMfZjLO/cmipW/UIG2U=", "AAAAAAAAAAAAAAAAXHL3b32uFt00y2GDtz9HkapLO8Q="], "address": "i8KwMLKZlk7vteHgs2mRNS5W0tM="}`)),
unmarshalEvmEvent(t, []byte(`{"data": "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAIeGeDJurJAAAA=", "topics": ["4f/8xJI9BLVZ9NKai/xs2gTrWw08RgdRwkAsXFzJEJw=", "AAAAAAAAAAAAAAAA3R7ge0bH7YiGcaZG88ejc5Toz4U="], "address": "i8KwMLKZlk7vteHgs2mRNS5W0tM="}`)),
unmarshalEvmEvent(t, []byte(`{"data": "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAIeGeDJurJAAAA=", "topics": ["jFvh5evsfVvRT3FCfR6E890DFMD3sikeWyAKyMfDuSU=", "AAAAAAAAAAAAAAAA3R7ge0bH7YiGcaZG88ejc5Toz4U=", "AAAAAAAAAAAAAAAAtTnx0BpDfH8wyvyZTpGPlS3cC6I="], "address": "i8KwMLKZlk7vteHgs2mRNS5W0tM="}`)),
}

name1 := "Transfer"
sig1 := ethCommon.HexToHash("0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef")
name2 := "Withdrawal"
sig2 := ethCommon.HexToHash("0x7fcf532c15f0a6db0bd6d0e038bea71d30d808c7d98cb3bf7268a95bf5081b65")
name3 := "Deposit"
sig3 := ethCommon.HexToHash("0xe1fffcc4923d04b559f4d29a8bfc6cda04eb5b0d3c460751c2402c5c5cc9109c")
name4 := "Approval"
sig4 := ethCommon.HexToHash("0x8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b925")

expected := []mockParsedEvent{
{
Name: &name1,
Sig: &sig1,
Args: []*abiEncodedArg{
{
Name: "src",
EvmType: "address",
Value: ethCommon.HexToAddress("0xc37F8341Ac6e4a94538302bCd4d49Cf0852D30C0"),
},
{
Name: "dst",
EvmType: "address",
Value: ethCommon.HexToAddress("0x59989A8fBff8be3d1deAFFF2b46B66B63ACB797e"),
},
{
Name: "wad",
EvmType: "uint256",
Value: "876558921078386560",
},
},
},
{
Name: &name2,
Sig: &sig2,
Args: []*abiEncodedArg{
{
Name: "src",
EvmType: "address",
Value: ethCommon.HexToAddress("0x5C72F76F7dae16dD34Cb6183b73F4791aa4B3BC4"),
},
{
Name: "wad",
EvmType: "uint256",
Value: "14212523248195733504",
},
},
},
{
Name: &name3,
Sig: &sig3,
Args: []*abiEncodedArg{
{
Name: "dst",
EvmType: "address",
Value: ethCommon.HexToAddress("0xDd1Ee07b46C7eD888671a646F3c7a37394e8cF85"),
},
{
Name: "wad",
EvmType: "uint256",
Value: "10000000000000000000000",
},
},
},
{
Name: &name4,
Sig: &sig4,
Args: []*abiEncodedArg{
{
Name: "src",
EvmType: "address",
Value: ethCommon.HexToAddress("0xDd1Ee07b46C7eD888671a646F3c7a37394e8cF85"),
},
{
Name: "guy",
EvmType: "address",
Value: ethCommon.HexToAddress("0xb539f1D01A437C7f30cAfC994e918F952dDc0bA2"),
},
{
Name: "wad",
EvmType: "uint256",
Value: "10000000000000000000000",
},
},
},
}

for i, ev := range evs {
name, args, sig, err := p.parseEvent(ev, *abi)
require.Nil(t, err)
verifyEvent(t, &expected[i], name, args, sig)
}
}

func TestParseUnknownEvent(t *testing.T) {
abi := evmabi.WROSE
p := &processor{
runtime: common.RuntimeSapphire,
target: nil,
logger: log.NewDefaultLogger("testing"),
}
// Non-WROSE event.
rawEv := []byte(`{"data": "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=", "topics": ["8nnmofXjIMypETVnbZy25EyooIwLiDQrzbEUT2URtWg=", "AAAAAAAAAAAAAAAArk2RKpUohmFUB3UShFG6FIKuqKc=", "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAI="], "address": "jZzJ7hGq+GWRPe7JOe6y3Hg4q3s="}`)
ev := unmarshalEvmEvent(t, rawEv)

name, args, sig, err := p.parseEvent(ev, *abi)
require.NotNil(t, err)
require.Nil(t, name)
require.Nil(t, args)
require.Nil(t, sig)
}

func TestParseTransactionCall(t *testing.T) {
abi := evmabi.WROSE
p := &processor{
runtime: common.RuntimeSapphire,
target: nil,
logger: log.NewDefaultLogger("testing"),
}
txs := []*abiEncodedTx{
// unmarshalEvmTx(t, "omRib2R5o2Jwa1gg6KR1JehYdjBZyYOH06CycJIxAuTmmY22C6nLtybyPTlkZGF0YVgbjk8cKK1D/PuiREnFTOkHm4YosIhcDHtRzPkPZW5vbmNlT95YOkkjR3eTTH7QR/O8tmZmb3JtYXQB", nil), // The WROSE abi in the nexus repository is out of date/incomplete.
unmarshalEvmTx(t, "Lhp9TQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAKcV46p6RigAA", nil),
unmarshalEvmTx(t, "qQWcuwAAAAAAAAAAAAAAAOY8J3oxo9tm0HXYxapOlEKOuxjxAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=", nil),
unmarshalEvmTx(t, "0OMNsA==", nil),
}

name1 := "withdraw"
name2 := "transfer"
name3 := "deposit"
expected := []mockParsedTxCall{
{
Name: &name1,
Args: []*abiEncodedArg{
{
Name: "wad",
EvmType: "uint256",
Value: "770545888011536171008",
},
},
},
{
Name: &name2,
Args: []*abiEncodedArg{
{
Name: "dst",
EvmType: "address",
Value: ethCommon.HexToAddress("0xE63c277a31A3dB66D075D8C5aA4E94428Ebb18F1"),
},
{
Name: "wad",
EvmType: "uint256",
Value: "0",
},
},
},
{
Name: &name3,
Args: []*abiEncodedArg{},
},
}
for i, tx := range txs {
name, args, err := p.parseTxCall(tx, *abi)
require.Nil(t, err)
verifyTxCall(t, &expected[i], name, args)
}
}

func TestParseTxErrorPlaintext(t *testing.T) {
abi := evmabi.WROSE
p := &processor{
runtime: common.RuntimeSapphire,
target: nil,
logger: log.NewDefaultLogger("testing"),
}
errMsg := "reverted: plaintext error message"
emptyErrMsg := "reverted: "
txs := []*abiEncodedTx{
unmarshalEvmTx(t, "", &errMsg),
unmarshalEvmTx(t, "", &emptyErrMsg),
}

for _, tx := range txs {
parsedMsg, args, err := p.parseTxErr(tx, *abi)
require.Nil(t, err)
require.Nil(t, parsedMsg)
require.Nil(t, args)
}
}

func verifyEvent(t *testing.T, expected *mockParsedEvent, name *string, args []*abiEncodedArg, sig *ethCommon.Hash) {
if expected.Name != nil {
require.NotNil(t, name)
require.Equal(t, *expected.Name, *name)
} else {
require.Nil(t, name)
}
if expected.Args != nil {
require.NotNil(t, args)
require.Equal(t, len(expected.Args), len(args))
for i, ea := range expected.Args {
require.Equal(t, ea.Name, args[i].Name)
require.Equal(t, ea.EvmType, args[i].EvmType)
require.Equal(t, ea.Value, args[i].Value)
}
} else {
require.Nil(t, args)
}
if expected.Sig != nil {
require.NotNil(t, sig)
require.Equal(t, *expected.Sig, *sig)
} else {
require.Nil(t, sig)
}
}

func verifyTxCall(t *testing.T, expected *mockParsedTxCall, name *string, args []*abiEncodedArg) {
if expected.Name != nil {
require.NotNil(t, name)
require.Equal(t, *expected.Name, *name)
} else {
require.Nil(t, name)
}
if expected.Args != nil {
require.NotNil(t, args)
require.Equal(t, len(expected.Args), len(args))
for i, ea := range expected.Args {
require.Equal(t, ea.Name, args[i].Name)
require.Equal(t, ea.EvmType, args[i].EvmType)
require.Equal(t, ea.Value, args[i].Value)
}
} else {
require.Nil(t, args)
}
}

0 comments on commit 6e241bf

Please sign in to comment.