@@ -16,12 +16,14 @@ import (
1616 "github.com/bilinearlabs/eth-metrics/config"
1717 "github.com/ethereum/go-ethereum/core/types"
1818 "github.com/ethereum/go-ethereum/ethclient"
19+ "github.com/ethereum/go-ethereum/rlp"
1920 "github.com/pkg/errors"
2021 log "github.com/sirupsen/logrus"
2122)
2223
2324type EpochBlockData struct {
24- Withdrawals map [uint64 ]* big.Int
25+ Withdrawals map [uint64 ]* big.Int
26+ ProposerTips map [uint64 ]* big.Int
2527}
2628
2729type BlockData struct {
@@ -49,7 +51,8 @@ func (b *BlockData) GetEpochBlockData(epoch uint64) (*EpochBlockData, error) {
4951 log .Info ("Fetching block data for epoch: " , epoch )
5052
5153 data := & EpochBlockData {
52- Withdrawals : make (map [uint64 ]* big.Int ),
54+ Withdrawals : make (map [uint64 ]* big.Int ),
55+ ProposerTips : make (map [uint64 ]* big.Int ),
5356 }
5457
5558 firstSlot := epoch * b .networkParameters .slotsInEpoch
@@ -76,12 +79,16 @@ func (b *BlockData) GetEpochBlockData(epoch uint64) (*EpochBlockData, error) {
7679
7780 b .extractWithdrawals (block , data .Withdrawals )
7881
79- // Extract transaction fees (add when needed)
82+ // Extract transaction fees
8083 proposerTip , err := b .GetProposerTip (block )
8184 if err != nil {
8285 return nil , errors .Wrap (err , "error getting proposer tip" )
8386 }
84- // TODO get proposer index of this block and add to data
87+ proposerIndex := b .GetProposerIndex (block )
88+ if _ , ok := data .ProposerTips [proposerIndex ]; ! ok {
89+ data .ProposerTips [proposerIndex ] = big .NewInt (0 )
90+ }
91+ data .ProposerTips [proposerIndex ].Add (data .ProposerTips [proposerIndex ], proposerTip )
8592 }
8693
8794 return data , nil
@@ -101,27 +108,36 @@ func (b *BlockData) extractWithdrawals(beaconBlock *spec.VersionedSignedBeaconBl
101108func (b * BlockData ) GetProposerTip (beaconBlock * spec.VersionedSignedBeaconBlock ) (* big.Int , error ) {
102109 blockNumber := b .GetBlockNumber (beaconBlock )
103110 rawTxs := b .GetBlockTransactions (beaconBlock )
104- header , receipts , err := b .getBlockHeaderAndReceipts (blockNumber , rawTxs )
111+ retryOpts := []retry.Option {
112+ retry .Attempts (5 ),
113+ retry .Delay (5 * time .Second ),
114+ }
115+ header , err := b .getBlockHeader (blockNumber , retryOpts )
105116 if err != nil {
106117 return nil , errors .Wrap (err , "error getting block header and receipts" )
107118 }
108119 baseFeePerGasBytes := b .GetBaseFeePerGas (beaconBlock )
109120 baseFeePerGas := new (big.Int ).SetBytes (baseFeePerGasBytes [:])
110121
111122 tips := big .NewInt (0 )
112- for i , rawTx := range rawTxs {
113- var tx * types.Transaction
114- err = tx .UnmarshalBinary (rawTx )
123+ for _ , rawTx := range rawTxs {
124+ println (rawTx )
125+ txReceipt , err := b .getTransactionReceipt (rawTx , retryOpts )
126+ if err != nil {
127+ return nil , errors .Wrap (err , "error getting block receipt" )
128+ }
129+ var tx types.Transaction
130+ err = rlp .DecodeBytes (rawTx , & tx )
115131 if err != nil {
116132 return nil , errors .Wrap (err , "error unmarshalling transaction" )
117133 }
118- if tx .Hash () != receipts [ i ] .TxHash {
134+ if tx .Hash () != txReceipt .TxHash {
119135 return nil , errors .New ("transaction hash mismatch" )
120136 }
121137
122138 tipFee := new (big.Int )
123139 gasPrice := tx .GasPrice ()
124- gasUsed := big .NewInt (int64 (receipts [ i ] .GasUsed ))
140+ gasUsed := big .NewInt (int64 (txReceipt .GasUsed ))
125141
126142 switch tx .Type () {
127143 case 0 , 1 :
@@ -139,25 +155,21 @@ func (b *BlockData) GetProposerTip(beaconBlock *spec.VersionedSignedBeaconBlock)
139155 default :
140156 return nil , errors .Errorf ("unknown transaction type: %d, hash: %s" , tx .Type (), tx .Hash ().String ())
141157 }
158+ tips .Add (tips , tipFee )
142159 }
143160 burnt := new (big.Int ).Mul (big .NewInt (int64 (b .GetGasUsed (beaconBlock ))), baseFeePerGas )
144161 proposerReward := new (big.Int ).Sub (tips , burnt )
145162 return proposerReward , nil
146163}
147164
148- func (b * BlockData ) getBlockHeaderAndReceipts (
165+ func (b * BlockData ) getBlockHeader (
149166 blockNumber uint64 ,
150- rawTxs []bellatrix.Transaction ,
151- ) (* types.Header , []* types.Receipt , error ) {
152-
167+ retryOpts []retry.Option ,
168+ ) (* types.Header , error ) {
153169 var header * types.Header
154170 var err error
155171
156172 blockNumberBig := new (big.Int ).SetUint64 (blockNumber )
157- retryOpts := []retry.Option {
158- retry .Attempts (5 ),
159- retry .Delay (5 * time .Second ),
160- }
161173
162174 err = retry .Do (func () error {
163175 header , err = b .executionClient .HeaderByNumber (context .Background (), blockNumberBig )
@@ -168,32 +180,33 @@ func (b *BlockData) getBlockHeaderAndReceipts(
168180 return nil
169181 }, retryOpts ... )
170182 if err != nil {
171- return nil , nil , errors .Wrap (err , "error getting header for block " + blockNumberBig .String ())
183+ return nil , errors .Wrap (err , "error getting header for block " + blockNumberBig .String ())
172184 }
173185
174- var receipts []* types.Receipt = make ([]* types.Receipt , 0 )
175- for _ , rawTx := range rawTxs {
176- var tx * types.Transaction
177- err = tx .UnmarshalBinary (rawTx )
178- if err != nil {
179- return nil , nil , errors .Wrap (err , "error unmarshalling transaction" )
180- }
181- var receipt * types.Receipt
182- err = retry .Do (func () error {
183- receipt , err = b .executionClient .TransactionReceipt (context .Background (), tx .Hash ())
184- if err != nil {
185- log .Warnf ("error getting transaction receipt for tx %s: %s. Retrying..." , tx .Hash ().String (), err )
186- return errors .Wrap (err , "error getting transaction receipt for block" )
187- }
188- return nil
189- }, retryOpts ... )
186+ return header , nil
187+ }
188+
189+ func (b * BlockData ) getTransactionReceipt (rawTx []byte , retryOpts []retry.Option ) (* types.Receipt , error ) {
190+ var tx types.Transaction
191+ err := tx .UnmarshalBinary (rawTx )
192+ if err != nil {
193+ return nil , errors .Wrap (err , "error unmarshalling transaction" )
194+ }
195+ var receipt * types.Receipt
196+ err = retry .Do (func () error {
197+ receipt , err = b .executionClient .TransactionReceipt (context .Background (), tx .Hash ())
190198 if err != nil {
191- return nil , nil , errors .Wrap (err , "error getting transaction receipt for block " + blockNumberBig .String ())
199+ log .Warnf ("error getting transaction receipt for tx %s: %s. Retrying..." , tx .Hash ().String (), err )
200+ return errors .Wrap (err , "error getting transaction receipt" )
192201 }
193- receipts = append (receipts , receipt )
202+ return nil
203+ }, retryOpts ... )
204+
205+ if err != nil {
206+ return nil , errors .Wrap (err , "error getting transaction receipt for tx " + tx .Hash ().String ())
194207 }
195208
196- return header , receipts , nil
209+ return receipt , nil
197210}
198211
199212func (b * BlockData ) GetBlockWithdrawals (beaconBlock * spec.VersionedSignedBeaconBlock ) []* capella.Withdrawal {
@@ -304,3 +317,23 @@ func (b *BlockData) GetGasUsed(beaconBlock *spec.VersionedSignedBeaconBlock) uin
304317 }
305318 return gasUsed
306319}
320+
321+ func (b * BlockData ) GetProposerIndex (beaconBlock * spec.VersionedSignedBeaconBlock ) uint64 {
322+ var proposerIndex uint64
323+ if beaconBlock .Altair != nil {
324+ proposerIndex = uint64 (beaconBlock .Altair .Message .ProposerIndex )
325+ } else if beaconBlock .Bellatrix != nil {
326+ proposerIndex = uint64 (beaconBlock .Bellatrix .Message .ProposerIndex )
327+ } else if beaconBlock .Capella != nil {
328+ proposerIndex = uint64 (beaconBlock .Capella .Message .ProposerIndex )
329+ } else if beaconBlock .Deneb != nil {
330+ proposerIndex = uint64 (beaconBlock .Deneb .Message .ProposerIndex )
331+ } else if beaconBlock .Electra != nil {
332+ proposerIndex = uint64 (beaconBlock .Electra .Message .ProposerIndex )
333+ } else if beaconBlock .Fulu != nil {
334+ proposerIndex = uint64 (beaconBlock .Fulu .Message .ProposerIndex )
335+ } else {
336+ log .Fatal ("Beacon block was empty" )
337+ }
338+ return proposerIndex
339+ }
0 commit comments