diff --git a/beacon-chain/execution/BUILD.bazel b/beacon-chain/execution/BUILD.bazel index 35e1ff8f2e..a1d3a3af0f 100644 --- a/beacon-chain/execution/BUILD.bazel +++ b/beacon-chain/execution/BUILD.bazel @@ -42,6 +42,7 @@ go_library( "//consensus-types/blocks:go_default_library", "//consensus-types/interfaces:go_default_library", "//consensus-types/payload-attribute:go_default_library", + "//consensus-types/primitives:go_default_library", "//container/trie:go_default_library", "//contracts/deposit:go_default_library", "//crypto/hash:go_default_library", diff --git a/beacon-chain/execution/engine_client.go b/beacon-chain/execution/engine_client.go index 8760e757e4..297cfbb31c 100644 --- a/beacon-chain/execution/engine_client.go +++ b/beacon-chain/execution/engine_client.go @@ -20,9 +20,11 @@ import ( "github.com/prysmaticlabs/prysm/v3/consensus-types/blocks" "github.com/prysmaticlabs/prysm/v3/consensus-types/interfaces" payloadattribute "github.com/prysmaticlabs/prysm/v3/consensus-types/payload-attribute" + prysmType "github.com/prysmaticlabs/prysm/v3/consensus-types/primitives" "github.com/prysmaticlabs/prysm/v3/encoding/bytesutil" pb "github.com/prysmaticlabs/prysm/v3/proto/engine/v1" "github.com/prysmaticlabs/prysm/v3/runtime/version" + "github.com/prysmaticlabs/prysm/v3/time/slots" "github.com/sirupsen/logrus" "go.opencensus.io/trace" ) @@ -30,12 +32,16 @@ import ( const ( // NewPayloadMethod v1 request string for JSON-RPC. NewPayloadMethod = "engine_newPayloadV1" + // NewPayloadMethodV2 v2 request string for JSON-RPC. + NewPayloadMethodV2 = "engine_newPayloadV2" // ForkchoiceUpdatedMethod v1 request string for JSON-RPC. ForkchoiceUpdatedMethod = "engine_forkchoiceUpdatedV1" // ForkchoiceUpdatedMethodV2 v2 request string for JSON-RPC. ForkchoiceUpdatedMethodV2 = "engine_forkchoiceUpdatedV2" // GetPayloadMethod v1 request string for JSON-RPC. GetPayloadMethod = "engine_getPayloadV1" + // GetPayloadMethodV2 v2 request string for JSON-RPC. + GetPayloadMethodV2 = "engine_getPayloadV2" // ExchangeTransitionConfigurationMethod v1 request string for JSON-RPC. ExchangeTransitionConfigurationMethod = "engine_exchangeTransitionConfigurationV1" // ExecutionBlockByHashMethod request string for JSON-RPC. @@ -72,7 +78,7 @@ type EngineCaller interface { ForkchoiceUpdated( ctx context.Context, state *pb.ForkchoiceState, attrs payloadattribute.Attributer, ) (*pb.PayloadIDBytes, []byte, error) - GetPayload(ctx context.Context, payloadId [8]byte) (*pb.ExecutionPayload, error) + GetPayload(ctx context.Context, payloadId [8]byte, slot prysmType.Slot) (interfaces.ExecutionData, error) ExchangeTransitionConfiguration( ctx context.Context, cfg *pb.TransitionConfiguration, ) error @@ -80,7 +86,7 @@ type EngineCaller interface { GetTerminalBlockHash(ctx context.Context, transitionTime uint64) ([]byte, bool, error) } -// NewPayload calls the engine_newPayloadV1 method via JSON-RPC. +// NewPayload calls the engine_newPayloadVX method via JSON-RPC. func (s *Service) NewPayload(ctx context.Context, payload interfaces.ExecutionData) ([]byte, error) { ctx, span := trace.StartSpan(ctx, "powchain.engine-api-client.NewPayload") defer span.End() @@ -93,13 +99,28 @@ func (s *Service) NewPayload(ctx context.Context, payload interfaces.ExecutionDa ctx, cancel := context.WithDeadline(ctx, d) defer cancel() result := &pb.PayloadStatus{} - payloadPb, ok := payload.Proto().(*pb.ExecutionPayload) - if !ok { - return nil, errors.New("execution data must be an execution payload") - } - err := s.rpcClient.CallContext(ctx, result, NewPayloadMethod, payloadPb) - if err != nil { - return nil, handleRPCError(err) + + switch payload.Proto().(type) { + case *pb.ExecutionPayload: + payloadPb, ok := payload.Proto().(*pb.ExecutionPayload) + if !ok { + return nil, errors.New("execution data must be a Bellatrix or Capella execution payload") + } + err := s.rpcClient.CallContext(ctx, result, NewPayloadMethod, payloadPb) + if err != nil { + return nil, handleRPCError(err) + } + case *pb.ExecutionPayloadCapella: + payloadPb, ok := payload.Proto().(*pb.ExecutionPayloadCapella) + if !ok { + return nil, errors.New("execution data must be a Capella execution payload") + } + err := s.rpcClient.CallContext(ctx, result, NewPayloadMethodV2, payloadPb) + if err != nil { + return nil, handleRPCError(err) + } + default: + return nil, errors.New("unknown execution data type") } switch result.Status { @@ -174,8 +195,8 @@ func (s *Service) ForkchoiceUpdated( } } -// GetPayload calls the engine_getPayloadV1 method via JSON-RPC. -func (s *Service) GetPayload(ctx context.Context, payloadId [8]byte) (*pb.ExecutionPayload, error) { +// GetPayload calls the engine_getPayloadVX method via JSON-RPC. +func (s *Service) GetPayload(ctx context.Context, payloadId [8]byte, slot prysmType.Slot) (interfaces.ExecutionData, error) { ctx, span := trace.StartSpan(ctx, "powchain.engine-api-client.GetPayload") defer span.End() start := time.Now() @@ -186,9 +207,22 @@ func (s *Service) GetPayload(ctx context.Context, payloadId [8]byte) (*pb.Execut d := time.Now().Add(defaultEngineTimeout) ctx, cancel := context.WithDeadline(ctx, d) defer cancel() + + if slots.ToEpoch(slot) >= params.BeaconConfig().CapellaForkEpoch { + result := &pb.ExecutionPayloadCapella{} + err := s.rpcClient.CallContext(ctx, result, GetPayloadMethodV2, pb.PayloadIDBytes(payloadId)) + if err != nil { + return nil, handleRPCError(err) + } + return blocks.WrappedExecutionPayloadCapella(result) + } + result := &pb.ExecutionPayload{} err := s.rpcClient.CallContext(ctx, result, GetPayloadMethod, pb.PayloadIDBytes(payloadId)) - return result, handleRPCError(err) + if err != nil { + return nil, handleRPCError(err) + } + return blocks.WrappedExecutionPayload(result) } // ExchangeTransitionConfiguration calls the engine_exchangeTransitionConfigurationV1 method via JSON-RPC. diff --git a/beacon-chain/execution/engine_client_test.go b/beacon-chain/execution/engine_client_test.go index eedf06182d..3305fc1b0d 100644 --- a/beacon-chain/execution/engine_client_test.go +++ b/beacon-chain/execution/engine_client_test.go @@ -63,13 +63,30 @@ func TestClient_IPC(t *testing.T) { ctx := context.Background() fix := fixtures() + params.SetupTestConfigCleanup(t) + cfg := params.BeaconConfig().Copy() + cfg.CapellaForkEpoch = 1 + params.OverrideBeaconConfig(cfg) + t.Run(GetPayloadMethod, func(t *testing.T) { want, ok := fix["ExecutionPayload"].(*pb.ExecutionPayload) require.Equal(t, true, ok) payloadId := [8]byte{1} - resp, err := srv.GetPayload(ctx, payloadId) + resp, err := srv.GetPayload(ctx, payloadId, 1) require.NoError(t, err) - require.DeepEqual(t, want, resp) + resPb, err := resp.PbBellatrix() + require.NoError(t, err) + require.DeepEqual(t, want, resPb) + }) + t.Run(GetPayloadMethodV2, func(t *testing.T) { + want, ok := fix["ExecutionPayloadCapella"].(*pb.ExecutionPayloadCapella) + require.Equal(t, true, ok) + payloadId := [8]byte{1} + resp, err := srv.GetPayload(ctx, payloadId, params.BeaconConfig().SlotsPerEpoch) + require.NoError(t, err) + resPb, err := resp.PbCapella() + require.NoError(t, err) + require.DeepEqual(t, want, resPb) }) t.Run(ForkchoiceUpdatedMethod, func(t *testing.T) { want, ok := fix["ForkchoiceUpdatedResponse"].(*ForkchoiceUpdatedResponse) @@ -102,6 +119,17 @@ func TestClient_IPC(t *testing.T) { require.NoError(t, err) require.DeepEqual(t, bytesutil.ToBytes32(want.LatestValidHash), bytesutil.ToBytes32(latestValidHash)) }) + t.Run(NewPayloadMethodV2, func(t *testing.T) { + want, ok := fix["ValidPayloadStatus"].(*pb.PayloadStatus) + require.Equal(t, true, ok) + req, ok := fix["ExecutionPayloadCapella"].(*pb.ExecutionPayloadCapella) + require.Equal(t, true, ok) + wrappedPayload, err := blocks.WrappedExecutionPayloadCapella(req) + require.NoError(t, err) + latestValidHash, err := srv.NewPayload(ctx, wrappedPayload) + require.NoError(t, err) + require.DeepEqual(t, bytesutil.ToBytes32(want.LatestValidHash), bytesutil.ToBytes32(latestValidHash)) + }) t.Run(ExchangeTransitionConfigurationMethod, func(t *testing.T) { want, ok := fix["TransitionConfiguration"].(*pb.TransitionConfiguration) require.Equal(t, true, ok) @@ -129,6 +157,11 @@ func TestClient_HTTP(t *testing.T) { ctx := context.Background() fix := fixtures() + params.SetupTestConfigCleanup(t) + cfg := params.BeaconConfig().Copy() + cfg.CapellaForkEpoch = 1 + params.OverrideBeaconConfig(cfg) + t.Run(GetPayloadMethod, func(t *testing.T) { payloadId := [8]byte{1} want, ok := fix["ExecutionPayload"].(*pb.ExecutionPayload) @@ -167,9 +200,55 @@ func TestClient_HTTP(t *testing.T) { client.rpcClient = rpcClient // We call the RPC method via HTTP and expect a proper result. - resp, err := client.GetPayload(ctx, payloadId) + resp, err := client.GetPayload(ctx, payloadId, 1) require.NoError(t, err) - require.DeepEqual(t, want, resp) + pb, err := resp.PbBellatrix() + require.NoError(t, err) + require.DeepEqual(t, want, pb) + }) + t.Run(GetPayloadMethodV2, func(t *testing.T) { + payloadId := [8]byte{1} + want, ok := fix["ExecutionPayloadCapella"].(*pb.ExecutionPayloadCapella) + require.Equal(t, true, ok) + srv := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { + w.Header().Set("Content-Type", "application/json") + defer func() { + require.NoError(t, r.Body.Close()) + }() + enc, err := io.ReadAll(r.Body) + require.NoError(t, err) + jsonRequestString := string(enc) + + reqArg, err := json.Marshal(pb.PayloadIDBytes(payloadId)) + require.NoError(t, err) + + // We expect the JSON string RPC request contains the right arguments. + require.Equal(t, true, strings.Contains( + jsonRequestString, string(reqArg), + )) + resp := map[string]interface{}{ + "jsonrpc": "2.0", + "id": 1, + "result": want, + } + err = json.NewEncoder(w).Encode(resp) + require.NoError(t, err) + })) + defer srv.Close() + + rpcClient, err := rpc.DialHTTP(srv.URL) + require.NoError(t, err) + defer rpcClient.Close() + + client := &Service{} + client.rpcClient = rpcClient + + // We call the RPC method via HTTP and expect a proper result. + resp, err := client.GetPayload(ctx, payloadId, params.BeaconConfig().SlotsPerEpoch) + require.NoError(t, err) + pb, err := resp.PbCapella() + require.NoError(t, err) + require.DeepEqual(t, want, pb) }) t.Run(ForkchoiceUpdatedMethod+" VALID status", func(t *testing.T) { forkChoiceState := &pb.ForkchoiceState{ @@ -325,6 +404,20 @@ func TestClient_HTTP(t *testing.T) { require.NoError(t, err) require.DeepEqual(t, want.LatestValidHash, resp) }) + t.Run(NewPayloadMethodV2+" VALID status", func(t *testing.T) { + execPayload, ok := fix["ExecutionPayloadCapella"].(*pb.ExecutionPayloadCapella) + require.Equal(t, true, ok) + want, ok := fix["ValidPayloadStatus"].(*pb.PayloadStatus) + require.Equal(t, true, ok) + client := newPayloadV2Setup(t, want, execPayload) + + // We call the RPC method via HTTP and expect a proper result. + wrappedPayload, err := blocks.WrappedExecutionPayloadCapella(execPayload) + require.NoError(t, err) + resp, err := client.NewPayload(ctx, wrappedPayload) + require.NoError(t, err) + require.DeepEqual(t, want.LatestValidHash, resp) + }) t.Run(NewPayloadMethod+" SYNCING status", func(t *testing.T) { execPayload, ok := fix["ExecutionPayload"].(*pb.ExecutionPayload) require.Equal(t, true, ok) @@ -339,6 +432,20 @@ func TestClient_HTTP(t *testing.T) { require.ErrorIs(t, ErrAcceptedSyncingPayloadStatus, err) require.DeepEqual(t, []uint8(nil), resp) }) + t.Run(NewPayloadMethodV2+" SYNCING status", func(t *testing.T) { + execPayload, ok := fix["ExecutionPayloadCapella"].(*pb.ExecutionPayloadCapella) + require.Equal(t, true, ok) + want, ok := fix["SyncingStatus"].(*pb.PayloadStatus) + require.Equal(t, true, ok) + client := newPayloadV2Setup(t, want, execPayload) + + // We call the RPC method via HTTP and expect a proper result. + wrappedPayload, err := blocks.WrappedExecutionPayloadCapella(execPayload) + require.NoError(t, err) + resp, err := client.NewPayload(ctx, wrappedPayload) + require.ErrorIs(t, ErrAcceptedSyncingPayloadStatus, err) + require.DeepEqual(t, []uint8(nil), resp) + }) t.Run(NewPayloadMethod+" INVALID_BLOCK_HASH status", func(t *testing.T) { execPayload, ok := fix["ExecutionPayload"].(*pb.ExecutionPayload) require.Equal(t, true, ok) @@ -353,6 +460,20 @@ func TestClient_HTTP(t *testing.T) { require.ErrorIs(t, ErrInvalidBlockHashPayloadStatus, err) require.DeepEqual(t, []uint8(nil), resp) }) + t.Run(NewPayloadMethodV2+" INVALID_BLOCK_HASH status", func(t *testing.T) { + execPayload, ok := fix["ExecutionPayloadCapella"].(*pb.ExecutionPayloadCapella) + require.Equal(t, true, ok) + want, ok := fix["InvalidBlockHashStatus"].(*pb.PayloadStatus) + require.Equal(t, true, ok) + client := newPayloadV2Setup(t, want, execPayload) + + // We call the RPC method via HTTP and expect a proper result. + wrappedPayload, err := blocks.WrappedExecutionPayloadCapella(execPayload) + require.NoError(t, err) + resp, err := client.NewPayload(ctx, wrappedPayload) + require.ErrorIs(t, ErrInvalidBlockHashPayloadStatus, err) + require.DeepEqual(t, []uint8(nil), resp) + }) t.Run(NewPayloadMethod+" INVALID status", func(t *testing.T) { execPayload, ok := fix["ExecutionPayload"].(*pb.ExecutionPayload) require.Equal(t, true, ok) @@ -367,6 +488,20 @@ func TestClient_HTTP(t *testing.T) { require.ErrorIs(t, ErrInvalidPayloadStatus, err) require.DeepEqual(t, want.LatestValidHash, resp) }) + t.Run(NewPayloadMethodV2+" INVALID status", func(t *testing.T) { + execPayload, ok := fix["ExecutionPayloadCapella"].(*pb.ExecutionPayloadCapella) + require.Equal(t, true, ok) + want, ok := fix["InvalidStatus"].(*pb.PayloadStatus) + require.Equal(t, true, ok) + client := newPayloadV2Setup(t, want, execPayload) + + // We call the RPC method via HTTP and expect a proper result. + wrappedPayload, err := blocks.WrappedExecutionPayloadCapella(execPayload) + require.NoError(t, err) + resp, err := client.NewPayload(ctx, wrappedPayload) + require.ErrorIs(t, ErrInvalidPayloadStatus, err) + require.DeepEqual(t, want.LatestValidHash, resp) + }) t.Run(NewPayloadMethod+" UNKNOWN status", func(t *testing.T) { execPayload, ok := fix["ExecutionPayload"].(*pb.ExecutionPayload) require.Equal(t, true, ok) @@ -1142,6 +1277,23 @@ func fixtures() map[string]interface{} { BlockHash: foo[:], Transactions: [][]byte{foo[:]}, } + executionPayloadFixtureCapella := &pb.ExecutionPayloadCapella{ + ParentHash: foo[:], + FeeRecipient: bar, + StateRoot: foo[:], + ReceiptsRoot: foo[:], + LogsBloom: baz, + PrevRandao: foo[:], + BlockNumber: 1, + GasLimit: 1, + GasUsed: 1, + Timestamp: 1, + ExtraData: foo[:], + BaseFeePerGas: bytesutil.PadTo(baseFeePerGas.Bytes(), fieldparams.RootLength), + BlockHash: foo[:], + Transactions: [][]byte{foo[:]}, + Withdrawals: []*pb.Withdrawal{}, + } parent := bytesutil.PadTo([]byte("parentHash"), fieldparams.RootLength) sha3Uncles := bytesutil.PadTo([]byte("sha3Uncles"), fieldparams.RootLength) miner := bytesutil.PadTo([]byte("miner"), fieldparams.FeeRecipientLength) @@ -1236,6 +1388,7 @@ func fixtures() map[string]interface{} { return map[string]interface{}{ "ExecutionBlock": executionBlock, "ExecutionPayload": executionPayloadFixture, + "ExecutionPayloadCapella": executionPayloadFixtureCapella, "ValidPayloadStatus": validStatus, "InvalidBlockHashStatus": inValidBlockHashStatus, "AcceptedStatus": acceptedStatus, @@ -1419,6 +1572,17 @@ func (*testEngineService) GetPayloadV1( return item } +func (*testEngineService) GetPayloadV2( + _ context.Context, _ pb.PayloadIDBytes, +) *pb.ExecutionPayloadCapella { + fix := fixtures() + item, ok := fix["ExecutionPayloadCapella"].(*pb.ExecutionPayloadCapella) + if !ok { + panic("not found") + } + return item +} + func (*testEngineService) ExchangeTransitionConfigurationV1( _ context.Context, _ *pb.TransitionConfiguration, ) *pb.TransitionConfiguration { @@ -1465,6 +1629,17 @@ func (*testEngineService) NewPayloadV1( return item } +func (*testEngineService) NewPayloadV2( + _ context.Context, _ *pb.ExecutionPayloadCapella, +) *pb.PayloadStatus { + fix := fixtures() + item, ok := fix["ValidPayloadStatus"].(*pb.PayloadStatus) + if !ok { + panic("not found") + } + return item +} + func forkchoiceUpdateSetup(t *testing.T, fcs *pb.ForkchoiceState, att *pb.PayloadAttributes, res *ForkchoiceUpdatedResponse) *Service { srv := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { w.Header().Set("Content-Type", "application/json") @@ -1576,3 +1751,37 @@ func newPayloadSetup(t *testing.T, status *pb.PayloadStatus, payload *pb.Executi service.rpcClient = rpcClient return service } + +func newPayloadV2Setup(t *testing.T, status *pb.PayloadStatus, payload *pb.ExecutionPayloadCapella) *Service { + srv := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { + w.Header().Set("Content-Type", "application/json") + defer func() { + require.NoError(t, r.Body.Close()) + }() + enc, err := io.ReadAll(r.Body) + require.NoError(t, err) + jsonRequestString := string(enc) + + reqArg, err := json.Marshal(payload) + require.NoError(t, err) + + // We expect the JSON string RPC request contains the right arguments. + require.Equal(t, true, strings.Contains( + jsonRequestString, string(reqArg), + )) + resp := map[string]interface{}{ + "jsonrpc": "2.0", + "id": 1, + "result": status, + } + err = json.NewEncoder(w).Encode(resp) + require.NoError(t, err) + })) + + rpcClient, err := rpc.DialHTTP(srv.URL) + require.NoError(t, err) + + service := &Service{} + service.rpcClient = rpcClient + return service +} diff --git a/beacon-chain/execution/testing/BUILD.bazel b/beacon-chain/execution/testing/BUILD.bazel index b5fbe8e411..a6a0f93adf 100644 --- a/beacon-chain/execution/testing/BUILD.bazel +++ b/beacon-chain/execution/testing/BUILD.bazel @@ -22,6 +22,7 @@ go_library( "//consensus-types/blocks:go_default_library", "//consensus-types/interfaces:go_default_library", "//consensus-types/payload-attribute:go_default_library", + "//consensus-types/primitives:go_default_library", "//encoding/bytesutil:go_default_library", "//proto/engine/v1:go_default_library", "//proto/prysm/v1alpha1:go_default_library", diff --git a/beacon-chain/execution/testing/mock_engine_client.go b/beacon-chain/execution/testing/mock_engine_client.go index 9ac9c876f7..7b99a22fe5 100644 --- a/beacon-chain/execution/testing/mock_engine_client.go +++ b/beacon-chain/execution/testing/mock_engine_client.go @@ -12,6 +12,7 @@ import ( "github.com/prysmaticlabs/prysm/v3/consensus-types/blocks" "github.com/prysmaticlabs/prysm/v3/consensus-types/interfaces" payloadattribute "github.com/prysmaticlabs/prysm/v3/consensus-types/payload-attribute" + types "github.com/prysmaticlabs/prysm/v3/consensus-types/primitives" "github.com/prysmaticlabs/prysm/v3/encoding/bytesutil" pb "github.com/prysmaticlabs/prysm/v3/proto/engine/v1" ) @@ -53,8 +54,12 @@ func (e *EngineClient) ForkchoiceUpdated( } // GetPayload -- -func (e *EngineClient) GetPayload(_ context.Context, _ [8]byte) (*pb.ExecutionPayload, error) { - return e.ExecutionPayload, e.ErrGetPayload +func (e *EngineClient) GetPayload(_ context.Context, _ [8]byte, _ types.Slot) (interfaces.ExecutionData, error) { + p, err := blocks.WrappedExecutionPayload(e.ExecutionPayload) + if err != nil { + return nil, err + } + return p, e.ErrGetPayload } // ExchangeTransitionConfiguration -- diff --git a/beacon-chain/rpc/prysm/v1alpha1/validator/proposer_execution_payload.go b/beacon-chain/rpc/prysm/v1alpha1/validator/proposer_execution_payload.go index 0d88f5a76c..9778b8eba0 100644 --- a/beacon-chain/rpc/prysm/v1alpha1/validator/proposer_execution_payload.go +++ b/beacon-chain/rpc/prysm/v1alpha1/validator/proposer_execution_payload.go @@ -68,11 +68,15 @@ func (vs *Server) getExecutionPayload(ctx context.Context, slot types.Slot, vIdx var pid [8]byte copy(pid[:], payloadId[:]) payloadIDCacheHit.Inc() - payload, err := vs.ExecutionEngineCaller.GetPayload(ctx, pid) + payload, err := vs.ExecutionEngineCaller.GetPayload(ctx, pid, slot) switch { case err == nil: - warnIfFeeRecipientDiffers(payload, feeRecipient) - return payload, nil + pb, err := payload.PbBellatrix() + if err != nil { + return nil, err + } + warnIfFeeRecipientDiffers(pb, feeRecipient) + return pb, nil case errors.Is(err, context.DeadlineExceeded): default: return nil, errors.Wrap(err, "could not get cached payload from execution client") @@ -168,12 +172,16 @@ func (vs *Server) getExecutionPayload(ctx context.Context, slot types.Slot, vIdx if payloadID == nil { return nil, fmt.Errorf("nil payload with block hash: %#x", parentHash) } - payload, err := vs.ExecutionEngineCaller.GetPayload(ctx, *payloadID) + payload, err := vs.ExecutionEngineCaller.GetPayload(ctx, *payloadID, slot) if err != nil { return nil, err } - warnIfFeeRecipientDiffers(payload, feeRecipient) - return payload, nil + pb, err := payload.PbBellatrix() + if err != nil { + return nil, err + } + warnIfFeeRecipientDiffers(pb, feeRecipient) + return pb, nil } // warnIfFeeRecipientDiffers logs a warning if the fee recipient in the included payload does not diff --git a/beacon-chain/rpc/prysm/v1alpha1/validator/proposer_execution_payload_test.go b/beacon-chain/rpc/prysm/v1alpha1/validator/proposer_execution_payload_test.go index 7b436978ca..4f570ed32b 100644 --- a/beacon-chain/rpc/prysm/v1alpha1/validator/proposer_execution_payload_test.go +++ b/beacon-chain/rpc/prysm/v1alpha1/validator/proposer_execution_payload_test.go @@ -118,7 +118,7 @@ func TestServer_getExecutionPayload(t *testing.T) { params.OverrideBeaconConfig(cfg) vs := &Server{ - ExecutionEngineCaller: &powtesting.EngineClient{PayloadIDBytes: tt.payloadID, ErrForkchoiceUpdated: tt.forkchoiceErr}, + ExecutionEngineCaller: &powtesting.EngineClient{PayloadIDBytes: tt.payloadID, ErrForkchoiceUpdated: tt.forkchoiceErr, ExecutionPayload: &pb.ExecutionPayload{}}, HeadFetcher: &chainMock.ChainService{State: tt.st}, BeaconDB: beaconDB, ProposerSlotIndexCache: cache.NewProposerPayloadIDsCache(), @@ -153,7 +153,7 @@ func TestServer_getExecutionPayloadContextTimeout(t *testing.T) { params.OverrideBeaconConfig(cfg) vs := &Server{ - ExecutionEngineCaller: &powtesting.EngineClient{PayloadIDBytes: &pb.PayloadIDBytes{}, ErrGetPayload: context.DeadlineExceeded}, + ExecutionEngineCaller: &powtesting.EngineClient{PayloadIDBytes: &pb.PayloadIDBytes{}, ErrGetPayload: context.DeadlineExceeded, ExecutionPayload: &pb.ExecutionPayload{}}, HeadFetcher: &chainMock.ChainService{State: nonTransitionSt}, BeaconDB: beaconDB, ProposerSlotIndexCache: cache.NewProposerPayloadIDsCache(), diff --git a/testing/spectest/shared/common/forkchoice/service.go b/testing/spectest/shared/common/forkchoice/service.go index d29e4ff284..60860ca295 100644 --- a/testing/spectest/shared/common/forkchoice/service.go +++ b/testing/spectest/shared/common/forkchoice/service.go @@ -19,6 +19,7 @@ import ( "github.com/prysmaticlabs/prysm/v3/beacon-chain/state/stategen" "github.com/prysmaticlabs/prysm/v3/consensus-types/interfaces" payloadattribute "github.com/prysmaticlabs/prysm/v3/consensus-types/payload-attribute" + types "github.com/prysmaticlabs/prysm/v3/consensus-types/primitives" "github.com/prysmaticlabs/prysm/v3/encoding/bytesutil" pb "github.com/prysmaticlabs/prysm/v3/proto/engine/v1" ethpb "github.com/prysmaticlabs/prysm/v3/proto/prysm/v1alpha1" @@ -77,12 +78,10 @@ type engineMock struct { payloadStatus error } -func (m *engineMock) GetPayload(context.Context, [8]byte) (*pb.ExecutionPayload, error) { - return nil, nil -} -func (m *engineMock) GetPayloadV2(context.Context, [8]byte) (*pb.ExecutionPayloadCapella, error) { +func (m *engineMock) GetPayload(context.Context, [8]byte, types.Slot) (interfaces.ExecutionData, error) { return nil, nil } + func (m *engineMock) ForkchoiceUpdated(context.Context, *pb.ForkchoiceState, payloadattribute.Attributer) (*pb.PayloadIDBytes, []byte, error) { return nil, m.latestValidHash, m.payloadStatus } @@ -90,7 +89,7 @@ func (m *engineMock) NewPayload(context.Context, interfaces.ExecutionData) ([]by return m.latestValidHash, m.payloadStatus } -func (m *engineMock) LatestExecutionBlock(context.Context) (*pb.ExecutionBlock, error) { +func (m *engineMock) LatestExecutionBlock() (*pb.ExecutionBlock, error) { return nil, nil }