Skip to content

Commit

Permalink
Add redis and database tests to store deneb payloads
Browse files Browse the repository at this point in the history
  • Loading branch information
avalonche committed Jan 4, 2024
1 parent 281bd86 commit b97138c
Show file tree
Hide file tree
Showing 11 changed files with 271 additions and 37 deletions.
14 changes: 12 additions & 2 deletions common/types_spec.go
Original file line number Diff line number Diff line change
Expand Up @@ -86,13 +86,23 @@ func BuildGetHeaderResponse(payload *VersionedSubmitBlockRequest, sk *bls.Secret
}

func BuildGetPayloadResponse(payload *VersionedSubmitBlockRequest) (*api.VersionedSubmitBlindedBlockResponse, error) {
if payload.Capella != nil {
switch payload.Version {
case consensusspec.DataVersionCapella:
return &api.VersionedSubmitBlindedBlockResponse{
Version: consensusspec.DataVersionCapella,
Capella: payload.Capella.ExecutionPayload,
}, nil
case consensusspec.DataVersionDeneb:
return &api.VersionedSubmitBlindedBlockResponse{
Version: consensusspec.DataVersionDeneb,
Deneb: &deneb.ExecutionPayloadAndBlobsBundle{
ExecutionPayload: payload.Deneb.ExecutionPayload,
BlobsBundle: payload.Deneb.BlobsBundle,
},
}, nil
case consensusspec.DataVersionUnknown, consensusspec.DataVersionPhase0, consensusspec.DataVersionAltair, consensusspec.DataVersionBellatrix:
return nil, ErrInvalidVersion
}

return nil, ErrEmptyPayload
}

Expand Down
48 changes: 48 additions & 0 deletions common/types_spec_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,14 @@ import (
"encoding/json"
"testing"

"github.com/attestantio/go-builder-client/api/deneb"
apiv1 "github.com/attestantio/go-builder-client/api/v1"
spec "github.com/attestantio/go-builder-client/spec"
consensusspec "github.com/attestantio/go-eth2-client/spec"
"github.com/attestantio/go-eth2-client/spec/bellatrix"
denebspec "github.com/attestantio/go-eth2-client/spec/deneb"
"github.com/attestantio/go-eth2-client/spec/phase0"
"github.com/holiman/uint256"
"github.com/stretchr/testify/require"
)

Expand Down Expand Up @@ -58,3 +66,43 @@ func TestSignedBlindedBlockJSON(t *testing.T) {

require.Equal(t, expectedJSONBytes, bytes.ToLower(marshalledJSONBytes))
}

func TestBuildGetPayloadResponse(t *testing.T) {
t.Run("Capella", func(t *testing.T) {
jsonBytes := LoadGzippedBytes(t, "../testdata/submitBlockPayloadCapella_Goerli.json.gz")

submitBlockData := new(VersionedSubmitBlockRequest)
err := json.Unmarshal(jsonBytes, &submitBlockData)
require.NoError(t, err)

resp, err := BuildGetPayloadResponse(submitBlockData)
require.NoError(t, err)

require.Equal(t, consensusspec.DataVersionCapella, resp.Version)
require.Equal(t, "0x1bafdc454116b605005364976b134d761dd736cb4788d25c835783b46daeb121", resp.Capella.BlockHash.String())
})

t.Run("Deneb", func(t *testing.T) {
// TODO: (deneb) add block request from goerli / devnet
submitBlockData := &VersionedSubmitBlockRequest{
VersionedSubmitBlockRequest: spec.VersionedSubmitBlockRequest{
Version: consensusspec.DataVersionDeneb,
Deneb: &deneb.SubmitBlockRequest{
ExecutionPayload: &denebspec.ExecutionPayload{
BaseFeePerGas: uint256.NewInt(123),
BlockHash: phase0.Hash32{0x09},
Transactions: []bellatrix.Transaction{},
},
BlobsBundle: &deneb.BlobsBundle{},
Message: &apiv1.BidTrace{},
},
},
}

resp, err := BuildGetPayloadResponse(submitBlockData)
require.NoError(t, err)

require.Equal(t, consensusspec.DataVersionDeneb, resp.Version)
require.Equal(t, "0x0900000000000000000000000000000000000000000000000000000000000000", resp.Deneb.ExecutionPayload.BlockHash.String())
})
}
51 changes: 38 additions & 13 deletions common/utils.go
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ import (
"github.com/attestantio/go-builder-client/spec"
consensusspec "github.com/attestantio/go-eth2-client/spec"
capellaspec "github.com/attestantio/go-eth2-client/spec/capella"
denebspec "github.com/attestantio/go-eth2-client/spec/deneb"
"github.com/attestantio/go-eth2-client/spec/phase0"
ethcommon "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/common/hexutil"
Expand Down Expand Up @@ -181,6 +182,7 @@ type CreateTestBlockSubmissionOpts struct {
relayPk phase0.BLSPubKey
domain phase0.Domain

Version consensusspec.DataVersion
Slot uint64
ParentHash string
ProposerPubkey string
Expand All @@ -196,6 +198,7 @@ func CreateTestBlockSubmission(t *testing.T, builderPubkey string, value *uint25
domain := phase0.Domain{}
proposerPk := phase0.BLSPubKey{}
parentHash := phase0.Hash32{}
version := consensusspec.DataVersionCapella

if opts != nil {
relaySk = opts.relaySk
Expand All @@ -212,26 +215,48 @@ func CreateTestBlockSubmission(t *testing.T, builderPubkey string, value *uint25
parentHash, err = StrToPhase0Hash(opts.ParentHash)
require.NoError(t, err)
}

if opts.Version != consensusspec.DataVersionUnknown {
version = opts.Version
}
}

builderPk, err := StrToPhase0Pubkey(builderPubkey)
require.NoError(t, err)

payload = &VersionedSubmitBlockRequest{
VersionedSubmitBlockRequest: spec.VersionedSubmitBlockRequest{ //nolint:exhaustruct
Version: consensusspec.DataVersionCapella,
Capella: &capella.SubmitBlockRequest{
Message: &apiv1.BidTrace{ //nolint:exhaustruct
BuilderPubkey: builderPk,
Value: value,
Slot: slot,
ParentHash: parentHash,
ProposerPubkey: proposerPk,
bidTrace := &apiv1.BidTrace{ //nolint:exhaustruct
BuilderPubkey: builderPk,
Value: value,
Slot: slot,
ParentHash: parentHash,
ProposerPubkey: proposerPk,
}

if version == consensusspec.DataVersionDeneb {
payload = &VersionedSubmitBlockRequest{
VersionedSubmitBlockRequest: spec.VersionedSubmitBlockRequest{ //nolint:exhaustruct
Version: version,
Deneb: &deneb.SubmitBlockRequest{
Message: bidTrace,
ExecutionPayload: &denebspec.ExecutionPayload{ //nolint:exhaustruct
BaseFeePerGas: uint256.NewInt(0),
},
BlobsBundle: &deneb.BlobsBundle{}, //nolint:exhaustruct
Signature: phase0.BLSSignature{},
},
},
}
} else {
payload = &VersionedSubmitBlockRequest{
VersionedSubmitBlockRequest: spec.VersionedSubmitBlockRequest{ //nolint:exhaustruct
Version: version,
Capella: &capella.SubmitBlockRequest{
Message: bidTrace,
ExecutionPayload: &capellaspec.ExecutionPayload{}, //nolint:exhaustruct
Signature: phase0.BLSSignature{},
},
ExecutionPayload: &capellaspec.ExecutionPayload{}, //nolint:exhaustruct
Signature: phase0.BLSSignature{},
},
},
}
}

getHeaderResponse, err = BuildGetHeaderResponse(payload, &relaySk, &relayPk, domain)
Expand Down
2 changes: 1 addition & 1 deletion datastore/datastore.go
Original file line number Diff line number Diff line change
Expand Up @@ -197,7 +197,7 @@ func (ds *Datastore) GetGetPayloadResponse(log *logrus.Entry, slot uint64, propo
_blockHash := strings.ToLower(blockHash)

// 1. try to get from Redis
resp, err := ds.redis.GetExecutionPayloadCapella(slot, _proposerPubkey, _blockHash)
resp, err := ds.redis.GetPayloadContents(slot, _proposerPubkey, _blockHash)
if errors.Is(err, redis.Nil) {
log.WithError(err).Warn("execution payload not found in redis")
} else if err != nil {
Expand Down
29 changes: 29 additions & 0 deletions datastore/datastore_test.go
Original file line number Diff line number Diff line change
@@ -1,11 +1,15 @@
package datastore

import (
"encoding/json"
"testing"

"github.com/alicebob/miniredis/v2"
"github.com/attestantio/go-builder-client/api/deneb"
consensusdeneb "github.com/attestantio/go-eth2-client/spec/deneb"
"github.com/flashbots/mev-boost-relay/common"
"github.com/flashbots/mev-boost-relay/database"
"github.com/holiman/uint256"
"github.com/stretchr/testify/require"
)

Expand Down Expand Up @@ -48,3 +52,28 @@ func TestGetPayloadDatabaseFallback(t *testing.T) {
require.NoError(t, err)
require.Equal(t, "0x1bafdc454116b605005364976b134d761dd736cb4788d25c835783b46daeb121", payload.Capella.BlockHash.String())
}

func TestGetPayloadDatabaseDeneb(t *testing.T) {
// TODO: (deneb) add execution payload and blobs bundle from goerli / devnet
payloadBytes, err := json.Marshal(&deneb.ExecutionPayloadAndBlobsBundle{
ExecutionPayload: &consensusdeneb.ExecutionPayload{
BaseFeePerGas: uint256.NewInt(5),
},
BlobsBundle: &deneb.BlobsBundle{},
})
require.NoError(t, err)

// prepare mock database with execution payload entry
mockDB := &database.MockDB{
ExecPayloads: map[string]*database.ExecutionPayloadEntry{
"1-a-b": {
Version: common.ForkVersionStringDeneb,
Payload: string(payloadBytes),
},
},
}
ds := setupTestDatastore(t, mockDB)
payload, err := ds.GetGetPayloadResponse(common.TestLog, 1, "a", "b")
require.NoError(t, err)
require.Equal(t, "0x5", payload.Deneb.ExecutionPayload.BaseFeePerGas.String())
}
59 changes: 50 additions & 9 deletions datastore/memcached_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,11 +10,13 @@ import (

"github.com/attestantio/go-builder-client/api"
"github.com/attestantio/go-builder-client/api/capella"
"github.com/attestantio/go-builder-client/api/deneb"
apiv1 "github.com/attestantio/go-builder-client/api/v1"
"github.com/attestantio/go-builder-client/spec"
consensusspec "github.com/attestantio/go-eth2-client/spec"
"github.com/attestantio/go-eth2-client/spec/bellatrix"
capellaspec "github.com/attestantio/go-eth2-client/spec/capella"
denebspec "github.com/attestantio/go-eth2-client/spec/deneb"
"github.com/attestantio/go-eth2-client/spec/phase0"
"github.com/ethereum/go-ethereum/common/math"
"github.com/flashbots/go-boost-utils/bls"
Expand All @@ -35,6 +37,47 @@ var (

func testBuilderSubmitBlockRequest(pubkey phase0.BLSPubKey, signature phase0.BLSSignature, version consensusspec.DataVersion) common.VersionedSubmitBlockRequest {
switch version {
case consensusspec.DataVersionDeneb:
return common.VersionedSubmitBlockRequest{
VersionedSubmitBlockRequest: spec.VersionedSubmitBlockRequest{
Version: consensusspec.DataVersionDeneb,
Deneb: &deneb.SubmitBlockRequest{
Signature: signature,
Message: &apiv1.BidTrace{
Slot: 1,
ParentHash: phase0.Hash32{0x01},
BlockHash: phase0.Hash32{0x09},
BuilderPubkey: pubkey,
ProposerPubkey: phase0.BLSPubKey{0x03},
ProposerFeeRecipient: bellatrix.ExecutionAddress{0x04},
Value: uint256.NewInt(123),
GasLimit: 5002,
GasUsed: 5003,
},
ExecutionPayload: &denebspec.ExecutionPayload{
ParentHash: phase0.Hash32{0x01},
FeeRecipient: bellatrix.ExecutionAddress{0x02},
StateRoot: phase0.Root{0x03},
ReceiptsRoot: phase0.Root{0x04},
LogsBloom: [256]byte{0x05},
PrevRandao: phase0.Hash32{0x06},
BlockNumber: 5001,
GasLimit: 5002,
GasUsed: 5003,
Timestamp: 5004,
ExtraData: []byte{0x07},
BaseFeePerGas: uint256.NewInt(123),
BlockHash: phase0.Hash32{0x09},
Transactions: []bellatrix.Transaction{},
},
BlobsBundle: &deneb.BlobsBundle{
Commitments: []denebspec.KzgCommitment{},
Proofs: []denebspec.KzgProof{},
Blobs: []denebspec.Blob{},
},
},
},
}
case consensusspec.DataVersionCapella:
return common.VersionedSubmitBlockRequest{
VersionedSubmitBlockRequest: spec.VersionedSubmitBlockRequest{
Expand Down Expand Up @@ -71,8 +114,6 @@ func testBuilderSubmitBlockRequest(pubkey phase0.BLSPubKey, signature phase0.BLS
},
},
}
case consensusspec.DataVersionDeneb:
fallthrough
case consensusspec.DataVersionUnknown, consensusspec.DataVersionPhase0, consensusspec.DataVersionAltair, consensusspec.DataVersionBellatrix:
fallthrough
default:
Expand Down Expand Up @@ -147,7 +188,7 @@ func TestMemcached(t *testing.T) {
},
{
Description: "Given a valid builder submit block request, we expect to successfully store and retrieve the value from memcached",
Input: testBuilderSubmitBlockRequest(builderPk, builderSk, consensusspec.DataVersionBellatrix),
Input: testBuilderSubmitBlockRequest(builderPk, builderSk, consensusspec.DataVersionCapella),
TestSuite: func(tc *test) func(*testing.T) {
return func(t *testing.T) {
t.Helper()
Expand Down Expand Up @@ -203,7 +244,7 @@ func TestMemcached(t *testing.T) {
},
{
Description: "Given a valid builder submit block request, updates to the same key should overwrite existing entry and return the last written value",
Input: testBuilderSubmitBlockRequest(builderPk, builderSk, consensusspec.DataVersionBellatrix),
Input: testBuilderSubmitBlockRequest(builderPk, builderSk, consensusspec.DataVersionDeneb),
TestSuite: func(tc *test) func(*testing.T) {
return func(t *testing.T) {
t.Helper()
Expand All @@ -225,22 +266,22 @@ func TestMemcached(t *testing.T) {
require.NoError(t, err)
require.Equal(t, len(prev.Capella.Transactions), len(submission.Transactions))

payload.Bellatrix.GasLimit++
require.NotEqual(t, prev.Bellatrix.GasLimit, payload.Bellatrix.GasLimit)
payload.Capella.GasLimit++
require.NotEqual(t, prev.Capella.GasLimit, payload.Capella.GasLimit)

err = mem.SaveExecutionPayload(submission.Slot, submission.Proposer.String(), submission.BlockHash.String(), payload)
require.NoError(t, err)

current, err := mem.GetExecutionPayload(submission.Slot, submission.Proposer.String(), submission.BlockHash.String())
require.NoError(t, err)
require.Equal(t, current.Bellatrix.GasLimit, payload.Bellatrix.GasLimit)
require.NotEqual(t, current.Bellatrix.GasLimit, prev.Bellatrix.GasLimit)
require.Equal(t, current.Capella.GasLimit, payload.Capella.GasLimit)
require.NotEqual(t, current.Capella.GasLimit, prev.Capella.GasLimit)
}
},
},
{
Description: fmt.Sprintf("Given a valid builder submit block request, memcached entry should expire after %d seconds", defaultMemcachedExpirySeconds),
Input: testBuilderSubmitBlockRequest(builderPk, builderSk, consensusspec.DataVersionBellatrix),
Input: testBuilderSubmitBlockRequest(builderPk, builderSk, consensusspec.DataVersionCapella),
TestSuite: func(tc *test) func(*testing.T) {
return func(t *testing.T) {
t.Helper()
Expand Down
Loading

0 comments on commit b97138c

Please sign in to comment.