github.com/prysmaticlabs/prysm@v1.4.4/slasher/db/kv/block_header_test.go (about) 1 package kv 2 3 import ( 4 "context" 5 "testing" 6 7 types "github.com/prysmaticlabs/eth2-types" 8 "github.com/prysmaticlabs/prysm/beacon-chain/core/helpers" 9 ethpb "github.com/prysmaticlabs/prysm/proto/eth/v1alpha1" 10 "github.com/prysmaticlabs/prysm/shared/bytesutil" 11 "github.com/prysmaticlabs/prysm/shared/params" 12 "github.com/prysmaticlabs/prysm/shared/testutil/assert" 13 "github.com/prysmaticlabs/prysm/shared/testutil/require" 14 ) 15 16 func TestNilDBHistoryBlkHdr(t *testing.T) { 17 db := setupDB(t) 18 ctx := context.Background() 19 20 slot := types.Slot(1) 21 validatorIndex := types.ValidatorIndex(1) 22 23 require.Equal(t, false, db.HasBlockHeader(ctx, slot, validatorIndex)) 24 25 bPrime, err := db.BlockHeaders(ctx, slot, validatorIndex) 26 require.NoError(t, err, "Failed to get block") 27 require.DeepEqual(t, []*ethpb.SignedBeaconBlockHeader(nil), bPrime, "Should return nil for a non existent key") 28 } 29 30 func TestSaveHistoryBlkHdr(t *testing.T) { 31 db := setupDB(t) 32 ctx := context.Background() 33 34 tests := []struct { 35 bh *ethpb.SignedBeaconBlockHeader 36 }{ 37 { 38 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in"), 96), Header: ðpb.BeaconBlockHeader{Slot: 0, ProposerIndex: 0}}, 39 }, 40 { 41 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in 2nd"), 96), Header: ðpb.BeaconBlockHeader{Slot: 0, ProposerIndex: 1}}, 42 }, 43 { 44 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in 3rd"), 96), Header: ðpb.BeaconBlockHeader{Slot: params.BeaconConfig().SlotsPerEpoch + 1, ProposerIndex: 0}}, 45 }, 46 { 47 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in 3rd"), 96), Header: ðpb.BeaconBlockHeader{Slot: 1, ProposerIndex: 0}}, 48 }, 49 } 50 51 for _, tt := range tests { 52 err := db.SaveBlockHeader(ctx, tt.bh) 53 require.NoError(t, err, "Save block failed") 54 55 bha, err := db.BlockHeaders(ctx, tt.bh.Header.Slot, tt.bh.Header.ProposerIndex) 56 require.NoError(t, err, "Failed to get block") 57 require.NotNil(t, bha) 58 require.DeepEqual(t, tt.bh, bha[0], "Should return bh") 59 } 60 } 61 62 func TestDeleteHistoryBlkHdr(t *testing.T) { 63 db := setupDB(t) 64 ctx := context.Background() 65 66 tests := []struct { 67 bh *ethpb.SignedBeaconBlockHeader 68 }{ 69 { 70 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in"), 96), Header: ðpb.BeaconBlockHeader{Slot: 0, ProposerIndex: 0}}, 71 }, 72 { 73 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in 2nd"), 96), Header: ðpb.BeaconBlockHeader{Slot: 0, ProposerIndex: 1}}, 74 }, 75 { 76 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in 3rd"), 96), Header: ðpb.BeaconBlockHeader{Slot: params.BeaconConfig().SlotsPerEpoch + 1, ProposerIndex: 0}}, 77 }, 78 } 79 for _, tt := range tests { 80 err := db.SaveBlockHeader(ctx, tt.bh) 81 require.NoError(t, err, "Save block failed") 82 } 83 84 for _, tt := range tests { 85 bha, err := db.BlockHeaders(ctx, tt.bh.Header.Slot, tt.bh.Header.ProposerIndex) 86 require.NoError(t, err, "Failed to get block") 87 require.NotNil(t, bha) 88 require.DeepEqual(t, tt.bh, bha[0], "Should return bh") 89 90 err = db.DeleteBlockHeader(ctx, tt.bh) 91 require.NoError(t, err, "Save block failed") 92 bh, err := db.BlockHeaders(ctx, tt.bh.Header.Slot, tt.bh.Header.ProposerIndex) 93 require.NoError(t, err) 94 assert.DeepEqual(t, []*ethpb.SignedBeaconBlockHeader(nil), bh, "Expected block to have been deleted") 95 } 96 } 97 98 func TestHasHistoryBlkHdr(t *testing.T) { 99 db := setupDB(t) 100 ctx := context.Background() 101 102 tests := []struct { 103 bh *ethpb.SignedBeaconBlockHeader 104 }{ 105 { 106 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in"), 96), Header: ðpb.BeaconBlockHeader{Slot: 0, ProposerIndex: 0}}, 107 }, 108 { 109 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in 2nd"), 96), Header: ðpb.BeaconBlockHeader{Slot: 0, ProposerIndex: 1}}, 110 }, 111 { 112 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in 3rd"), 96), Header: ðpb.BeaconBlockHeader{Slot: params.BeaconConfig().SlotsPerEpoch + 1, ProposerIndex: 0}}, 113 }, 114 { 115 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in 4th"), 96), Header: ðpb.BeaconBlockHeader{Slot: 1, ProposerIndex: 0}}, 116 }, 117 } 118 for _, tt := range tests { 119 found := db.HasBlockHeader(ctx, tt.bh.Header.Slot, tt.bh.Header.ProposerIndex) 120 require.Equal(t, false, found, "has block header should return false for block headers that are not in db") 121 err := db.SaveBlockHeader(ctx, tt.bh) 122 require.NoError(t, err, "Save block failed") 123 } 124 for _, tt := range tests { 125 err := db.SaveBlockHeader(ctx, tt.bh) 126 require.NoError(t, err, "Save block failed") 127 128 found := db.HasBlockHeader(ctx, tt.bh.Header.Slot, tt.bh.Header.ProposerIndex) 129 require.Equal(t, true, found, "Block header should exist") 130 } 131 } 132 133 func TestPruneHistoryBlkHdr(t *testing.T) { 134 db := setupDB(t) 135 ctx := context.Background() 136 137 tests := []struct { 138 bh *ethpb.SignedBeaconBlockHeader 139 }{ 140 { 141 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in"), 96), Header: ðpb.BeaconBlockHeader{Slot: 0, ProposerIndex: 0}}, 142 }, 143 { 144 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in 2nd"), 96), Header: ðpb.BeaconBlockHeader{Slot: 0, ProposerIndex: 1}}, 145 }, 146 { 147 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in 3rd"), 96), Header: ðpb.BeaconBlockHeader{Slot: params.BeaconConfig().SlotsPerEpoch + 1, ProposerIndex: 0}}, 148 }, 149 { 150 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in 4th"), 96), Header: ðpb.BeaconBlockHeader{Slot: params.BeaconConfig().SlotsPerEpoch*2 + 1, ProposerIndex: 0}}, 151 }, 152 { 153 bh: ðpb.SignedBeaconBlockHeader{Signature: bytesutil.PadTo([]byte("let me in 5th"), 96), Header: ðpb.BeaconBlockHeader{Slot: params.BeaconConfig().SlotsPerEpoch*3 + 1, ProposerIndex: 0}}, 154 }, 155 } 156 157 for _, tt := range tests { 158 err := db.SaveBlockHeader(ctx, tt.bh) 159 require.NoError(t, err, "Save block header failed") 160 161 bha, err := db.BlockHeaders(ctx, tt.bh.Header.Slot, tt.bh.Header.ProposerIndex) 162 require.NoError(t, err, "Failed to get block header") 163 require.NotNil(t, bha) 164 require.DeepEqual(t, tt.bh, bha[0], "Should return bh") 165 } 166 currentEpoch := types.Epoch(3) 167 historyToKeep := types.Epoch(2) 168 err := db.PruneBlockHistory(ctx, currentEpoch, historyToKeep) 169 require.NoError(t, err, "Failed to prune") 170 171 for _, tt := range tests { 172 bha, err := db.BlockHeaders(ctx, tt.bh.Header.Slot, tt.bh.Header.ProposerIndex) 173 require.NoError(t, err, "Failed to get block header") 174 if helpers.SlotToEpoch(tt.bh.Header.Slot) >= currentEpoch-historyToKeep { 175 require.NotNil(t, bha) 176 require.DeepEqual(t, tt.bh, bha[0], "Should return bh") 177 } else { 178 require.Equal(t, 0, len(bha), "Block header should have been pruned") 179 require.DeepEqual(t, []*ethpb.SignedBeaconBlockHeader(nil), bha, "Block header should have been pruned") 180 } 181 } 182 }