Skip to content

Commit

Permalink
refactor(dot/state): only store finalised blocks in database (#1833)
Browse files Browse the repository at this point in the history
  • Loading branch information
noot committed Oct 21, 2021
1 parent 67bb5ef commit 5e42215
Show file tree
Hide file tree
Showing 37 changed files with 612 additions and 1,053 deletions.
2 changes: 1 addition & 1 deletion dot/core/service_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -201,7 +201,7 @@ func TestHandleChainReorg_WithReorg_Trans(t *testing.T) {

nonce := uint64(0)

// Add extrinsic to block `block31`
// Add extrinsic to block `block41`
ext := createExtrinsic(t, rt, bs.GenesisHash(), nonce)

block41 := sync.BuildBlock(t, rt, &block31.Header, ext)
Expand Down
6 changes: 4 additions & 2 deletions dot/digest/digest_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -94,13 +94,15 @@ func TestHandler_GrandpaScheduledChange(t *testing.T) {

headers, _ := state.AddBlocksToState(t, handler.blockState.(*state.BlockState), 2, false)
for i, h := range headers {
handler.blockState.(*state.BlockState).SetFinalisedHash(h.Hash(), uint64(i), 0)
err = handler.blockState.(*state.BlockState).SetFinalisedHash(h.Hash(), uint64(i), 0)
require.NoError(t, err)
}

// authorities should change on start of block 3 from start
headers, _ = state.AddBlocksToState(t, handler.blockState.(*state.BlockState), 1, false)
for _, h := range headers {
handler.blockState.(*state.BlockState).SetFinalisedHash(h.Hash(), 3, 0)
err = handler.blockState.(*state.BlockState).SetFinalisedHash(h.Hash(), 3, 0)
require.NoError(t, err)
}

time.Sleep(time.Millisecond * 500)
Expand Down
2 changes: 1 addition & 1 deletion dot/rpc/modules/chain.go
Original file line number Diff line number Diff line change
Expand Up @@ -103,7 +103,7 @@ func (cm *ChainModule) GetBlock(r *http.Request, req *ChainHashRequest, res *Cha
return err
}
for _, e := range ext {
res.Block.Body = append(res.Block.Body, fmt.Sprintf("0x%x", e))
res.Block.Body = append(res.Block.Body, e.String())
}
}
return nil
Expand Down
55 changes: 22 additions & 33 deletions dot/rpc/modules/chain_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -314,13 +314,14 @@ func TestChainGetFinalizedHeadByRound(t *testing.T) {

digest := types.NewDigest()
digest.Add(*types.NewBabeSecondaryPlainPreDigest(0, 1).ToPreRuntimeDigest())
header := &types.Header{

header := types.Header{
ParentHash: genesisHeader.Hash(),
Number: big.NewInt(1),
Digest: digest,
}
err = state.Block.AddBlock(&types.Block{
Header: *header,
Header: header,
Body: types.Body{},
})
require.NoError(t, err)
Expand Down Expand Up @@ -369,60 +370,48 @@ func newTestStateService(t *testing.T) *state.Service {
rt, err := wasmer.NewRuntimeFromGenesis(rtCfg)
require.NoError(t, err)

err = loadTestBlocks(t, genesisHeader.Hash(), stateSrvc.Block, rt)
require.NoError(t, err)
loadTestBlocks(t, genesisHeader.Hash(), stateSrvc.Block, rt)

t.Cleanup(func() {
stateSrvc.Stop()
})
return stateSrvc
}

func loadTestBlocks(t *testing.T, gh common.Hash, bs *state.BlockState, rt runtime.Instance) error {
// Create header
header0 := &types.Header{
Number: big.NewInt(0),
func loadTestBlocks(t *testing.T, gh common.Hash, bs *state.BlockState, rt runtime.Instance) {
header1 := &types.Header{
Number: big.NewInt(1),
Digest: types.NewDigest(),
ParentHash: gh,
StateRoot: trie.EmptyHash,
}
// Create blockHash
blockHash0 := header0.Hash()
block0 := &types.Block{
Header: *header0,
Body: sampleBodyBytes,
}

err := bs.AddBlock(block0)
if err != nil {
return err
block1 := &types.Block{
Header: *header1,
Body: sampleBodyBytes,
}

bs.StoreRuntime(block0.Header.Hash(), rt)
err := bs.AddBlock(block1)
require.NoError(t, err)
bs.StoreRuntime(header1.Hash(), rt)

// Create header & blockData for block 1
digest := types.NewDigest()
err = digest.Add(*types.NewBabeSecondaryPlainPreDigest(0, 1).ToPreRuntimeDigest())
require.NoError(t, err)
header1 := &types.Header{
Number: big.NewInt(1),

header2 := &types.Header{
Number: big.NewInt(2),
Digest: digest,
ParentHash: blockHash0,
ParentHash: header1.Hash(),
StateRoot: trie.EmptyHash,
}

block1 := &types.Block{
Header: *header1,
block2 := &types.Block{
Header: *header2,
Body: sampleBodyBytes,
}

// Add the block1 to the DB
err = bs.AddBlock(block1)
if err != nil {
return err
}

bs.StoreRuntime(block1.Header.Hash(), rt)

return nil
err = bs.AddBlock(block2)
require.NoError(t, err)
bs.StoreRuntime(header2.Hash(), rt)
}
2 changes: 1 addition & 1 deletion dot/rpc/modules/dev_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ func newState(t *testing.T) (*state.BlockState, *state.EpochState) {
_, _, genesisHeader := genesis.NewTestGenesisWithTrieAndHeader(t)
bs, err := state.NewBlockStateFromGenesis(db, genesisHeader)
require.NoError(t, err)
es, err := state.NewEpochStateFromGenesis(db, genesisBABEConfig)
es, err := state.NewEpochStateFromGenesis(db, bs, genesisBABEConfig)
require.NoError(t, err)
return bs, es
}
Expand Down
4 changes: 2 additions & 2 deletions dot/rpc/modules/state_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -543,7 +543,7 @@ func setupStateModule(t *testing.T) (*StateModule, *common.Hash, *common.Hash) {
b := &types.Block{
Header: types.Header{
ParentHash: chain.Block.BestBlockHash(),
Number: big.NewInt(2),
Number: big.NewInt(3),
StateRoot: sr1,
},
Body: *types.NewBody([]types.Extrinsic{[]byte{}}),
Expand All @@ -557,7 +557,7 @@ func setupStateModule(t *testing.T) (*StateModule, *common.Hash, *common.Hash) {

chain.Block.StoreRuntime(b.Header.Hash(), rt)

hash, _ := chain.Block.GetBlockHash(big.NewInt(2))
hash, _ := chain.Block.GetBlockHash(big.NewInt(3))
core := newCoreService(t, chain)
return NewStateModule(net, chain.Storage, core), &hash, &sr1
}
2 changes: 1 addition & 1 deletion dot/rpc/modules/system_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -308,7 +308,7 @@ func setupSystemModule(t *testing.T) *SystemModule {
require.NoError(t, err)
err = chain.Block.AddBlock(&types.Block{
Header: types.Header{
Number: big.NewInt(1),
Number: big.NewInt(3),
ParentHash: chain.Block.BestBlockHash(),
StateRoot: ts.MustRoot(),
},
Expand Down
12 changes: 0 additions & 12 deletions dot/services.go
Original file line number Diff line number Diff line change
Expand Up @@ -74,18 +74,6 @@ func createStateService(cfg *Config) (*state.Service, error) {
}
}

// load most recent state from database
latestState, err := stateSrvc.Base.LoadLatestStorageHash()
if err != nil {
return nil, fmt.Errorf("failed to load latest state root hash: %s", err)
}

// load most recent state from database
_, err = stateSrvc.Storage.LoadFromDB(latestState)
if err != nil {
return nil, fmt.Errorf("failed to load latest state from database: %s", err)
}

return stateSrvc, nil
}

Expand Down
30 changes: 0 additions & 30 deletions dot/state/base.go
Original file line number Diff line number Diff line change
Expand Up @@ -54,21 +54,6 @@ func (s *BaseState) LoadNodeGlobalName() (string, error) {
return string(nodeName), nil
}

// StoreBestBlockHash stores the hash at the BestBlockHashKey
func (s *BaseState) StoreBestBlockHash(hash common.Hash) error {
return s.db.Put(common.BestBlockHashKey, hash[:])
}

// LoadBestBlockHash loads the hash stored at BestBlockHashKey
func (s *BaseState) LoadBestBlockHash() (common.Hash, error) {
hash, err := s.db.Get(common.BestBlockHashKey)
if err != nil {
return common.Hash{}, err
}

return common.NewHash(hash), nil
}

// StoreGenesisData stores the given genesis data at the known GenesisDataKey.
func (s *BaseState) StoreGenesisData(gen *genesis.Data) error {
enc, err := json.Marshal(gen)
Expand All @@ -95,21 +80,6 @@ func (s *BaseState) LoadGenesisData() (*genesis.Data, error) {
return data, nil
}

// StoreLatestStorageHash stores the current root hash in the database at LatestStorageHashKey
func (s *BaseState) StoreLatestStorageHash(root common.Hash) error {
return s.db.Put(common.LatestStorageHashKey, root[:])
}

// LoadLatestStorageHash retrieves the hash stored at LatestStorageHashKey from the DB
func (s *BaseState) LoadLatestStorageHash() (common.Hash, error) {
hashbytes, err := s.db.Get(common.LatestStorageHashKey)
if err != nil {
return common.Hash{}, err
}

return common.NewHash(hashbytes), nil
}

// StoreCodeSubstitutedBlockHash stores the hash at the CodeSubstitutedBlock key
func (s *BaseState) StoreCodeSubstitutedBlockHash(hash common.Hash) error {
return s.db.Put(common.CodeSubstitutedBlock, hash[:])
Expand Down
50 changes: 0 additions & 50 deletions dot/state/base_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -39,42 +39,6 @@ func TestTrie_StoreAndLoadFromDB(t *testing.T) {
require.Equal(t, expected, tt.MustHash())
}

type test struct {
key []byte
value []byte
}

func TestStoreAndLoadLatestStorageHash(t *testing.T) {
db := NewInMemoryDB(t)
base := NewBaseState(db)
tt := trie.NewEmptyTrie()

tests := []test{
{key: []byte{0x01, 0x35}, value: []byte("pen")},
{key: []byte{0x01, 0x35, 0x79}, value: []byte("penguin")},
{key: []byte{0x01, 0x35, 0x7}, value: []byte("g")},
{key: []byte{0xf2}, value: []byte("feather")},
{key: []byte{0xf2, 0x3}, value: []byte("f")},
{key: []byte{0x09, 0xd3}, value: []byte("noot")},
{key: []byte{0x07}, value: []byte("ramen")},
{key: []byte{0}, value: nil},
}

for _, test := range tests {
tt.Put(test.key, test.value)
}

expected, err := tt.Hash()
require.NoError(t, err)

err = base.StoreLatestStorageHash(expected)
require.NoError(t, err)

hash, err := base.LoadLatestStorageHash()
require.NoError(t, err)
require.Equal(t, expected, hash)
}

func TestStoreAndLoadGenesisData(t *testing.T) {
db := NewInMemoryDB(t)
base := NewBaseState(db)
Expand All @@ -99,20 +63,6 @@ func TestStoreAndLoadGenesisData(t *testing.T) {
require.Equal(t, expected, gen)
}

func TestStoreAndLoadBestBlockHash(t *testing.T) {
db := NewInMemoryDB(t)
base := NewBaseState(db)

hash, _ := common.HexToHash("0x3f5a19b9e9507e05276216f3877bb289e47885f8184010c65d0e41580d3663cc")

err := base.StoreBestBlockHash(hash)
require.NoError(t, err)

res, err := base.LoadBestBlockHash()
require.NoError(t, err)
require.Equal(t, hash, res)
}

func TestLoadStoreEpochLength(t *testing.T) {
db := NewInMemoryDB(t)
base := NewBaseState(db)
Expand Down
Loading

0 comments on commit 5e42215

Please sign in to comment.