From be13ad94b1e58b4e5fa5cb52ddc0ed6bf009c68d Mon Sep 17 00:00:00 2001 From: maskpp Date: Wed, 24 Apr 2024 18:13:53 +0800 Subject: [PATCH] one more test --- proposer/proposer.go | 3 +- proposer/proposer_test.go | 78 +++++++++++++++++++++++++++++++++++++++ 2 files changed, 79 insertions(+), 2 deletions(-) diff --git a/proposer/proposer.go b/proposer/proposer.go index dd38e1846..f2aa606e1 100644 --- a/proposer/proposer.go +++ b/proposer/proposer.go @@ -17,7 +17,6 @@ import ( "github.com/ethereum/go-ethereum/crypto" "github.com/ethereum/go-ethereum/log" "github.com/ethereum/go-ethereum/rlp" - "github.com/urfave/cli/v2" "github.com/taikoxyz/taiko-client/bindings" @@ -375,7 +374,7 @@ func (p *Proposer) ProposeTxLists(ctx context.Context, txListsBytes [][]byte) [] // If a transaction is reverted on chain, the error string returned by txSender will like this: // fmt.Errorf("%w purpose: %v hash: %v", ErrTransactionReverted, txPurpose, rcpt.Receipt.TxHash) // Then we try parsing the custom error for more details in log. - if strings.Contains("purpose: ", err.Error()) && strings.Contains("hash: ", err.Error()) { + if strings.Contains(err.Error(), "purpose: ") && strings.Contains(err.Error(), "hash: ") { txHash := strings.Split(err.Error(), "hash: ")[1] receipt, err := p.rpc.L1.TransactionReceipt(ctx, common.HexToHash(txHash)) if err != nil { diff --git a/proposer/proposer_test.go b/proposer/proposer_test.go index 557ef2608..1db83e881 100644 --- a/proposer/proposer_test.go +++ b/proposer/proposer_test.go @@ -3,9 +3,11 @@ package proposer import ( "context" "os" + "strings" "testing" "time" + "github.com/ethereum-optimism/optimism/op-service/eth" "github.com/ethereum-optimism/optimism/op-service/txmgr" "github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common/math" @@ -17,6 +19,7 @@ import ( "github.com/stretchr/testify/suite" "github.com/taikoxyz/taiko-client/bindings" + "github.com/taikoxyz/taiko-client/bindings/encoding" "github.com/taikoxyz/taiko-client/driver/chain_syncer/beaconsync" "github.com/taikoxyz/taiko-client/driver/chain_syncer/blob" "github.com/taikoxyz/taiko-client/driver/state" @@ -25,6 +28,7 @@ import ( "github.com/taikoxyz/taiko-client/internal/utils" "github.com/taikoxyz/taiko-client/pkg/jwt" "github.com/taikoxyz/taiko-client/pkg/rpc" + builder "github.com/taikoxyz/taiko-client/proposer/transaction_builder" ) type ProposerTestSuite struct { @@ -285,6 +289,80 @@ func (s *ProposerTestSuite) TestAssignProverSuccessFirstRound() { s.Equal(fee.Uint64(), s.p.OptimisticTierFee.Uint64()) } +func (s *ProposerTestSuite) TestProposeTxLists() { + p := s.p + ctx := p.ctx + cfg := s.p.Config + + txBuilder := builder.NewBlobTransactionBuilder( + p.rpc, + p.L1ProposerPrivKey, + p.proverSelector, + p.Config.L1BlockBuilderTip, + cfg.TaikoL1Address, + cfg.L2SuggestedFeeRecipient, + cfg.AssignmentHookAddress, + cfg.ProposeBlockTxGasLimit, + cfg.ExtraData, + ) + + emptyTxListBytes, err := rlp.EncodeToBytes(types.Transactions{}) + s.Nil(err) + txListsBytes := [][]byte{emptyTxListBytes} + txCandidates := make([]txmgr.TxCandidate, len(txListsBytes)) + for i, txListBytes := range txListsBytes { + compressedTxListBytes, err := utils.Compress(txListBytes) + if err != nil { + log.Warn("Failed to compress transactions list", "index", i, "error", err) + break + } + + candidate, err := txBuilder.Build( + p.ctx, + p.tierFees, + p.IncludeParentMetaHash, + compressedTxListBytes, + ) + if err != nil { + log.Warn("Failed to build TaikoL1.proposeBlock transaction", "error", err) + break + } + + // trigger the error + candidate.Blobs = []*eth.Blob{} + candidate.GasLimit = 10000000 + + txCandidates[i] = *candidate + } + + // Send the transactions to the TaikoL1 contract, and if any of them fails, try + // to parse the custom error. + errors := p.txSender.SendAndWaitDetailed("proposeBlock", txCandidates...) + for i, err := range errors { + if err == nil { + continue + } + + // If a transaction is reverted on chain, the error string returned by txSender will like this: + // fmt.Errorf("%w purpose: %v hash: %v", ErrTransactionReverted, txPurpose, rcpt.Receipt.TxHash) + // Then we try parsing the custom error for more details in log. + if strings.Contains(err.Error(), "purpose: ") && strings.Contains(err.Error(), "hash: ") { + txHash := strings.Split(err.Error(), "hash: ")[1] + receipt, err := p.rpc.L1.TransactionReceipt(ctx, common.HexToHash(txHash)) + if err != nil { + log.Error("Failed to fetch receipt", "txHash", txHash, "error", err) + continue + } + errors[i] = encoding.TryParsingCustomErrorFromReceipt(ctx, p.rpc.L1, p.proposerAddress, receipt) + } + } + + // confirm errors handled + for _, err := range errors { + s.Equal("L1_BLOB_NOT_AVAILABLE", err.Error()) + } +} + func (s *ProposerTestSuite) TestUpdateProposingTicker() { s.p.ProposeInterval = 1 * time.Hour s.NotPanics(s.p.updateProposingTicker)