Giulio rebuffo eaf0348bd0
[Grindmas] Added tests to Beacon API, also fixed stuff. (#9074)
* Testing Beacon API
* Fixed sentinel code (a little bit)
* Fixed sentinel tests
* Added historical state support
* Fixed state-related endpoints (i was drunk when writing them)
2023-12-25 02:34:13 +01:00

195 lines
6.3 KiB
Go

package tests
import (
"context"
"embed"
_ "embed"
"strconv"
"testing"
libcommon "github.com/ledgerwatch/erigon-lib/common"
"github.com/ledgerwatch/erigon-lib/kv"
"github.com/ledgerwatch/erigon/cl/clparams"
"github.com/ledgerwatch/erigon/cl/cltypes"
"github.com/ledgerwatch/erigon/cl/persistence"
"github.com/ledgerwatch/erigon/cl/persistence/beacon_indicies"
state_accessors "github.com/ledgerwatch/erigon/cl/persistence/state"
"github.com/ledgerwatch/erigon/cl/phase1/core/state"
"github.com/ledgerwatch/erigon/cl/utils"
"github.com/spf13/afero"
"github.com/stretchr/testify/require"
)
//go:embed test_data/capella/blocks_0.ssz_snappy
var capella_blocks_0_ssz_snappy []byte
//go:embed test_data/capella/blocks_1.ssz_snappy
var capella_blocks_1_ssz_snappy []byte
//go:embed test_data/capella/pre.ssz_snappy
var capella_pre_state_ssz_snappy []byte
//go:embed test_data/capella/post.ssz_snappy
var capella_post_state_ssz_snappy []byte
//go:embed test_data/phase0/blocks_0.ssz_snappy
var phase0_blocks_0_ssz_snappy []byte
//go:embed test_data/phase0/blocks_1.ssz_snappy
var phase0_blocks_1_ssz_snappy []byte
//go:embed test_data/phase0/pre.ssz_snappy
var phase0_pre_state_ssz_snappy []byte
//go:embed test_data/phase0/post.ssz_snappy
var phase0_post_state_ssz_snappy []byte
// bellatrix is long
//go:embed test_data/bellatrix
var bellatrixFS embed.FS
type MockBlockReader struct {
u map[uint64]*cltypes.SignedBeaconBlock
}
func NewMockBlockReader() *MockBlockReader {
return &MockBlockReader{u: make(map[uint64]*cltypes.SignedBeaconBlock)}
}
func (m *MockBlockReader) ReadBlockBySlot(ctx context.Context, tx kv.Tx, slot uint64) (*cltypes.SignedBeaconBlock, error) {
return m.u[slot], nil
}
func (m *MockBlockReader) ReadBlockByRoot(ctx context.Context, tx kv.Tx, blockRoot libcommon.Hash) (*cltypes.SignedBeaconBlock, error) {
// do a linear search
for _, v := range m.u {
r, err := v.Block.HashSSZ()
if err != nil {
return nil, err
}
if r == blockRoot {
return v, nil
}
}
return nil, nil
}
func (m *MockBlockReader) ReadHeaderByRoot(ctx context.Context, tx kv.Tx, blockRoot libcommon.Hash) (*cltypes.SignedBeaconBlockHeader, error) {
block, err := m.ReadBlockByRoot(ctx, tx, blockRoot)
if err != nil {
return nil, err
}
if block == nil {
return nil, nil
}
return block.SignedBeaconBlockHeader(), nil
}
func (m *MockBlockReader) FrozenSlots() uint64 {
panic("implement me")
}
func LoadChain(blocks []*cltypes.SignedBeaconBlock, s *state.CachingBeaconState, db kv.RwDB, t *testing.T) (*MockBlockReader, afero.Fs) {
tx, err := db.BeginRw(context.Background())
require.NoError(t, err)
defer tx.Rollback()
fs := afero.NewMemMapFs()
bs := persistence.NewAferoRawBlockSaver(fs, &clparams.MainnetBeaconConfig)
source := persistence.NewBeaconChainDatabaseFilesystem(bs, nil, &clparams.MainnetBeaconConfig)
m := NewMockBlockReader()
for _, block := range blocks {
m.u[block.Block.Slot] = block
require.NoError(t, source.WriteBlock(context.Background(), tx, block, true))
require.NoError(t, beacon_indicies.WriteHighestFinalized(tx, block.Block.Slot+64))
}
require.NoError(t, state_accessors.InitializeStaticTables(tx, s))
require.NoError(t, tx.Commit())
return m, fs
}
func GetCapellaRandom() ([]*cltypes.SignedBeaconBlock, *state.CachingBeaconState, *state.CachingBeaconState) {
block1 := cltypes.NewSignedBeaconBlock(&clparams.MainnetBeaconConfig)
block2 := cltypes.NewSignedBeaconBlock(&clparams.MainnetBeaconConfig)
// Lets do te
if err := utils.DecodeSSZSnappy(block1, capella_blocks_0_ssz_snappy, int(clparams.CapellaVersion)); err != nil {
panic(err)
}
if err := utils.DecodeSSZSnappy(block2, capella_blocks_1_ssz_snappy, int(clparams.CapellaVersion)); err != nil {
panic(err)
}
preState := state.New(&clparams.MainnetBeaconConfig)
if err := utils.DecodeSSZSnappy(preState, capella_pre_state_ssz_snappy, int(clparams.CapellaVersion)); err != nil {
panic(err)
}
postState := state.New(&clparams.MainnetBeaconConfig)
if err := utils.DecodeSSZSnappy(postState, capella_post_state_ssz_snappy, int(clparams.CapellaVersion)); err != nil {
panic(err)
}
return []*cltypes.SignedBeaconBlock{block1, block2}, preState, postState
}
func GetPhase0Random() ([]*cltypes.SignedBeaconBlock, *state.CachingBeaconState, *state.CachingBeaconState) {
block1 := cltypes.NewSignedBeaconBlock(&clparams.MainnetBeaconConfig)
block2 := cltypes.NewSignedBeaconBlock(&clparams.MainnetBeaconConfig)
// Lets do te
if err := utils.DecodeSSZSnappy(block1, phase0_blocks_0_ssz_snappy, int(clparams.Phase0Version)); err != nil {
panic(err)
}
if err := utils.DecodeSSZSnappy(block2, phase0_blocks_1_ssz_snappy, int(clparams.Phase0Version)); err != nil {
panic(err)
}
preState := state.New(&clparams.MainnetBeaconConfig)
if err := utils.DecodeSSZSnappy(preState, phase0_pre_state_ssz_snappy, int(clparams.Phase0Version)); err != nil {
panic(err)
}
postState := state.New(&clparams.MainnetBeaconConfig)
if err := utils.DecodeSSZSnappy(postState, phase0_post_state_ssz_snappy, int(clparams.Phase0Version)); err != nil {
panic(err)
}
return []*cltypes.SignedBeaconBlock{block1, block2}, preState, postState
}
func GetBellatrixRandom() ([]*cltypes.SignedBeaconBlock, *state.CachingBeaconState, *state.CachingBeaconState) {
ret := make([]*cltypes.SignedBeaconBlock, 0, 96)
// format for blocks is blocks_{i}.ssz_snappy where i is the index of the block, starting from 0 to 95 included.
for i := 0; i < 96; i++ {
block := cltypes.NewSignedBeaconBlock(&clparams.MainnetBeaconConfig)
// Lets do te
b, err := bellatrixFS.ReadFile("test_data/bellatrix/blocks_" + strconv.FormatInt(int64(i), 10) + ".ssz_snappy")
if err != nil {
panic(err)
}
if err := utils.DecodeSSZSnappy(block, b, int(clparams.BellatrixVersion)); err != nil {
panic(err)
}
ret = append(ret, block)
}
preState := state.New(&clparams.MainnetBeaconConfig)
b, err := bellatrixFS.ReadFile("test_data/bellatrix/pre.ssz_snappy")
if err != nil {
panic(err)
}
if err := utils.DecodeSSZSnappy(preState, b, int(clparams.BellatrixVersion)); err != nil {
panic(err)
}
postState := state.New(&clparams.MainnetBeaconConfig)
b, err = bellatrixFS.ReadFile("test_data/bellatrix/post.ssz_snappy")
if err != nil {
panic(err)
}
if err := utils.DecodeSSZSnappy(postState, b, int(clparams.BellatrixVersion)); err != nil {
panic(err)
}
return ret, preState, postState
}