From d998368cb6d8521cb51564af6d08d0f2fb5cfec0 Mon Sep 17 00:00:00 2001 From: avalonche Date: Sat, 8 Jul 2023 07:35:51 +1000 Subject: [PATCH 1/2] Add versioned submit block request --- spec/versionedsubmitblockrequest.go | 531 +++++ spec/versionedsubmitblockrequest_json.go | 94 + spec/versionedsubmitblockrequest_json_test.go | 84 + spec/versionedsubmitblockrequest_test.go | 1838 +++++++++++++++++ 4 files changed, 2547 insertions(+) create mode 100644 spec/versionedsubmitblockrequest.go create mode 100644 spec/versionedsubmitblockrequest_json.go create mode 100644 spec/versionedsubmitblockrequest_json_test.go create mode 100644 spec/versionedsubmitblockrequest_test.go diff --git a/spec/versionedsubmitblockrequest.go b/spec/versionedsubmitblockrequest.go new file mode 100644 index 0000000..c50be99 --- /dev/null +++ b/spec/versionedsubmitblockrequest.go @@ -0,0 +1,531 @@ +// Copyright © 2022 Attestant Limited. +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +package spec + +import ( + "encoding/json" + "errors" + "fmt" + + "github.com/attestantio/go-builder-client/api/bellatrix" + "github.com/attestantio/go-builder-client/api/capella" + consensusspec "github.com/attestantio/go-eth2-client/spec" + consensusbellatrix "github.com/attestantio/go-eth2-client/spec/bellatrix" + consensuscapella "github.com/attestantio/go-eth2-client/spec/capella" + "github.com/attestantio/go-eth2-client/spec/phase0" + "github.com/holiman/uint256" +) + +// VersionedSubmitBlockRequest contains a versioned signed builder bid. +type VersionedSubmitBlockRequest struct { + Version consensusspec.DataVersion + Bellatrix *bellatrix.SubmitBlockRequest + Capella *capella.SubmitBlockRequest +} + +// IsEmpty returns true if there is no request. +func (v *VersionedSubmitBlockRequest) IsEmpty() bool { + switch v.Version { + case consensusspec.DataVersionBellatrix: + return v.Bellatrix == nil + case consensusspec.DataVersionCapella: + return v.Capella == nil + default: + return true + } +} + +// Slot returns the slot of the request +func (v *VersionedSubmitBlockRequest) Slot() (uint64, error) { + if v == nil { + return 0, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return 0, errors.New("no data") + } + if v.Bellatrix.Message == nil { + return 0, errors.New("no data message") + } + return v.Bellatrix.Message.Slot, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return 0, errors.New("no data") + } + if v.Capella.Message == nil { + return 0, errors.New("no data message") + } + return v.Capella.Message.Slot, nil + default: + return 0, errors.New("unsupported version") + } +} + +// BlockHash returns the block hash of the request. +func (v *VersionedSubmitBlockRequest) BlockHash() (phase0.Hash32, error) { + if v == nil { + return phase0.Hash32{}, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return phase0.Hash32{}, errors.New("no data") + } + if v.Bellatrix.Message == nil { + return phase0.Hash32{}, errors.New("no data message") + } + return v.Bellatrix.Message.BlockHash, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return phase0.Hash32{}, errors.New("no data") + } + if v.Capella.Message == nil { + return phase0.Hash32{}, errors.New("no data message") + } + return v.Capella.Message.BlockHash, nil + default: + return phase0.Hash32{}, errors.New("unsupported version") + } +} + +// Builder returns the builder of the request. +func (v *VersionedSubmitBlockRequest) Builder() (phase0.BLSPubKey, error) { + if v == nil { + return phase0.BLSPubKey{}, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return phase0.BLSPubKey{}, errors.New("no data") + } + if v.Bellatrix.Message == nil { + return phase0.BLSPubKey{}, errors.New("no data message") + } + return v.Bellatrix.Message.BuilderPubkey, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return phase0.BLSPubKey{}, errors.New("no data") + } + if v.Capella.Message == nil { + return phase0.BLSPubKey{}, errors.New("no data message") + } + return v.Capella.Message.BuilderPubkey, nil + default: + return phase0.BLSPubKey{}, errors.New("unsupported version") + } +} + +// ProposerFeeRecipient returns the proposer fee recipient of the request. +func (v *VersionedSubmitBlockRequest) ProposerFeeRecipient() (consensusbellatrix.ExecutionAddress, error) { + if v == nil { + return consensusbellatrix.ExecutionAddress{}, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return consensusbellatrix.ExecutionAddress{}, errors.New("no data") + } + if v.Bellatrix.Message == nil { + return consensusbellatrix.ExecutionAddress{}, errors.New("no data message") + } + return v.Bellatrix.Message.ProposerFeeRecipient, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return consensusbellatrix.ExecutionAddress{}, errors.New("no data") + } + if v.Capella.Message == nil { + return consensusbellatrix.ExecutionAddress{}, errors.New("no data message") + } + return v.Capella.Message.ProposerFeeRecipient, nil + default: + return consensusbellatrix.ExecutionAddress{}, errors.New("unsupported version") + } +} + +// ProposerPubkey returns the proposer fee recipient of the request. +func (v *VersionedSubmitBlockRequest) ProposerPubkey() (phase0.BLSPubKey, error) { + if v == nil { + return phase0.BLSPubKey{}, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return phase0.BLSPubKey{}, errors.New("no data") + } + if v.Bellatrix.Message == nil { + return phase0.BLSPubKey{}, errors.New("no data message") + } + return v.Bellatrix.Message.ProposerPubkey, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return phase0.BLSPubKey{}, errors.New("no data") + } + if v.Capella.Message == nil { + return phase0.BLSPubKey{}, errors.New("no data message") + } + return v.Capella.Message.ProposerPubkey, nil + default: + return phase0.BLSPubKey{}, errors.New("unsupported version") + } +} + +// ParentHash returns the parent hash of the request. +func (v *VersionedSubmitBlockRequest) ParentHash() (phase0.Hash32, error) { + if v == nil { + return phase0.Hash32{}, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return phase0.Hash32{}, errors.New("no data") + } + if v.Bellatrix.Message == nil { + return phase0.Hash32{}, errors.New("no data message") + } + return v.Bellatrix.Message.ParentHash, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return phase0.Hash32{}, errors.New("no data") + } + if v.Capella.Message == nil { + return phase0.Hash32{}, errors.New("no data message") + } + return v.Capella.Message.ParentHash, nil + default: + return phase0.Hash32{}, errors.New("unsupported version") + } +} + +// Value returns the value of the request. +func (v *VersionedSubmitBlockRequest) Value() (*uint256.Int, error) { + if v == nil { + return nil, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return nil, errors.New("no data") + } + if v.Bellatrix.Message == nil { + return nil, errors.New("no data message") + } + return v.Bellatrix.Message.Value, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return nil, errors.New("no data") + } + if v.Capella.Message == nil { + return nil, errors.New("no data message") + } + return v.Capella.Message.Value, nil + default: + return nil, errors.New("unsupported version") + } +} + +// MessageHashTreeRoot returns the hash tree root of the message of the bid. +func (v *VersionedSubmitBlockRequest) MessageHashTreeRoot() (phase0.Root, error) { + if v == nil { + return phase0.Root{}, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return phase0.Root{}, errors.New("no data") + } + if v.Bellatrix.Message == nil { + return phase0.Root{}, errors.New("no data message") + } + return v.Bellatrix.Message.HashTreeRoot() + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return phase0.Root{}, errors.New("no data") + } + if v.Capella.Message == nil { + return phase0.Root{}, errors.New("no data message") + } + return v.Capella.Message.HashTreeRoot() + default: + return phase0.Root{}, errors.New("unsupported version") + } +} + +// Signature returns the signature of the bid. +func (v *VersionedSubmitBlockRequest) Signature() (phase0.BLSSignature, error) { + if v == nil { + return phase0.BLSSignature{}, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return phase0.BLSSignature{}, errors.New("no data") + } + return v.Bellatrix.Signature, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return phase0.BLSSignature{}, errors.New("no data") + } + return v.Capella.Signature, nil + default: + return phase0.BLSSignature{}, errors.New("unsupported version") + } +} + +// ExecutionPayloadBlockHash returns the block hash of the payload +func (v *VersionedSubmitBlockRequest) ExecutionPayloadBlockHash() (phase0.Hash32, error) { + if v == nil { + return phase0.Hash32{}, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return phase0.Hash32{}, errors.New("no data") + } + if v.Bellatrix.ExecutionPayload == nil { + return phase0.Hash32{}, errors.New("no data execution payload") + } + return v.Bellatrix.ExecutionPayload.BlockHash, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return phase0.Hash32{}, errors.New("no data") + } + if v.Capella.ExecutionPayload == nil { + return phase0.Hash32{}, errors.New("no data execution payload") + } + return v.Capella.ExecutionPayload.BlockHash, nil + default: + return phase0.Hash32{}, errors.New("unsupported version") + } +} + +// ExecutionPayloadParentHash returns the block hash of the payload +func (v *VersionedSubmitBlockRequest) ExecutionPayloadParentHash() (phase0.Hash32, error) { + if v == nil { + return phase0.Hash32{}, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return phase0.Hash32{}, errors.New("no data") + } + if v.Bellatrix.ExecutionPayload == nil { + return phase0.Hash32{}, errors.New("no data execution payload") + } + return v.Bellatrix.ExecutionPayload.ParentHash, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return phase0.Hash32{}, errors.New("no data") + } + if v.Capella.ExecutionPayload == nil { + return phase0.Hash32{}, errors.New("no data execution payload") + } + return v.Capella.ExecutionPayload.ParentHash, nil + default: + return phase0.Hash32{}, errors.New("unsupported version") + } +} + +// PrevRandao returns the prev randao of the payload +func (v *VersionedSubmitBlockRequest) PrevRandao() (phase0.Hash32, error) { + if v == nil { + return phase0.Hash32{}, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return phase0.Hash32{}, errors.New("no data") + } + if v.Bellatrix.ExecutionPayload == nil { + return phase0.Hash32{}, errors.New("no data execution payload") + } + return v.Bellatrix.ExecutionPayload.PrevRandao, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return phase0.Hash32{}, errors.New("no data") + } + if v.Capella.ExecutionPayload == nil { + return phase0.Hash32{}, errors.New("no data execution payload") + } + return v.Capella.ExecutionPayload.PrevRandao, nil + default: + return phase0.Hash32{}, errors.New("unsupported version") + } +} + +// GasLimit returns the prev randao of the payload +func (v *VersionedSubmitBlockRequest) GasLimit() (uint64, error) { + if v == nil { + return 0, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return 0, errors.New("no data") + } + if v.Bellatrix.ExecutionPayload == nil { + return 0, errors.New("no data execution payload") + } + return v.Bellatrix.ExecutionPayload.GasLimit, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return 0, errors.New("no data") + } + if v.Capella.ExecutionPayload == nil { + return 0, errors.New("no data execution payload") + } + return v.Capella.ExecutionPayload.GasLimit, nil + default: + return 0, errors.New("unsupported version") + } +} + +// GasUsed returns the prev randao of the payload +func (v *VersionedSubmitBlockRequest) GasUsed() (uint64, error) { + if v == nil { + return 0, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return 0, errors.New("no data") + } + if v.Bellatrix.ExecutionPayload == nil { + return 0, errors.New("no data execution payload") + } + return v.Bellatrix.ExecutionPayload.GasUsed, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return 0, errors.New("no data") + } + if v.Capella.ExecutionPayload == nil { + return 0, errors.New("no data execution payload") + } + return v.Capella.ExecutionPayload.GasUsed, nil + default: + return 0, errors.New("unsupported version") + } +} + +// BlockNumber returns the block number of the payload. +func (v *VersionedSubmitBlockRequest) BlockNumber() (uint64, error) { + if v == nil { + return 0, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return 0, errors.New("no data") + } + if v.Bellatrix.ExecutionPayload == nil { + return 0, errors.New("no data execution payload") + } + return v.Bellatrix.ExecutionPayload.BlockNumber, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return 0, errors.New("no data") + } + if v.Capella.ExecutionPayload == nil { + return 0, errors.New("no data execution payload") + } + return v.Capella.ExecutionPayload.BlockNumber, nil + default: + return 0, errors.New("unsupported version") + } +} + +// Timestamp returns the timestamp of the payload. +func (v *VersionedSubmitBlockRequest) Timestamp() (uint64, error) { + if v == nil { + return 0, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return 0, errors.New("no data") + } + if v.Bellatrix.ExecutionPayload == nil { + return 0, errors.New("no data execution payload") + } + return v.Bellatrix.ExecutionPayload.Timestamp, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return 0, errors.New("no data") + } + if v.Capella.ExecutionPayload == nil { + return 0, errors.New("no data execution payload") + } + return v.Capella.ExecutionPayload.Timestamp, nil + default: + return 0, errors.New("unsupported version") + } +} + +// Transactions returns the transactions of the payload +func (v *VersionedSubmitBlockRequest) Transactions() ([]consensusbellatrix.Transaction, error) { + if v == nil { + return nil, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionBellatrix: + if v.Bellatrix == nil { + return nil, errors.New("no data") + } + if v.Bellatrix.ExecutionPayload == nil { + return nil, errors.New("no data execution payload") + } + return v.Bellatrix.ExecutionPayload.Transactions, nil + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return nil, errors.New("no data") + } + if v.Capella.ExecutionPayload == nil { + return nil, errors.New("no data execution payload") + } + return v.Capella.ExecutionPayload.Transactions, nil + default: + return nil, errors.New("unsupported version") + } +} + +// Withdrawals returns the withdrawals of the payload +func (v *VersionedSubmitBlockRequest) Withdrawals() ([]*consensuscapella.Withdrawal, error) { + if v == nil { + return nil, errors.New("nil struct") + } + switch v.Version { + case consensusspec.DataVersionCapella: + if v.Capella == nil { + return nil, errors.New("no data") + } + if v.Capella.ExecutionPayload == nil { + return nil, errors.New("no data execution payload") + } + return v.Capella.ExecutionPayload.Withdrawals, nil + default: + return nil, errors.New("unsupported version") + } +} + +// String returns a string version of the structure. +func (v *VersionedSubmitBlockRequest) String() string { + if v == nil { + return "" + } + data, err := json.Marshal(v) + if err != nil { + return fmt.Sprintf("ERR: %v", err) + } + return string(data) +} diff --git a/spec/versionedsubmitblockrequest_json.go b/spec/versionedsubmitblockrequest_json.go new file mode 100644 index 0000000..247434b --- /dev/null +++ b/spec/versionedsubmitblockrequest_json.go @@ -0,0 +1,94 @@ +// Copyright © 2023 Attestant Limited. +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +package spec + +import ( + "encoding/json" + "fmt" + + "github.com/attestantio/go-builder-client/api/bellatrix" + "github.com/attestantio/go-builder-client/api/capella" + "github.com/attestantio/go-eth2-client/spec" + "github.com/pkg/errors" +) + +type bellatrixVersionedSubmitBlockRequestJSON struct { + Data *bellatrix.SubmitBlockRequest `json:"data"` +} +type capellaVersionedSubmitBlockRequestJSON struct { + Data *capella.SubmitBlockRequest `json:"data"` +} + +// MarshalJSON implements json.Marshaler. +func (v *VersionedSubmitBlockRequest) MarshalJSON() ([]byte, error) { + version := &versionJSON{ + Version: v.Version, + } + + switch v.Version { + case spec.DataVersionBellatrix: + if v.Bellatrix == nil { + return nil, errors.New("no bellatrix data") + } + data := &bellatrixVersionedSubmitBlockRequestJSON{ + Data: v.Bellatrix, + } + payload := struct { + *versionJSON + *bellatrixVersionedSubmitBlockRequestJSON + }{version, data} + return json.Marshal(payload) + case spec.DataVersionCapella: + if v.Capella == nil { + return nil, errors.New("no capella data") + } + data := &capellaVersionedSubmitBlockRequestJSON{ + Data: v.Capella, + } + payload := struct { + *versionJSON + *capellaVersionedSubmitBlockRequestJSON + }{version, data} + return json.Marshal(payload) + default: + return nil, fmt.Errorf("unsupported data version %v", v.Version) + } +} + +// UnmarshalJSON implements json.Unmarshaler. +func (v *VersionedSubmitBlockRequest) UnmarshalJSON(input []byte) error { + var metadata versionJSON + if err := json.Unmarshal(input, &metadata); err != nil { + return errors.Wrap(err, "invalid JSON") + } + v.Version = metadata.Version + switch metadata.Version { + case spec.DataVersionBellatrix: + var data bellatrixVersionedSubmitBlockRequestJSON + if err := json.Unmarshal(input, &data); err != nil { + return errors.Wrap(err, "invalid JSON") + } + v.Bellatrix = data.Data + case spec.DataVersionCapella: + var data capellaVersionedSubmitBlockRequestJSON + if err := json.Unmarshal(input, &data); err != nil { + return errors.Wrap(err, "invalid JSON") + } + v.Capella = data.Data + default: + return fmt.Errorf("unsupported data version %v", metadata.Version) + } + + return nil +} diff --git a/spec/versionedsubmitblockrequest_json_test.go b/spec/versionedsubmitblockrequest_json_test.go new file mode 100644 index 0000000..9e061f7 --- /dev/null +++ b/spec/versionedsubmitblockrequest_json_test.go @@ -0,0 +1,84 @@ +// Copyright © 2023 Attestant Limited. +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +package spec_test + +import ( + "encoding/json" + "testing" + + "github.com/attestantio/go-builder-client/spec" + "github.com/stretchr/testify/require" + "gotest.tools/assert" +) + +func TestVersionedSubmitBlockRequestJSON(t *testing.T) { + tests := []struct { + name string + input []byte + err string + }{ + { + name: "Empty", + err: "unexpected end of JSON input", + }, + { + name: "JSONBad", + input: []byte("[]"), + err: "invalid JSON: json: cannot unmarshal array into Go value of type spec.versionJSON", + }, + { + name: "VersionMissing", + input: []byte(`{"data":{"message":{"header":{"parent_hash":"0x17f4eeae822cc81533016678413443b95e34517e67f12b4a3a92ff6b66f972ef","fee_recipient":"0x58E809C71e4885cB7B3f1D5c793AB04eD239d779","state_root":"0x3d6e230e6eceb8f3db582777b1500b8b31b9d268339e7b32bba8d6f1311b211d","receipts_root":"0xea760203509bdde017a506b12c825976d12b04db7bce9eca9e1ed007056a3f36","logs_bloom":"0x0c803a8d3c6642adee3185bd914c599317d96487831dabda82461f65700b2528781bdadf785664f9d8b11c4ee1139dfeb056125d2abd67e379cabc6d58f1c3ea304b97cf17fcd8a4c53f4dedeaa041acce062fc8fbc88ffc111577db4a936378749f2fd82b4bfcb880821dd5cbefee984bc1ad116096a64a44a2aac8a1791a7ad3a53d91c584ac69a8973daed6daee4432a198c9935fa0e5c2a4a6ca78b821a5b046e571a5c0961f469d40e429066755fec611afe25b560db07f989933556ce0cea4070ca47677b007b4b9857fc092625f82c84526737dc98e173e34fe6e4d0f1a400fd994298b7c2fa8187331c333c415f0499836ff0eed5c762bf570e67b44","prev_randao":"0x76ff751467270668df463600d26dba58297a986e649bac84ea856712d4779c00","block_number":"2983837628677007840","gas_limit":"6738255228996962210","gas_used":"5573520557770513197","timestamp":"1744720080366521389","extra_data":"0xc648","base_fee_per_gas":"88770397543877639215846057887940126737648744594802753726778414602657613619599","block_hash":"0x42c294e902bfc9884c1ce5fef156d4661bb8f0ff488bface37f18c3e7be64b0f","transactions_root":"0x8457d0eb7611a621e7a094059f087415ffcfc91714fc184a1f3c48db06b4d08b","withdrawals_root":"0x5c1a7e3e0eab917a7c0d677c6b692ed55ce05f07d572e09b1c06d558f474ea7a"},"value":"12345","pubkey":"0x010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101"},"signature":"0x010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101"}}`), + err: "unsupported data version phase0", + }, + { + name: "VersionUnknown", + input: []byte(`{"version":"unknown","data":{"message":{"slot":"1","parent_hash":"0xae694782c41219774f46891c6365243b97d63d66aeb7827023b8336161615652","block_hash":"0x6462e48cff39c6e4e02e5fe1aa97bf03b23a1aa588f07cfd6296d2b9bb909ce4","builder_pubkey":"0x8efc1675ffb449abc00a6ad8a2808cdf798d96fbb979cf00956012f3983577c9afe69495411a89385421f1cff47dfc98","proposer_pubkey":"0xb7da036d8aedf726e2b3439f95bdf0e68519bb55ab83d5d97a70a5b8510f612ad45a6ecc58b8b5b9b09c6b445491a02b","proposer_fee_recipient":"0x9427A30991170f917d7b83dEf6e44d26577871Ed","gas_limit":"30000000","gas_used":"7675443","value":"22135875749231725"},"execution_payload":{"parent_hash":"0x17f4eeae822cc81533016678413443b95e34517e67f12b4a3a92ff6b66f972ef","fee_recipient":"0x58E809C71e4885cB7B3f1D5c793AB04eD239d779","state_root":"0x3d6e230e6eceb8f3db582777b1500b8b31b9d268339e7b32bba8d6f1311b211d","receipts_root":"0xea760203509bdde017a506b12c825976d12b04db7bce9eca9e1ed007056a3f36","logs_bloom":"0x0c803a8d3c6642adee3185bd914c599317d96487831dabda82461f65700b2528781bdadf785664f9d8b11c4ee1139dfeb056125d2abd67e379cabc6d58f1c3ea304b97cf17fcd8a4c53f4dedeaa041acce062fc8fbc88ffc111577db4a936378749f2fd82b4bfcb880821dd5cbefee984bc1ad116096a64a44a2aac8a1791a7ad3a53d91c584ac69a8973daed6daee4432a198c9935fa0e5c2a4a6ca78b821a5b046e571a5c0961f469d40e429066755fec611afe25b560db07f989933556ce0cea4070ca47677b007b4b9857fc092625f82c84526737dc98e173e34fe6e4d0f1a400fd994298b7c2fa8187331c333c415f0499836ff0eed5c762bf570e67b44","prev_randao":"0x76ff751467270668df463600d26dba58297a986e649bac84ea856712d4779c00","block_number":"2983837628677007840","gas_limit":"6738255228996962210","gas_used":"5573520557770513197","timestamp":"1744720080366521389","extra_data":"0xc648","base_fee_per_gas":"1","block_hash":"0x42c294e902bfc9884c1ce5fef156d4661bb8f0ff488bface37f18c3e7be64b0f","transactions":["0x101b883470f1cb7e0a74561be59e08a6eff6aedd3408c190fd359f0bfb628d2461354b7fe4fdad4b8e72b8775cd44e339ad6b5f22a8f53c418bda2b01200a07f1fe3d010bbb96f5ca0d4919192370c15bc46ed455c797b1b11154be359638f9e487121182fae03a7d26012ed7c85b64a63aa5d56a98ac589f9950a9f5bf1a42c1eea245a98f2f4e743c5f8eac1584893104853dc1b5576826156b371a50c59bcb238d0794a185dc0816dbd8c10a0b0e1b8fbe01c4e8dd719f1e4e9b2ded8613f87f1d01e3ea28e9311d135301b2d1260e4811789e1ecbc33e573346f4da94f4c272e21e23b1d414706429c7f0b40c3de243894349c4a59ece791e5fd086897aef81fc23e4d55bb52b28174c3fa9f2c44d370fbbac1dee561f120560c3dda34a731d4618fd22d595b725efa87bb62f8f93bd7d906c4782a647e2cb14ed293e58bc793852058ab5e6f3df76b30e99102b82c8e7d005e1b675fc74b95032616c590ff08da710dd085be570cc0b2c13891625b44b5b3e1846606c39ad39bb72b","0x4b5edff58cf95969ead0470ab897da6c9d69b517e07fd4ed8fa48c14284a5a060ecb745f66cf1be55fb4905d62d8d376865f7d2d1816844fc4719f5d79ab905474d00f62aed6692e5a93be1b32740a8083fc2a61b0e1fc13ad409410d37f3cb0a5275c966abab015047c15251cd301cd31a7b2a0502f7f953e672d61606616b16d5117163064fb33d97eb566f7fce5f01d3833343c1c97e6221f9f0798415f3a4b87fd472e53a24c1a101e1dd55c8f65c2c0f4ccc4b46a133fda49db5dba96631b4cfd1a05662e42a8e15a26d3148a70be305c85f87dae4217fb91498c4098b946a9042355968b765e2e62bb0cf26d59e534c3af8795fa0f4a44ed0d39d258acd934c3416e4d4a738eaa473526d99bee037765d5f6034c830eb766ef067a1468630fbb65b7c5a862017fe84d4d1961f90c37f18a4bd2509fe2e96cb1e26971900e20295c8a9e9ed77b348d4509a8425090318be5c9d2bcda36bdfabb71bfb36755794f78c877df2825bd736a358933af77eae6edf701ed7ef168f57f677df3445d89c5eefc783184eadd3886fcfd75f5f142bc10904a019acdf7861caa7e0fba3e7831b0a549a56c0f174e80cffb8992346ddf7ce4eeff9e335531df3dff57d5f539bc0d3eac57f70a8f973e0864c87b25c3e0bea72e05eda8a120178186dfbfaa9a00f904f23a","0x452af990975c3bcafee7bde4738fdf32b8479be0e9e30b11b0ccbf31a6f884f4098e47759b7a3eb7d7bd0cfa2510dd654b28d664696aca987f55c7bfe73be1cc70a768cdb2594a13a763dbb991186b8b8b2e913857aadc08f940239d03a0b181ae849d557da5b54bfc966231690bb4660e083cdae28caf8ed33e3f66672772ea827253421bade013af57a290a915dbc777f2afccd9cb29e260ecc5ea54cd3a1e25cf66f2937f8061b3ba6b1ebf3129568f16e3dd04d5c50992cc348f3e615af346dbf2c144aeb19932dcfbff0221fae0ed9706b53245176630d011b9cd2d8630848ab1196cf9a3cc0d94392df4295be246e0ac24545c2715a40dcbc57aabffd0a86acec362affaf1bafc5c75b7ca28698a1ac14ea2c8def8ac1a32d3bf65b98aac7d0cb6fd93e5ff16274ad6d0eedf773694f29fc7a234deebc893e4cea4a5483d876e4f35019d6a62f1c407739b68b7a9f5408b4fb854534344fbffe3239feb17c0e7ac269b447bc6246579e1208b6904751eeacb985cbd43bb7792de0b428f1476301c479a3922f61f650c8298fb0b7584b52c7bfcf4dfe51335ab68d571c5815fc78d772346b0b13dbbb8906f076a0452e7e7a414e005dc37cfee85810eccab5999e2d43e13709bf66e8a8936a4283885b158115050789d3b4d9c8dc8026ac720069d78d47dd5e183032f9c53d4c57640fcd6207118d9738f00cd5ddf587f3a7c401d923aa2fb08dba1768728001abc3436cc2b5cf978b558ae58a0578344e7464cd00e719135c70244e2faf1264571a8999789c26f401753e429a1135f18906ebef19e122489622738724a6424cad363bed43304c1285c8da4824fec75d7c51b0a34070d8b976e8e8c8fd50908a7e440092dddd970fd55793e2a4446342bd3daf5b96220977d8f0c","0x0877448694993717a89c57b63640612ac4b0258cb5fdda4a311650c631c35c7313b6d2a094fdb207857d94500c37ab20ea0aa54af951fb04584a37b857981c6d13922e95cfecb70b69ab9a57ee6c13ccf8aa38c52de008ec16d9090aa4bf15db2f4afcdbb1bf4920efe5a1aeeff2c949d43460d67837af87bcdffd9e972340cb40de6d87fa11d83bbfb29e97ef2509097e8dec69a1318132a5dd7d95c1c1e13cc85d37a33c9f7d52379b4a47bf889903c8f3ebd2800526d0916e1aad00e02b682e55bc2865c3ff4ce0cc6aad1bd7d8e2901ea53f3a5e2c025dbb9a00f0ce88583c1dbd3d491ed04ba8260dc06fdb8a9162e022c75e9f057da0abed537b34214df234e1f8b26e7374cfa5470272ef03f7b41f7ed067c4c6011c8a17b2e65340e36af81ecb86420755fe5a0413495e16fabee3f9e5524ab7b12a3cffe20b1df7be32434d7da3fb1f3e9b16f42a4f550501120036b193701ac9eb6f760c2da70e3175a66b10463e43c0442a56217ca7cd25fdb46f3eff28cf1bdfe1b7eb3bf9e85ad8ffde207529c9bb1094dbae4db04a4bff6571c985bd629cdc2b78f739eca6694f32fded6944202859277740267d5dc4c1f74ddd1401c6d514ce23b885723c4618789b5c2ddeffec2179be8dec1347ca4ebed5e8bb10d7d17d41c9709a978fc6189f0c3d49d1b7f41bf8f1dc112f2ece84b6c6a687f44b95e62d274f89fa07bd0d3fdd3ee2a97233e363329ef7096ae5a45b2982859e983f5d989a928e9b88579308ece2391dbde378b81a54d38b3f81225d59f8bb511ba7eb590154ceb8258b804b6da98b3af6f395f5b3f1d12f5fd3c29ef54f31ccea0a36ec2daec0a87030daba8d079093ddde17871c4aa1a7dc3dbd4d760be2152dc250ca2bba34a55daf257b9e3704c3ee244081524cb1ae7c22a0d22f1c65b88b1e534ea1cb8f75cea4a7c03d6786f85327876da72dff1d4d049b51ecc10124279a0cbc151e76ddd475cf3dfeede59a902f4c7145786b5993c8bf8016265ec36298b27d0c6a21c7484fc01a8f14c8c287d14ab86789e34699fdb57f6c43486f0fd9013f2f2c62c60b75b1dc3e4d38a6f7c06e7029f874a204b059d834ffb44c99f843ae33ed0950","0x259310d5134d22e0ef42c3686b2adadc6cd1ae7d7836ac71a69d8ba2d02d0152c320610c12c57cba182c5d1e21198e787b21d0c522106aa8243ec994c4ea0b7959a3269d13566f3d0a3eb5ed276d9e22b33fc12e26cafde04b24ec0fd90455dc26d30a9fc25588b762681ca69aecc19e7971dd4cd063d4e31ee99f3c82015ed9a70e58b9d7cd9a8de38eba90ceffc629e7d6c06e4f2fe9cd45bae557652fe58cc9be54de9a994bf14c3bce787a106778416fbe966e95e51a35ba78d3dc4e4f7551e2791af00d50362493697d55ea6718ba2f089eda330e26100fb5adbb939afaf74982795414422712e8560cec372eaf1a56b50ba4e00e42b145537e94e88eddd7d200d0153edb6dcc12eb298666b0aef9ea495fccfda06b7affe7227bceb41d9ac9dd150df8642cdb11df5ab92b69629b6a5ccdc7ba92b6cf12172217057d291b2fdc6f104e86617be1b7fffeb36af59a018f50c055e24ef9b6daff839083bc9dfeae9101f6aff49f808f603834802d160283cd71b275bf97eb49f5612215cc8fe93875","0xfa082adb51ff0dca75ff57ba7852d794284db5b8d498002a821e5fc2c57a27cc1fe591f12860895b0057bc75ecbff9824bb46e2af06a785b6adfa9e32f49d6235776c3bcace18b330cec1126ac2bb5f3679339037817eab536fed29fe5c62ef790cb74893f1524280b0111e24fc0172130d00a88361e63511eb56a96e552d02c4944544c193189a152844ca49cadae38b7424426a74d61763716a068ba5ca9f3bdc2e0e9b644f1f2e02596bd3f446bb9f13dfb18ad2c9a2ba97771bb994f801affe2e8dda8d638e366c5b8263cc891a8a35e52c79f0856bfeaf0719bd1bfb54acc467783b6c08e55491d39b20f218342991381c38d357a4659baf8d44ddf5045d7f116bcc55f78c28a0dc100d06dff44e639b8e7adf967816c03de54eccdf9f6402a2806889d2cd980f34e5197771f13f1fa6b8c7c732031664bb675ff12d642ae62459e92b1cc28c62349e1636850b8a3ff411e1f14b097f7fa3b23eaa173d17a13f0703eecd7358aa623057325eed381a2ba13c50a13a3d8adaad0295960d925709d6e7cb101e894d9ae8db3dcb82a45570b6e02ab68aa4ea94f8779a9c45a5599","0x71ea3e9ec7ac8a144753ec38e78401b14b489a79266dd0527a4505adca584fe7406d9f7f05ef46d262384fbf1c0607f745a40681d4855aa34c37375b2cf7c99d46b6ae4e3aa9ee209782dce9d167bbff79686e59426a0513b951818ee02a9ea5ed8bcd0f991f46eee44c6e82fc6d07823a9f44f2fd7bfa0e250d6699cf7ad2577eb9eaf0dd9b1595cf018383c3d45956e508fa982bbb7744522a03bac5cba22f58a41801f579434126f5b866dcc6ca0454e9be1c7f2f6649254f3cc09142068f412d5d454b4e4d5b54e459719550f2df1901a18467d9d5297ed4a9eedb9f402f2bfd4bd2e50ab697ea5bef5e7e8082650b823635a4f0f55c18712d0f4d365824c79827d454425aec0b4ea6561ce3f1c5411ab4dff26e2412791cdaa28bf6c8fa53af412828c599d7876508f78f2c82ee67e8357947c6848af143fc5d20409049925cd1b194244466711ce7c34a72a165392564b96e280406a95da927d14ebbb6b999ef446d5ad49881c219dac8ad02d994e059569e91b84f211a4c39a3fbd594a8c835aa5976e0c8899d81a5abaa14301662b9e14fb96ea89862ad898cd7d77bcd2547f0f40471f86d4a4f26e4274f2e95fd9b2b604de867be95630b1ea6ce45ba79acc81b986605e46acda208bd3302ffcc6e83f91bff8362b3f9641ca0227d8b31341e320003","0x2b2acf1e7e043b2c38ea1750a6c31f174b0a8b00137ec3eea24ed9fdf979bf04ed923a2cf5cc05a9acf697d27ccdb2a903a4846729cd9b2eead414da983d4f5bfd0ff4f2e7eb75988e58c3a635c271","0xce0c3b31143f1d68987deaac86a1e079deb07b3d2d497de5ebe8d94486e9a7b300c691621a68b3af4fee781c7c05a931123f910054d096c2e154950d32a26c38edb70dda50a242be4d15ce60c265767b141011cd84aa585c3af798fc1eb5ea63e93e0a426c3e1468f402f7e64f20281a4bd73cc1234174f1762a9a41989f570997036c885b1fdbf9c8153a1d19afb6526a123ca6a2fe6e98c6009f8439f6b6eea881453cc58ef344338ffd04783ce9c28c2e373812a65157643f679ed99ab35f4024e6ee31877e536b03c38616fccc993365143ddaffce39c805b391674070e993c6464156043a84266860c769de218bb5f5698f4c7a9b74142535cbcc08d5b3f747cbf6a7dfbb6c7b0ccc58af4886bc441558496e9c84d80660117777f01cdb84c0a2d3b0f2d8a6eacff5a0e55bd1be6387c3793ae8f5231c59697ae914894a49b3ae13a3a124cbf6cea33b7eb575cf6cd13e6073ddf4d033a3f87366c27089afc03707ef9a44c828388733d70f09bc08de574d07cf193f0a26a08ce8253bfdb26d5306632012c6dae194783deb31b72ac35bbd57f07f1667746d85f5d5b2132b885f8cb0206949780f9406307396dc7ece7938225fc5a55c65ed3608c27f668ba9b08875979e249655d15a4c3d77b1433ab26f56d80e2ca9178d88501ee682a14d07b17635e9968da2d98aa9eb4a5ae639e42eed0c7735313d3308fd079589d5cb2dd381a9298f67325976a6dcd3e38f836e4bc3106885f6348c57c90beadd7cbca17570b90130aaadc7eb0ed2bfb97c5c8a791d0b6b2736d43b0f444909449e6ea32ba706ddfe28c407a85e82e3f22064696d2fd7b37b33e01e0016ad91047f95f0cf5c5d6abc8fd7698c4155c290a1a1db842e77e656c69ad8bc06cea9e00dadbec886ca64af5fe3045ebc8c549bf23e71c634f02da8b250618c169a54e4af45d799f2de6747bde01395a13f1a605e9be5","0x9ced04a51e77ed0730f3420571164ea5247a670b962ebf6b453660748ca5"]},"signature":"0x010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101"}}`), + err: "invalid JSON: unrecognised data version \"unknown\"", + }, + { + name: "BadBellatrix", + input: []byte(`{"version":"bellatrix","data":[]}`), + err: "invalid JSON: invalid JSON: json: cannot unmarshal array into Go value of type bellatrix.submitBlockRequestJSON", + }, + { + name: "GoodBellatrix", + input: []byte(`{"version":"bellatrix","data":{"message":{"slot":"1","parent_hash":"0xae694782c41219774f46891c6365243b97d63d66aeb7827023b8336161615652","block_hash":"0x6462e48cff39c6e4e02e5fe1aa97bf03b23a1aa588f07cfd6296d2b9bb909ce4","builder_pubkey":"0x8efc1675ffb449abc00a6ad8a2808cdf798d96fbb979cf00956012f3983577c9afe69495411a89385421f1cff47dfc98","proposer_pubkey":"0xb7da036d8aedf726e2b3439f95bdf0e68519bb55ab83d5d97a70a5b8510f612ad45a6ecc58b8b5b9b09c6b445491a02b","proposer_fee_recipient":"0x9427A30991170f917d7b83dEf6e44d26577871Ed","gas_limit":"30000000","gas_used":"7675443","value":"22135875749231725"},"execution_payload":{"parent_hash":"0x17f4eeae822cc81533016678413443b95e34517e67f12b4a3a92ff6b66f972ef","fee_recipient":"0x58E809C71e4885cB7B3f1D5c793AB04eD239d779","state_root":"0x3d6e230e6eceb8f3db582777b1500b8b31b9d268339e7b32bba8d6f1311b211d","receipts_root":"0xea760203509bdde017a506b12c825976d12b04db7bce9eca9e1ed007056a3f36","logs_bloom":"0x0c803a8d3c6642adee3185bd914c599317d96487831dabda82461f65700b2528781bdadf785664f9d8b11c4ee1139dfeb056125d2abd67e379cabc6d58f1c3ea304b97cf17fcd8a4c53f4dedeaa041acce062fc8fbc88ffc111577db4a936378749f2fd82b4bfcb880821dd5cbefee984bc1ad116096a64a44a2aac8a1791a7ad3a53d91c584ac69a8973daed6daee4432a198c9935fa0e5c2a4a6ca78b821a5b046e571a5c0961f469d40e429066755fec611afe25b560db07f989933556ce0cea4070ca47677b007b4b9857fc092625f82c84526737dc98e173e34fe6e4d0f1a400fd994298b7c2fa8187331c333c415f0499836ff0eed5c762bf570e67b44","prev_randao":"0x76ff751467270668df463600d26dba58297a986e649bac84ea856712d4779c00","block_number":"2983837628677007840","gas_limit":"6738255228996962210","gas_used":"5573520557770513197","timestamp":"1744720080366521389","extra_data":"0xc648","base_fee_per_gas":"1","block_hash":"0x42c294e902bfc9884c1ce5fef156d4661bb8f0ff488bface37f18c3e7be64b0f","transactions":["0x101b883470f1cb7e0a74561be59e08a6eff6aedd3408c190fd359f0bfb628d2461354b7fe4fdad4b8e72b8775cd44e339ad6b5f22a8f53c418bda2b01200a07f1fe3d010bbb96f5ca0d4919192370c15bc46ed455c797b1b11154be359638f9e487121182fae03a7d26012ed7c85b64a63aa5d56a98ac589f9950a9f5bf1a42c1eea245a98f2f4e743c5f8eac1584893104853dc1b5576826156b371a50c59bcb238d0794a185dc0816dbd8c10a0b0e1b8fbe01c4e8dd719f1e4e9b2ded8613f87f1d01e3ea28e9311d135301b2d1260e4811789e1ecbc33e573346f4da94f4c272e21e23b1d414706429c7f0b40c3de243894349c4a59ece791e5fd086897aef81fc23e4d55bb52b28174c3fa9f2c44d370fbbac1dee561f120560c3dda34a731d4618fd22d595b725efa87bb62f8f93bd7d906c4782a647e2cb14ed293e58bc793852058ab5e6f3df76b30e99102b82c8e7d005e1b675fc74b95032616c590ff08da710dd085be570cc0b2c13891625b44b5b3e1846606c39ad39bb72b","0x4b5edff58cf95969ead0470ab897da6c9d69b517e07fd4ed8fa48c14284a5a060ecb745f66cf1be55fb4905d62d8d376865f7d2d1816844fc4719f5d79ab905474d00f62aed6692e5a93be1b32740a8083fc2a61b0e1fc13ad409410d37f3cb0a5275c966abab015047c15251cd301cd31a7b2a0502f7f953e672d61606616b16d5117163064fb33d97eb566f7fce5f01d3833343c1c97e6221f9f0798415f3a4b87fd472e53a24c1a101e1dd55c8f65c2c0f4ccc4b46a133fda49db5dba96631b4cfd1a05662e42a8e15a26d3148a70be305c85f87dae4217fb91498c4098b946a9042355968b765e2e62bb0cf26d59e534c3af8795fa0f4a44ed0d39d258acd934c3416e4d4a738eaa473526d99bee037765d5f6034c830eb766ef067a1468630fbb65b7c5a862017fe84d4d1961f90c37f18a4bd2509fe2e96cb1e26971900e20295c8a9e9ed77b348d4509a8425090318be5c9d2bcda36bdfabb71bfb36755794f78c877df2825bd736a358933af77eae6edf701ed7ef168f57f677df3445d89c5eefc783184eadd3886fcfd75f5f142bc10904a019acdf7861caa7e0fba3e7831b0a549a56c0f174e80cffb8992346ddf7ce4eeff9e335531df3dff57d5f539bc0d3eac57f70a8f973e0864c87b25c3e0bea72e05eda8a120178186dfbfaa9a00f904f23a","0x452af990975c3bcafee7bde4738fdf32b8479be0e9e30b11b0ccbf31a6f884f4098e47759b7a3eb7d7bd0cfa2510dd654b28d664696aca987f55c7bfe73be1cc70a768cdb2594a13a763dbb991186b8b8b2e913857aadc08f940239d03a0b181ae849d557da5b54bfc966231690bb4660e083cdae28caf8ed33e3f66672772ea827253421bade013af57a290a915dbc777f2afccd9cb29e260ecc5ea54cd3a1e25cf66f2937f8061b3ba6b1ebf3129568f16e3dd04d5c50992cc348f3e615af346dbf2c144aeb19932dcfbff0221fae0ed9706b53245176630d011b9cd2d8630848ab1196cf9a3cc0d94392df4295be246e0ac24545c2715a40dcbc57aabffd0a86acec362affaf1bafc5c75b7ca28698a1ac14ea2c8def8ac1a32d3bf65b98aac7d0cb6fd93e5ff16274ad6d0eedf773694f29fc7a234deebc893e4cea4a5483d876e4f35019d6a62f1c407739b68b7a9f5408b4fb854534344fbffe3239feb17c0e7ac269b447bc6246579e1208b6904751eeacb985cbd43bb7792de0b428f1476301c479a3922f61f650c8298fb0b7584b52c7bfcf4dfe51335ab68d571c5815fc78d772346b0b13dbbb8906f076a0452e7e7a414e005dc37cfee85810eccab5999e2d43e13709bf66e8a8936a4283885b158115050789d3b4d9c8dc8026ac720069d78d47dd5e183032f9c53d4c57640fcd6207118d9738f00cd5ddf587f3a7c401d923aa2fb08dba1768728001abc3436cc2b5cf978b558ae58a0578344e7464cd00e719135c70244e2faf1264571a8999789c26f401753e429a1135f18906ebef19e122489622738724a6424cad363bed43304c1285c8da4824fec75d7c51b0a34070d8b976e8e8c8fd50908a7e440092dddd970fd55793e2a4446342bd3daf5b96220977d8f0c","0x0877448694993717a89c57b63640612ac4b0258cb5fdda4a311650c631c35c7313b6d2a094fdb207857d94500c37ab20ea0aa54af951fb04584a37b857981c6d13922e95cfecb70b69ab9a57ee6c13ccf8aa38c52de008ec16d9090aa4bf15db2f4afcdbb1bf4920efe5a1aeeff2c949d43460d67837af87bcdffd9e972340cb40de6d87fa11d83bbfb29e97ef2509097e8dec69a1318132a5dd7d95c1c1e13cc85d37a33c9f7d52379b4a47bf889903c8f3ebd2800526d0916e1aad00e02b682e55bc2865c3ff4ce0cc6aad1bd7d8e2901ea53f3a5e2c025dbb9a00f0ce88583c1dbd3d491ed04ba8260dc06fdb8a9162e022c75e9f057da0abed537b34214df234e1f8b26e7374cfa5470272ef03f7b41f7ed067c4c6011c8a17b2e65340e36af81ecb86420755fe5a0413495e16fabee3f9e5524ab7b12a3cffe20b1df7be32434d7da3fb1f3e9b16f42a4f550501120036b193701ac9eb6f760c2da70e3175a66b10463e43c0442a56217ca7cd25fdb46f3eff28cf1bdfe1b7eb3bf9e85ad8ffde207529c9bb1094dbae4db04a4bff6571c985bd629cdc2b78f739eca6694f32fded6944202859277740267d5dc4c1f74ddd1401c6d514ce23b885723c4618789b5c2ddeffec2179be8dec1347ca4ebed5e8bb10d7d17d41c9709a978fc6189f0c3d49d1b7f41bf8f1dc112f2ece84b6c6a687f44b95e62d274f89fa07bd0d3fdd3ee2a97233e363329ef7096ae5a45b2982859e983f5d989a928e9b88579308ece2391dbde378b81a54d38b3f81225d59f8bb511ba7eb590154ceb8258b804b6da98b3af6f395f5b3f1d12f5fd3c29ef54f31ccea0a36ec2daec0a87030daba8d079093ddde17871c4aa1a7dc3dbd4d760be2152dc250ca2bba34a55daf257b9e3704c3ee244081524cb1ae7c22a0d22f1c65b88b1e534ea1cb8f75cea4a7c03d6786f85327876da72dff1d4d049b51ecc10124279a0cbc151e76ddd475cf3dfeede59a902f4c7145786b5993c8bf8016265ec36298b27d0c6a21c7484fc01a8f14c8c287d14ab86789e34699fdb57f6c43486f0fd9013f2f2c62c60b75b1dc3e4d38a6f7c06e7029f874a204b059d834ffb44c99f843ae33ed0950","0x259310d5134d22e0ef42c3686b2adadc6cd1ae7d7836ac71a69d8ba2d02d0152c320610c12c57cba182c5d1e21198e787b21d0c522106aa8243ec994c4ea0b7959a3269d13566f3d0a3eb5ed276d9e22b33fc12e26cafde04b24ec0fd90455dc26d30a9fc25588b762681ca69aecc19e7971dd4cd063d4e31ee99f3c82015ed9a70e58b9d7cd9a8de38eba90ceffc629e7d6c06e4f2fe9cd45bae557652fe58cc9be54de9a994bf14c3bce787a106778416fbe966e95e51a35ba78d3dc4e4f7551e2791af00d50362493697d55ea6718ba2f089eda330e26100fb5adbb939afaf74982795414422712e8560cec372eaf1a56b50ba4e00e42b145537e94e88eddd7d200d0153edb6dcc12eb298666b0aef9ea495fccfda06b7affe7227bceb41d9ac9dd150df8642cdb11df5ab92b69629b6a5ccdc7ba92b6cf12172217057d291b2fdc6f104e86617be1b7fffeb36af59a018f50c055e24ef9b6daff839083bc9dfeae9101f6aff49f808f603834802d160283cd71b275bf97eb49f5612215cc8fe93875","0xfa082adb51ff0dca75ff57ba7852d794284db5b8d498002a821e5fc2c57a27cc1fe591f12860895b0057bc75ecbff9824bb46e2af06a785b6adfa9e32f49d6235776c3bcace18b330cec1126ac2bb5f3679339037817eab536fed29fe5c62ef790cb74893f1524280b0111e24fc0172130d00a88361e63511eb56a96e552d02c4944544c193189a152844ca49cadae38b7424426a74d61763716a068ba5ca9f3bdc2e0e9b644f1f2e02596bd3f446bb9f13dfb18ad2c9a2ba97771bb994f801affe2e8dda8d638e366c5b8263cc891a8a35e52c79f0856bfeaf0719bd1bfb54acc467783b6c08e55491d39b20f218342991381c38d357a4659baf8d44ddf5045d7f116bcc55f78c28a0dc100d06dff44e639b8e7adf967816c03de54eccdf9f6402a2806889d2cd980f34e5197771f13f1fa6b8c7c732031664bb675ff12d642ae62459e92b1cc28c62349e1636850b8a3ff411e1f14b097f7fa3b23eaa173d17a13f0703eecd7358aa623057325eed381a2ba13c50a13a3d8adaad0295960d925709d6e7cb101e894d9ae8db3dcb82a45570b6e02ab68aa4ea94f8779a9c45a5599","0x71ea3e9ec7ac8a144753ec38e78401b14b489a79266dd0527a4505adca584fe7406d9f7f05ef46d262384fbf1c0607f745a40681d4855aa34c37375b2cf7c99d46b6ae4e3aa9ee209782dce9d167bbff79686e59426a0513b951818ee02a9ea5ed8bcd0f991f46eee44c6e82fc6d07823a9f44f2fd7bfa0e250d6699cf7ad2577eb9eaf0dd9b1595cf018383c3d45956e508fa982bbb7744522a03bac5cba22f58a41801f579434126f5b866dcc6ca0454e9be1c7f2f6649254f3cc09142068f412d5d454b4e4d5b54e459719550f2df1901a18467d9d5297ed4a9eedb9f402f2bfd4bd2e50ab697ea5bef5e7e8082650b823635a4f0f55c18712d0f4d365824c79827d454425aec0b4ea6561ce3f1c5411ab4dff26e2412791cdaa28bf6c8fa53af412828c599d7876508f78f2c82ee67e8357947c6848af143fc5d20409049925cd1b194244466711ce7c34a72a165392564b96e280406a95da927d14ebbb6b999ef446d5ad49881c219dac8ad02d994e059569e91b84f211a4c39a3fbd594a8c835aa5976e0c8899d81a5abaa14301662b9e14fb96ea89862ad898cd7d77bcd2547f0f40471f86d4a4f26e4274f2e95fd9b2b604de867be95630b1ea6ce45ba79acc81b986605e46acda208bd3302ffcc6e83f91bff8362b3f9641ca0227d8b31341e320003","0x2b2acf1e7e043b2c38ea1750a6c31f174b0a8b00137ec3eea24ed9fdf979bf04ed923a2cf5cc05a9acf697d27ccdb2a903a4846729cd9b2eead414da983d4f5bfd0ff4f2e7eb75988e58c3a635c271","0xce0c3b31143f1d68987deaac86a1e079deb07b3d2d497de5ebe8d94486e9a7b300c691621a68b3af4fee781c7c05a931123f910054d096c2e154950d32a26c38edb70dda50a242be4d15ce60c265767b141011cd84aa585c3af798fc1eb5ea63e93e0a426c3e1468f402f7e64f20281a4bd73cc1234174f1762a9a41989f570997036c885b1fdbf9c8153a1d19afb6526a123ca6a2fe6e98c6009f8439f6b6eea881453cc58ef344338ffd04783ce9c28c2e373812a65157643f679ed99ab35f4024e6ee31877e536b03c38616fccc993365143ddaffce39c805b391674070e993c6464156043a84266860c769de218bb5f5698f4c7a9b74142535cbcc08d5b3f747cbf6a7dfbb6c7b0ccc58af4886bc441558496e9c84d80660117777f01cdb84c0a2d3b0f2d8a6eacff5a0e55bd1be6387c3793ae8f5231c59697ae914894a49b3ae13a3a124cbf6cea33b7eb575cf6cd13e6073ddf4d033a3f87366c27089afc03707ef9a44c828388733d70f09bc08de574d07cf193f0a26a08ce8253bfdb26d5306632012c6dae194783deb31b72ac35bbd57f07f1667746d85f5d5b2132b885f8cb0206949780f9406307396dc7ece7938225fc5a55c65ed3608c27f668ba9b08875979e249655d15a4c3d77b1433ab26f56d80e2ca9178d88501ee682a14d07b17635e9968da2d98aa9eb4a5ae639e42eed0c7735313d3308fd079589d5cb2dd381a9298f67325976a6dcd3e38f836e4bc3106885f6348c57c90beadd7cbca17570b90130aaadc7eb0ed2bfb97c5c8a791d0b6b2736d43b0f444909449e6ea32ba706ddfe28c407a85e82e3f22064696d2fd7b37b33e01e0016ad91047f95f0cf5c5d6abc8fd7698c4155c290a1a1db842e77e656c69ad8bc06cea9e00dadbec886ca64af5fe3045ebc8c549bf23e71c634f02da8b250618c169a54e4af45d799f2de6747bde01395a13f1a605e9be5","0x9ced04a51e77ed0730f3420571164ea5247a670b962ebf6b453660748ca5"]},"signature":"0x010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101"}}`), + }, + { + name: "BadCapella", + input: []byte(`{"version":"capella","data":[]}`), + err: "invalid JSON: invalid JSON: json: cannot unmarshal array into Go value of type capella.submitBlockRequestJSON", + }, + { + name: "GoodCapella", + input: []byte(`{"version":"capella","data":{"message":{"slot":"1","parent_hash":"0xae694782c41219774f46891c6365243b97d63d66aeb7827023b8336161615652","block_hash":"0x6462e48cff39c6e4e02e5fe1aa97bf03b23a1aa588f07cfd6296d2b9bb909ce4","builder_pubkey":"0x8efc1675ffb449abc00a6ad8a2808cdf798d96fbb979cf00956012f3983577c9afe69495411a89385421f1cff47dfc98","proposer_pubkey":"0xb7da036d8aedf726e2b3439f95bdf0e68519bb55ab83d5d97a70a5b8510f612ad45a6ecc58b8b5b9b09c6b445491a02b","proposer_fee_recipient":"0x9427A30991170f917d7b83dEf6e44d26577871Ed","gas_limit":"30000000","gas_used":"7675443","value":"22135875749231725"},"execution_payload":{"parent_hash":"0x17f4eeae822cc81533016678413443b95e34517e67f12b4a3a92ff6b66f972ef","fee_recipient":"0x58E809C71e4885cB7B3f1D5c793AB04eD239d779","state_root":"0x3d6e230e6eceb8f3db582777b1500b8b31b9d268339e7b32bba8d6f1311b211d","receipts_root":"0xea760203509bdde017a506b12c825976d12b04db7bce9eca9e1ed007056a3f36","logs_bloom":"0x0c803a8d3c6642adee3185bd914c599317d96487831dabda82461f65700b2528781bdadf785664f9d8b11c4ee1139dfeb056125d2abd67e379cabc6d58f1c3ea304b97cf17fcd8a4c53f4dedeaa041acce062fc8fbc88ffc111577db4a936378749f2fd82b4bfcb880821dd5cbefee984bc1ad116096a64a44a2aac8a1791a7ad3a53d91c584ac69a8973daed6daee4432a198c9935fa0e5c2a4a6ca78b821a5b046e571a5c0961f469d40e429066755fec611afe25b560db07f989933556ce0cea4070ca47677b007b4b9857fc092625f82c84526737dc98e173e34fe6e4d0f1a400fd994298b7c2fa8187331c333c415f0499836ff0eed5c762bf570e67b44","prev_randao":"0x76ff751467270668df463600d26dba58297a986e649bac84ea856712d4779c00","block_number":"2983837628677007840","gas_limit":"6738255228996962210","gas_used":"5573520557770513197","timestamp":"1744720080366521389","extra_data":"0xc648","base_fee_per_gas":"1","block_hash":"0x42c294e902bfc9884c1ce5fef156d4661bb8f0ff488bface37f18c3e7be64b0f","transactions":["0x101b883470f1cb7e0a74561be59e08a6eff6aedd3408c190fd359f0bfb628d2461354b7fe4fdad4b8e72b8775cd44e339ad6b5f22a8f53c418bda2b01200a07f1fe3d010bbb96f5ca0d4919192370c15bc46ed455c797b1b11154be359638f9e487121182fae03a7d26012ed7c85b64a63aa5d56a98ac589f9950a9f5bf1a42c1eea245a98f2f4e743c5f8eac1584893104853dc1b5576826156b371a50c59bcb238d0794a185dc0816dbd8c10a0b0e1b8fbe01c4e8dd719f1e4e9b2ded8613f87f1d01e3ea28e9311d135301b2d1260e4811789e1ecbc33e573346f4da94f4c272e21e23b1d414706429c7f0b40c3de243894349c4a59ece791e5fd086897aef81fc23e4d55bb52b28174c3fa9f2c44d370fbbac1dee561f120560c3dda34a731d4618fd22d595b725efa87bb62f8f93bd7d906c4782a647e2cb14ed293e58bc793852058ab5e6f3df76b30e99102b82c8e7d005e1b675fc74b95032616c590ff08da710dd085be570cc0b2c13891625b44b5b3e1846606c39ad39bb72b","0x4b5edff58cf95969ead0470ab897da6c9d69b517e07fd4ed8fa48c14284a5a060ecb745f66cf1be55fb4905d62d8d376865f7d2d1816844fc4719f5d79ab905474d00f62aed6692e5a93be1b32740a8083fc2a61b0e1fc13ad409410d37f3cb0a5275c966abab015047c15251cd301cd31a7b2a0502f7f953e672d61606616b16d5117163064fb33d97eb566f7fce5f01d3833343c1c97e6221f9f0798415f3a4b87fd472e53a24c1a101e1dd55c8f65c2c0f4ccc4b46a133fda49db5dba96631b4cfd1a05662e42a8e15a26d3148a70be305c85f87dae4217fb91498c4098b946a9042355968b765e2e62bb0cf26d59e534c3af8795fa0f4a44ed0d39d258acd934c3416e4d4a738eaa473526d99bee037765d5f6034c830eb766ef067a1468630fbb65b7c5a862017fe84d4d1961f90c37f18a4bd2509fe2e96cb1e26971900e20295c8a9e9ed77b348d4509a8425090318be5c9d2bcda36bdfabb71bfb36755794f78c877df2825bd736a358933af77eae6edf701ed7ef168f57f677df3445d89c5eefc783184eadd3886fcfd75f5f142bc10904a019acdf7861caa7e0fba3e7831b0a549a56c0f174e80cffb8992346ddf7ce4eeff9e335531df3dff57d5f539bc0d3eac57f70a8f973e0864c87b25c3e0bea72e05eda8a120178186dfbfaa9a00f904f23a","0x452af990975c3bcafee7bde4738fdf32b8479be0e9e30b11b0ccbf31a6f884f4098e47759b7a3eb7d7bd0cfa2510dd654b28d664696aca987f55c7bfe73be1cc70a768cdb2594a13a763dbb991186b8b8b2e913857aadc08f940239d03a0b181ae849d557da5b54bfc966231690bb4660e083cdae28caf8ed33e3f66672772ea827253421bade013af57a290a915dbc777f2afccd9cb29e260ecc5ea54cd3a1e25cf66f2937f8061b3ba6b1ebf3129568f16e3dd04d5c50992cc348f3e615af346dbf2c144aeb19932dcfbff0221fae0ed9706b53245176630d011b9cd2d8630848ab1196cf9a3cc0d94392df4295be246e0ac24545c2715a40dcbc57aabffd0a86acec362affaf1bafc5c75b7ca28698a1ac14ea2c8def8ac1a32d3bf65b98aac7d0cb6fd93e5ff16274ad6d0eedf773694f29fc7a234deebc893e4cea4a5483d876e4f35019d6a62f1c407739b68b7a9f5408b4fb854534344fbffe3239feb17c0e7ac269b447bc6246579e1208b6904751eeacb985cbd43bb7792de0b428f1476301c479a3922f61f650c8298fb0b7584b52c7bfcf4dfe51335ab68d571c5815fc78d772346b0b13dbbb8906f076a0452e7e7a414e005dc37cfee85810eccab5999e2d43e13709bf66e8a8936a4283885b158115050789d3b4d9c8dc8026ac720069d78d47dd5e183032f9c53d4c57640fcd6207118d9738f00cd5ddf587f3a7c401d923aa2fb08dba1768728001abc3436cc2b5cf978b558ae58a0578344e7464cd00e719135c70244e2faf1264571a8999789c26f401753e429a1135f18906ebef19e122489622738724a6424cad363bed43304c1285c8da4824fec75d7c51b0a34070d8b976e8e8c8fd50908a7e440092dddd970fd55793e2a4446342bd3daf5b96220977d8f0c","0x0877448694993717a89c57b63640612ac4b0258cb5fdda4a311650c631c35c7313b6d2a094fdb207857d94500c37ab20ea0aa54af951fb04584a37b857981c6d13922e95cfecb70b69ab9a57ee6c13ccf8aa38c52de008ec16d9090aa4bf15db2f4afcdbb1bf4920efe5a1aeeff2c949d43460d67837af87bcdffd9e972340cb40de6d87fa11d83bbfb29e97ef2509097e8dec69a1318132a5dd7d95c1c1e13cc85d37a33c9f7d52379b4a47bf889903c8f3ebd2800526d0916e1aad00e02b682e55bc2865c3ff4ce0cc6aad1bd7d8e2901ea53f3a5e2c025dbb9a00f0ce88583c1dbd3d491ed04ba8260dc06fdb8a9162e022c75e9f057da0abed537b34214df234e1f8b26e7374cfa5470272ef03f7b41f7ed067c4c6011c8a17b2e65340e36af81ecb86420755fe5a0413495e16fabee3f9e5524ab7b12a3cffe20b1df7be32434d7da3fb1f3e9b16f42a4f550501120036b193701ac9eb6f760c2da70e3175a66b10463e43c0442a56217ca7cd25fdb46f3eff28cf1bdfe1b7eb3bf9e85ad8ffde207529c9bb1094dbae4db04a4bff6571c985bd629cdc2b78f739eca6694f32fded6944202859277740267d5dc4c1f74ddd1401c6d514ce23b885723c4618789b5c2ddeffec2179be8dec1347ca4ebed5e8bb10d7d17d41c9709a978fc6189f0c3d49d1b7f41bf8f1dc112f2ece84b6c6a687f44b95e62d274f89fa07bd0d3fdd3ee2a97233e363329ef7096ae5a45b2982859e983f5d989a928e9b88579308ece2391dbde378b81a54d38b3f81225d59f8bb511ba7eb590154ceb8258b804b6da98b3af6f395f5b3f1d12f5fd3c29ef54f31ccea0a36ec2daec0a87030daba8d079093ddde17871c4aa1a7dc3dbd4d760be2152dc250ca2bba34a55daf257b9e3704c3ee244081524cb1ae7c22a0d22f1c65b88b1e534ea1cb8f75cea4a7c03d6786f85327876da72dff1d4d049b51ecc10124279a0cbc151e76ddd475cf3dfeede59a902f4c7145786b5993c8bf8016265ec36298b27d0c6a21c7484fc01a8f14c8c287d14ab86789e34699fdb57f6c43486f0fd9013f2f2c62c60b75b1dc3e4d38a6f7c06e7029f874a204b059d834ffb44c99f843ae33ed0950","0x259310d5134d22e0ef42c3686b2adadc6cd1ae7d7836ac71a69d8ba2d02d0152c320610c12c57cba182c5d1e21198e787b21d0c522106aa8243ec994c4ea0b7959a3269d13566f3d0a3eb5ed276d9e22b33fc12e26cafde04b24ec0fd90455dc26d30a9fc25588b762681ca69aecc19e7971dd4cd063d4e31ee99f3c82015ed9a70e58b9d7cd9a8de38eba90ceffc629e7d6c06e4f2fe9cd45bae557652fe58cc9be54de9a994bf14c3bce787a106778416fbe966e95e51a35ba78d3dc4e4f7551e2791af00d50362493697d55ea6718ba2f089eda330e26100fb5adbb939afaf74982795414422712e8560cec372eaf1a56b50ba4e00e42b145537e94e88eddd7d200d0153edb6dcc12eb298666b0aef9ea495fccfda06b7affe7227bceb41d9ac9dd150df8642cdb11df5ab92b69629b6a5ccdc7ba92b6cf12172217057d291b2fdc6f104e86617be1b7fffeb36af59a018f50c055e24ef9b6daff839083bc9dfeae9101f6aff49f808f603834802d160283cd71b275bf97eb49f5612215cc8fe93875","0xfa082adb51ff0dca75ff57ba7852d794284db5b8d498002a821e5fc2c57a27cc1fe591f12860895b0057bc75ecbff9824bb46e2af06a785b6adfa9e32f49d6235776c3bcace18b330cec1126ac2bb5f3679339037817eab536fed29fe5c62ef790cb74893f1524280b0111e24fc0172130d00a88361e63511eb56a96e552d02c4944544c193189a152844ca49cadae38b7424426a74d61763716a068ba5ca9f3bdc2e0e9b644f1f2e02596bd3f446bb9f13dfb18ad2c9a2ba97771bb994f801affe2e8dda8d638e366c5b8263cc891a8a35e52c79f0856bfeaf0719bd1bfb54acc467783b6c08e55491d39b20f218342991381c38d357a4659baf8d44ddf5045d7f116bcc55f78c28a0dc100d06dff44e639b8e7adf967816c03de54eccdf9f6402a2806889d2cd980f34e5197771f13f1fa6b8c7c732031664bb675ff12d642ae62459e92b1cc28c62349e1636850b8a3ff411e1f14b097f7fa3b23eaa173d17a13f0703eecd7358aa623057325eed381a2ba13c50a13a3d8adaad0295960d925709d6e7cb101e894d9ae8db3dcb82a45570b6e02ab68aa4ea94f8779a9c45a5599","0x71ea3e9ec7ac8a144753ec38e78401b14b489a79266dd0527a4505adca584fe7406d9f7f05ef46d262384fbf1c0607f745a40681d4855aa34c37375b2cf7c99d46b6ae4e3aa9ee209782dce9d167bbff79686e59426a0513b951818ee02a9ea5ed8bcd0f991f46eee44c6e82fc6d07823a9f44f2fd7bfa0e250d6699cf7ad2577eb9eaf0dd9b1595cf018383c3d45956e508fa982bbb7744522a03bac5cba22f58a41801f579434126f5b866dcc6ca0454e9be1c7f2f6649254f3cc09142068f412d5d454b4e4d5b54e459719550f2df1901a18467d9d5297ed4a9eedb9f402f2bfd4bd2e50ab697ea5bef5e7e8082650b823635a4f0f55c18712d0f4d365824c79827d454425aec0b4ea6561ce3f1c5411ab4dff26e2412791cdaa28bf6c8fa53af412828c599d7876508f78f2c82ee67e8357947c6848af143fc5d20409049925cd1b194244466711ce7c34a72a165392564b96e280406a95da927d14ebbb6b999ef446d5ad49881c219dac8ad02d994e059569e91b84f211a4c39a3fbd594a8c835aa5976e0c8899d81a5abaa14301662b9e14fb96ea89862ad898cd7d77bcd2547f0f40471f86d4a4f26e4274f2e95fd9b2b604de867be95630b1ea6ce45ba79acc81b986605e46acda208bd3302ffcc6e83f91bff8362b3f9641ca0227d8b31341e320003","0x2b2acf1e7e043b2c38ea1750a6c31f174b0a8b00137ec3eea24ed9fdf979bf04ed923a2cf5cc05a9acf697d27ccdb2a903a4846729cd9b2eead414da983d4f5bfd0ff4f2e7eb75988e58c3a635c271","0xce0c3b31143f1d68987deaac86a1e079deb07b3d2d497de5ebe8d94486e9a7b300c691621a68b3af4fee781c7c05a931123f910054d096c2e154950d32a26c38edb70dda50a242be4d15ce60c265767b141011cd84aa585c3af798fc1eb5ea63e93e0a426c3e1468f402f7e64f20281a4bd73cc1234174f1762a9a41989f570997036c885b1fdbf9c8153a1d19afb6526a123ca6a2fe6e98c6009f8439f6b6eea881453cc58ef344338ffd04783ce9c28c2e373812a65157643f679ed99ab35f4024e6ee31877e536b03c38616fccc993365143ddaffce39c805b391674070e993c6464156043a84266860c769de218bb5f5698f4c7a9b74142535cbcc08d5b3f747cbf6a7dfbb6c7b0ccc58af4886bc441558496e9c84d80660117777f01cdb84c0a2d3b0f2d8a6eacff5a0e55bd1be6387c3793ae8f5231c59697ae914894a49b3ae13a3a124cbf6cea33b7eb575cf6cd13e6073ddf4d033a3f87366c27089afc03707ef9a44c828388733d70f09bc08de574d07cf193f0a26a08ce8253bfdb26d5306632012c6dae194783deb31b72ac35bbd57f07f1667746d85f5d5b2132b885f8cb0206949780f9406307396dc7ece7938225fc5a55c65ed3608c27f668ba9b08875979e249655d15a4c3d77b1433ab26f56d80e2ca9178d88501ee682a14d07b17635e9968da2d98aa9eb4a5ae639e42eed0c7735313d3308fd079589d5cb2dd381a9298f67325976a6dcd3e38f836e4bc3106885f6348c57c90beadd7cbca17570b90130aaadc7eb0ed2bfb97c5c8a791d0b6b2736d43b0f444909449e6ea32ba706ddfe28c407a85e82e3f22064696d2fd7b37b33e01e0016ad91047f95f0cf5c5d6abc8fd7698c4155c290a1a1db842e77e656c69ad8bc06cea9e00dadbec886ca64af5fe3045ebc8c549bf23e71c634f02da8b250618c169a54e4af45d799f2de6747bde01395a13f1a605e9be5","0x9ced04a51e77ed0730f3420571164ea5247a670b962ebf6b453660748ca5"],"withdrawals":[{"index":"2","validator_index":"3","address":"0x000102030405060708090a0b0c0d0e0f10111213","amount":"1000000000000000000"}]},"signature":"0x010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101"}}`), + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + var res spec.VersionedSubmitBlockRequest + err := json.Unmarshal(test.input, &res) + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + rt, err := json.Marshal(&res) + require.NoError(t, err) + assert.Equal(t, string(test.input), string(rt)) + } + }) + } +} diff --git a/spec/versionedsubmitblockrequest_test.go b/spec/versionedsubmitblockrequest_test.go new file mode 100644 index 0000000..b663207 --- /dev/null +++ b/spec/versionedsubmitblockrequest_test.go @@ -0,0 +1,1838 @@ +// Copyright © 2022 Attestant Limited. +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +package spec_test + +import ( + "testing" + + "github.com/attestantio/go-builder-client/api/bellatrix" + "github.com/attestantio/go-builder-client/api/capella" + apiv1 "github.com/attestantio/go-builder-client/api/v1" + "github.com/attestantio/go-builder-client/spec" + consensusspec "github.com/attestantio/go-eth2-client/spec" + consensusbellatrix "github.com/attestantio/go-eth2-client/spec/bellatrix" + consensuscapella "github.com/attestantio/go-eth2-client/spec/capella" + "github.com/attestantio/go-eth2-client/spec/phase0" + "github.com/holiman/uint256" + "github.com/stretchr/testify/require" +) + +func TestVersionedSubmitBlockRequestEmpty(t *testing.T) { + empty := &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + } + require.True(t, empty.IsEmpty()) + + mismatch1 := &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Capella: &capella.SubmitBlockRequest{}, + } + require.True(t, mismatch1.IsEmpty()) + + mismatch2 := &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + } + require.True(t, mismatch2.IsEmpty()) + + incorrectVersion := &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + Capella: &capella.SubmitBlockRequest{}, + } + require.True(t, incorrectVersion.IsEmpty()) + + notEmpty := &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + } + require.False(t, notEmpty.IsEmpty()) +} + +func TestVersionedSubmitBlockRequestSlot(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res uint64 + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + Slot: 12345, + }, + }, + }, + res: 12345, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + Slot: 12345, + }, + }, + }, + res: 12345, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.Slot() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestBlockHash(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res phase0.Hash32 + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + BlockHash: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + }, + }, + res: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + BlockHash: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + }, + }, + res: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.BlockHash() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestBuilder(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res phase0.BLSPubKey + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + BuilderPubkey: phase0.BLSPubKey{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + }, + }, + }, + }, + res: phase0.BLSPubKey{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + }, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + BuilderPubkey: phase0.BLSPubKey{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + }, + }, + }, + }, + res: phase0.BLSPubKey{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.Builder() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestProposerFeeRecipient(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res consensusbellatrix.ExecutionAddress + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + ProposerFeeRecipient: consensusbellatrix.ExecutionAddress{ + 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, + 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, + }, + }, + }, + }, + res: consensusbellatrix.ExecutionAddress{ + 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, + 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, + }, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + ProposerFeeRecipient: consensusbellatrix.ExecutionAddress{ + 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, + 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, + }, + }, + }, + }, + res: consensusbellatrix.ExecutionAddress{ + 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, + 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.ProposerFeeRecipient() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestProposerPubkey(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res phase0.BLSPubKey + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + ProposerPubkey: phase0.BLSPubKey{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + }, + }, + }, + }, + res: phase0.BLSPubKey{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + }, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + ProposerPubkey: phase0.BLSPubKey{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + }, + }, + }, + }, + res: phase0.BLSPubKey{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.ProposerPubkey() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestParentHash(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res phase0.Hash32 + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + ParentHash: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + }, + }, + res: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + ParentHash: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + }, + }, + res: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.ParentHash() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestValue(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res *uint256.Int + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + Value: uint256.NewInt(12345), + }, + }, + }, + res: uint256.NewInt(12345), + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + Value: uint256.NewInt(12345), + }, + }, + }, + res: uint256.NewInt(12345), + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.Value() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestMessageHashTreeRoot(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res phase0.Root + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + Value: uint256.NewInt(12345), + }, + }, + }, + res: phase0.Root{ + 0x6e, 0x21, 0x57, 0xbe, 0x11, 0xe5, 0xda, 0xc3, 0x30, 0x6b, 0xd6, 0x41, 0x61, 0x17, 0x93, 0x30, + 0x53, 0xe8, 0x7d, 0x66, 0xb2, 0xfc, 0xcd, 0x7b, 0xd1, 0x7f, 0x27, 0xee, 0x90, 0xb4, 0x6c, 0x7c, + }, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataMessage", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data message", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + Value: uint256.NewInt(12345), + }, + }, + }, + res: phase0.Root{ + 0x6e, 0x21, 0x57, 0xbe, 0x11, 0xe5, 0xda, 0xc3, 0x30, 0x6b, 0xd6, 0x41, 0x61, 0x17, 0x93, 0x30, + 0x53, 0xe8, 0x7d, 0x66, 0xb2, 0xfc, 0xcd, 0x7b, 0xd1, 0x7f, 0x27, 0xee, 0x90, 0xb4, 0x6c, 0x7c, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.MessageHashTreeRoot() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestSignature(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res phase0.BLSSignature + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + Signature: phase0.BLSSignature{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, + }, + }, + }, + res: phase0.BLSSignature{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, + }, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + Signature: phase0.BLSSignature{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, + }, + }, + }, + res: phase0.BLSSignature{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.Signature() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestExecutionPayloadBlockHash(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res phase0.Hash32 + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + ExecutionPayload: &consensusbellatrix.ExecutionPayload{ + BlockHash: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + }, + }, + res: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + ExecutionPayload: &consensuscapella.ExecutionPayload{ + BlockHash: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + }, + }, + res: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.ExecutionPayloadBlockHash() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestExecutionPayloadParentHash(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res phase0.Hash32 + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + ExecutionPayload: &consensusbellatrix.ExecutionPayload{ + ParentHash: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + }, + }, + res: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + ExecutionPayload: &consensuscapella.ExecutionPayload{ + ParentHash: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + }, + }, + res: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.ExecutionPayloadParentHash() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestPrevRandao(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res phase0.Hash32 + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + ExecutionPayload: &consensusbellatrix.ExecutionPayload{ + PrevRandao: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + }, + }, + res: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + ExecutionPayload: &consensuscapella.ExecutionPayload{ + PrevRandao: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + }, + }, + res: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.PrevRandao() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestGasLimit(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res uint64 + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + ExecutionPayload: &consensusbellatrix.ExecutionPayload{ + GasLimit: 123, + }, + }, + }, + res: 123, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + ExecutionPayload: &consensuscapella.ExecutionPayload{ + GasLimit: 123, + }, + }, + }, + res: 123, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.GasLimit() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestGasUsed(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res uint64 + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + ExecutionPayload: &consensusbellatrix.ExecutionPayload{ + GasUsed: 123, + }, + }, + }, + res: 123, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + ExecutionPayload: &consensuscapella.ExecutionPayload{ + GasUsed: 123, + }, + }, + }, + res: 123, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.GasUsed() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestBlockNumber(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res uint64 + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + ExecutionPayload: &consensusbellatrix.ExecutionPayload{ + BlockNumber: 123, + }, + }, + }, + res: 123, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + ExecutionPayload: &consensuscapella.ExecutionPayload{ + BlockNumber: 123, + }, + }, + }, + res: 123, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.BlockNumber() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestTimestamp(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res uint64 + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + ExecutionPayload: &consensusbellatrix.ExecutionPayload{ + Timestamp: 12345, + }, + }, + }, + res: 12345, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + ExecutionPayload: &consensuscapella.ExecutionPayload{ + Timestamp: 12345, + }, + }, + }, + res: 12345, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.Timestamp() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestTransactions(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res []consensusbellatrix.Transaction + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + err: "unsupported version", + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "no data", + }, + { + name: "BellatrixNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + ExecutionPayload: &consensusbellatrix.ExecutionPayload{ + Transactions: []consensusbellatrix.Transaction{ + {0x00}, + {0x01}, + }, + }, + }, + }, + res: []consensusbellatrix.Transaction{ + {0x00}, + {0x01}, + }, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + ExecutionPayload: &consensuscapella.ExecutionPayload{ + Transactions: []consensusbellatrix.Transaction{ + {0x00}, + {0x01}, + }, + }, + }, + }, + res: []consensusbellatrix.Transaction{ + {0x00}, + {0x01}, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.Transactions() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestWithdrawals(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res []*consensuscapella.Withdrawal + err string + }{ + { + name: "Empty", + err: "nil struct", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + err: "unsupported version", + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + err: "no data", + }, + { + name: "CapellaNoDataExecutionPayload", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{}, + }, + err: "no data execution payload", + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + ExecutionPayload: &consensuscapella.ExecutionPayload{ + Withdrawals: []*consensuscapella.Withdrawal{ + { + Index: 5, + ValidatorIndex: 10, + Address: consensusbellatrix.ExecutionAddress{}, + Amount: 12345, + }, + { + Index: 10, + ValidatorIndex: 20, + Address: consensusbellatrix.ExecutionAddress{}, + Amount: 12345, + }, + }, + }, + }, + }, + res: []*consensuscapella.Withdrawal{ + { + Index: 5, + ValidatorIndex: 10, + Address: consensusbellatrix.ExecutionAddress{}, + Amount: 12345, + }, + { + Index: 10, + ValidatorIndex: 20, + Address: consensusbellatrix.ExecutionAddress{}, + Amount: 12345, + }, + }, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + res, err := test.request.Withdrawals() + if test.err != "" { + require.EqualError(t, err, test.err) + } else { + require.NoError(t, err) + require.Equal(t, test.res, res) + } + }) + } +} + +func TestVersionedSubmitBlockRequestString(t *testing.T) { + tests := []struct { + name string + request *spec.VersionedSubmitBlockRequest + res string + }{ + { + name: "Empty", + }, + { + name: "UnsupportedVersion", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionAltair, + }, + res: `ERR: json: error calling MarshalJSON for type *spec.VersionedSubmitBlockRequest: unsupported data version altair`, + }, + { + name: "BellatrixNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + }, + res: `ERR: json: error calling MarshalJSON for type *spec.VersionedSubmitBlockRequest: no bellatrix data`, + }, + { + name: "BellatrixGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionBellatrix, + Bellatrix: &bellatrix.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + Slot: 123, + Value: uint256.NewInt(12345), + }, + ExecutionPayload: &consensusbellatrix.ExecutionPayload{ + ParentHash: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + }, + Signature: phase0.BLSSignature{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, + }, + }, + }, + res: `{"version":"bellatrix","data":{"message":{"slot":"123","parent_hash":"0x0000000000000000000000000000000000000000000000000000000000000000","block_hash":"0x0000000000000000000000000000000000000000000000000000000000000000","builder_pubkey":"0x000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000","proposer_pubkey":"0x000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000","proposer_fee_recipient":"0x0000000000000000000000000000000000000000","gas_limit":"0","gas_used":"0","value":"12345"},"execution_payload":{"parent_hash":"0x000102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f","fee_recipient":"0x0000000000000000000000000000000000000000","state_root":"0x0000000000000000000000000000000000000000000000000000000000000000","receipts_root":"0x0000000000000000000000000000000000000000000000000000000000000000","logs_bloom":"0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000","prev_randao":"0x0000000000000000000000000000000000000000000000000000000000000000","block_number":"0","gas_limit":"0","gas_used":"0","timestamp":"0","extra_data":"0x","base_fee_per_gas":"0","block_hash":"0x0000000000000000000000000000000000000000000000000000000000000000","transactions":[]},"signature":"0x000102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f202122232425262728292a2b2c2d2e2f303132333435363738393a3b3c3d3e3f0000000000000000000000000000000000000000000000000000000000000000"}}`, + }, + { + name: "CapellaNoData", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + }, + res: `ERR: json: error calling MarshalJSON for type *spec.VersionedSubmitBlockRequest: no capella data`, + }, + { + name: "CapellaGood", + request: &spec.VersionedSubmitBlockRequest{ + Version: consensusspec.DataVersionCapella, + Capella: &capella.SubmitBlockRequest{ + Message: &apiv1.BidTrace{ + Slot: 123, + Value: uint256.NewInt(12345), + }, + ExecutionPayload: &consensuscapella.ExecutionPayload{ + ParentHash: phase0.Hash32{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + }, + Withdrawals: make([]*consensuscapella.Withdrawal, 0), + }, + Signature: phase0.BLSSignature{ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, + }, + }, + }, + res: `{"version":"capella","data":{"message":{"slot":"123","parent_hash":"0x0000000000000000000000000000000000000000000000000000000000000000","block_hash":"0x0000000000000000000000000000000000000000000000000000000000000000","builder_pubkey":"0x000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000","proposer_pubkey":"0x000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000","proposer_fee_recipient":"0x0000000000000000000000000000000000000000","gas_limit":"0","gas_used":"0","value":"12345"},"execution_payload":{"parent_hash":"0x000102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f","fee_recipient":"0x0000000000000000000000000000000000000000","state_root":"0x0000000000000000000000000000000000000000000000000000000000000000","receipts_root":"0x0000000000000000000000000000000000000000000000000000000000000000","logs_bloom":"0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000","prev_randao":"0x0000000000000000000000000000000000000000000000000000000000000000","block_number":"0","gas_limit":"0","gas_used":"0","timestamp":"0","extra_data":"0x","base_fee_per_gas":"0","block_hash":"0x0000000000000000000000000000000000000000000000000000000000000000","transactions":[],"withdrawals":[]},"signature":"0x000102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f202122232425262728292a2b2c2d2e2f303132333435363738393a3b3c3d3e3f0000000000000000000000000000000000000000000000000000000000000000"}}`, + }, + } + + for _, test := range tests { + t.Run(test.name, func(t *testing.T) { + require.Equal(t, test.res, test.request.String()) + }) + } +} From c1ca05d6e8b799c622c10016cc6f53555818f169 Mon Sep 17 00:00:00 2001 From: avalonche Date: Mon, 10 Jul 2023 16:04:35 +1000 Subject: [PATCH 2/2] linting --- spec/versionedsubmitblockrequest.go | 41 ++++++++-------- spec/versionedsubmitblockrequest_test.go | 62 ++++++++++++------------ 2 files changed, 53 insertions(+), 50 deletions(-) diff --git a/spec/versionedsubmitblockrequest.go b/spec/versionedsubmitblockrequest.go index c50be99..b5e600f 100644 --- a/spec/versionedsubmitblockrequest.go +++ b/spec/versionedsubmitblockrequest.go @@ -20,6 +20,7 @@ import ( "github.com/attestantio/go-builder-client/api/bellatrix" "github.com/attestantio/go-builder-client/api/capella" + v1 "github.com/attestantio/go-builder-client/api/v1" consensusspec "github.com/attestantio/go-eth2-client/spec" consensusbellatrix "github.com/attestantio/go-eth2-client/spec/bellatrix" consensuscapella "github.com/attestantio/go-eth2-client/spec/capella" @@ -46,7 +47,7 @@ func (v *VersionedSubmitBlockRequest) IsEmpty() bool { } } -// Slot returns the slot of the request +// Slot returns the slot of the request. func (v *VersionedSubmitBlockRequest) Slot() (uint64, error) { if v == nil { return 0, errors.New("nil struct") @@ -154,8 +155,8 @@ func (v *VersionedSubmitBlockRequest) ProposerFeeRecipient() (consensusbellatrix } } -// ProposerPubkey returns the proposer fee recipient of the request. -func (v *VersionedSubmitBlockRequest) ProposerPubkey() (phase0.BLSPubKey, error) { +// ProposerPubKey returns the proposer fee recipient of the request. +func (v *VersionedSubmitBlockRequest) ProposerPubKey() (phase0.BLSPubKey, error) { if v == nil { return phase0.BLSPubKey{}, errors.New("nil struct") } @@ -235,30 +236,30 @@ func (v *VersionedSubmitBlockRequest) Value() (*uint256.Int, error) { } } -// MessageHashTreeRoot returns the hash tree root of the message of the bid. -func (v *VersionedSubmitBlockRequest) MessageHashTreeRoot() (phase0.Root, error) { +// BidTrace returns the bid trace of the request. +func (v *VersionedSubmitBlockRequest) BidTrace() (*v1.BidTrace, error) { if v == nil { - return phase0.Root{}, errors.New("nil struct") + return nil, errors.New("nil struct") } switch v.Version { case consensusspec.DataVersionBellatrix: if v.Bellatrix == nil { - return phase0.Root{}, errors.New("no data") + return nil, errors.New("no data") } if v.Bellatrix.Message == nil { - return phase0.Root{}, errors.New("no data message") + return nil, errors.New("no data message") } - return v.Bellatrix.Message.HashTreeRoot() + return v.Bellatrix.Message, nil case consensusspec.DataVersionCapella: if v.Capella == nil { - return phase0.Root{}, errors.New("no data") + return nil, errors.New("no data") } if v.Capella.Message == nil { - return phase0.Root{}, errors.New("no data message") + return nil, errors.New("no data message") } - return v.Capella.Message.HashTreeRoot() + return v.Capella.Message, nil default: - return phase0.Root{}, errors.New("unsupported version") + return nil, errors.New("unsupported version") } } @@ -283,7 +284,7 @@ func (v *VersionedSubmitBlockRequest) Signature() (phase0.BLSSignature, error) { } } -// ExecutionPayloadBlockHash returns the block hash of the payload +// ExecutionPayloadBlockHash returns the block hash of the payload. func (v *VersionedSubmitBlockRequest) ExecutionPayloadBlockHash() (phase0.Hash32, error) { if v == nil { return phase0.Hash32{}, errors.New("nil struct") @@ -310,7 +311,7 @@ func (v *VersionedSubmitBlockRequest) ExecutionPayloadBlockHash() (phase0.Hash32 } } -// ExecutionPayloadParentHash returns the block hash of the payload +// ExecutionPayloadParentHash returns the block hash of the payload. func (v *VersionedSubmitBlockRequest) ExecutionPayloadParentHash() (phase0.Hash32, error) { if v == nil { return phase0.Hash32{}, errors.New("nil struct") @@ -337,7 +338,7 @@ func (v *VersionedSubmitBlockRequest) ExecutionPayloadParentHash() (phase0.Hash3 } } -// PrevRandao returns the prev randao of the payload +// PrevRandao returns the prev randao of the payload. func (v *VersionedSubmitBlockRequest) PrevRandao() (phase0.Hash32, error) { if v == nil { return phase0.Hash32{}, errors.New("nil struct") @@ -364,7 +365,7 @@ func (v *VersionedSubmitBlockRequest) PrevRandao() (phase0.Hash32, error) { } } -// GasLimit returns the prev randao of the payload +// GasLimit returns the prev randao of the payload. func (v *VersionedSubmitBlockRequest) GasLimit() (uint64, error) { if v == nil { return 0, errors.New("nil struct") @@ -391,7 +392,7 @@ func (v *VersionedSubmitBlockRequest) GasLimit() (uint64, error) { } } -// GasUsed returns the prev randao of the payload +// GasUsed returns the prev randao of the payload. func (v *VersionedSubmitBlockRequest) GasUsed() (uint64, error) { if v == nil { return 0, errors.New("nil struct") @@ -472,7 +473,7 @@ func (v *VersionedSubmitBlockRequest) Timestamp() (uint64, error) { } } -// Transactions returns the transactions of the payload +// Transactions returns the transactions of the payload. func (v *VersionedSubmitBlockRequest) Transactions() ([]consensusbellatrix.Transaction, error) { if v == nil { return nil, errors.New("nil struct") @@ -499,7 +500,7 @@ func (v *VersionedSubmitBlockRequest) Transactions() ([]consensusbellatrix.Trans } } -// Withdrawals returns the withdrawals of the payload +// Withdrawals returns the withdrawals of the payload. func (v *VersionedSubmitBlockRequest) Withdrawals() ([]*consensuscapella.Withdrawal, error) { if v == nil { return nil, errors.New("nil struct") diff --git a/spec/versionedsubmitblockrequest_test.go b/spec/versionedsubmitblockrequest_test.go index b663207..d43fb23 100644 --- a/spec/versionedsubmitblockrequest_test.go +++ b/spec/versionedsubmitblockrequest_test.go @@ -18,7 +18,7 @@ import ( "github.com/attestantio/go-builder-client/api/bellatrix" "github.com/attestantio/go-builder-client/api/capella" - apiv1 "github.com/attestantio/go-builder-client/api/v1" + v1 "github.com/attestantio/go-builder-client/api/v1" "github.com/attestantio/go-builder-client/spec" consensusspec "github.com/attestantio/go-eth2-client/spec" consensusbellatrix "github.com/attestantio/go-eth2-client/spec/bellatrix" @@ -98,7 +98,7 @@ func TestVersionedSubmitBlockRequestSlot(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionBellatrix, Bellatrix: &bellatrix.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ Slot: 12345, }, }, @@ -125,7 +125,7 @@ func TestVersionedSubmitBlockRequestSlot(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionCapella, Capella: &capella.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ Slot: 12345, }, }, @@ -185,7 +185,7 @@ func TestVersionedSubmitBlockRequestBlockHash(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionBellatrix, Bellatrix: &bellatrix.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ BlockHash: phase0.Hash32{ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, @@ -218,7 +218,7 @@ func TestVersionedSubmitBlockRequestBlockHash(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionCapella, Capella: &capella.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ BlockHash: phase0.Hash32{ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, @@ -284,7 +284,7 @@ func TestVersionedSubmitBlockRequestBuilder(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionBellatrix, Bellatrix: &bellatrix.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ BuilderPubkey: phase0.BLSPubKey{ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, @@ -319,7 +319,7 @@ func TestVersionedSubmitBlockRequestBuilder(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionCapella, Capella: &capella.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ BuilderPubkey: phase0.BLSPubKey{ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, @@ -387,7 +387,7 @@ func TestVersionedSubmitBlockRequestProposerFeeRecipient(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionBellatrix, Bellatrix: &bellatrix.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ ProposerFeeRecipient: consensusbellatrix.ExecutionAddress{ 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, @@ -420,7 +420,7 @@ func TestVersionedSubmitBlockRequestProposerFeeRecipient(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionCapella, Capella: &capella.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ ProposerFeeRecipient: consensusbellatrix.ExecutionAddress{ 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, @@ -448,7 +448,7 @@ func TestVersionedSubmitBlockRequestProposerFeeRecipient(t *testing.T) { } } -func TestVersionedSubmitBlockRequestProposerPubkey(t *testing.T) { +func TestVersionedSubmitBlockRequestProposerPubKey(t *testing.T) { tests := []struct { name string request *spec.VersionedSubmitBlockRequest @@ -486,7 +486,7 @@ func TestVersionedSubmitBlockRequestProposerPubkey(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionBellatrix, Bellatrix: &bellatrix.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ ProposerPubkey: phase0.BLSPubKey{ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, @@ -521,7 +521,7 @@ func TestVersionedSubmitBlockRequestProposerPubkey(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionCapella, Capella: &capella.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ ProposerPubkey: phase0.BLSPubKey{ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, @@ -540,7 +540,7 @@ func TestVersionedSubmitBlockRequestProposerPubkey(t *testing.T) { for _, test := range tests { t.Run(test.name, func(t *testing.T) { - res, err := test.request.ProposerPubkey() + res, err := test.request.ProposerPubKey() if test.err != "" { require.EqualError(t, err, test.err) } else { @@ -589,7 +589,7 @@ func TestVersionedSubmitBlockRequestParentHash(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionBellatrix, Bellatrix: &bellatrix.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ ParentHash: phase0.Hash32{ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, @@ -622,7 +622,7 @@ func TestVersionedSubmitBlockRequestParentHash(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionCapella, Capella: &capella.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ ParentHash: phase0.Hash32{ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, @@ -688,7 +688,7 @@ func TestVersionedSubmitBlockRequestValue(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionBellatrix, Bellatrix: &bellatrix.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ Value: uint256.NewInt(12345), }, }, @@ -715,7 +715,7 @@ func TestVersionedSubmitBlockRequestValue(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionCapella, Capella: &capella.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ Value: uint256.NewInt(12345), }, }, @@ -737,11 +737,11 @@ func TestVersionedSubmitBlockRequestValue(t *testing.T) { } } -func TestVersionedSubmitBlockRequestMessageHashTreeRoot(t *testing.T) { +func TestVersionedSubmitBlockRequestBidTrace(t *testing.T) { tests := []struct { name string request *spec.VersionedSubmitBlockRequest - res phase0.Root + res *v1.BidTrace err string }{ { @@ -775,14 +775,15 @@ func TestVersionedSubmitBlockRequestMessageHashTreeRoot(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionBellatrix, Bellatrix: &bellatrix.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ + Slot: 123, Value: uint256.NewInt(12345), }, }, }, - res: phase0.Root{ - 0x6e, 0x21, 0x57, 0xbe, 0x11, 0xe5, 0xda, 0xc3, 0x30, 0x6b, 0xd6, 0x41, 0x61, 0x17, 0x93, 0x30, - 0x53, 0xe8, 0x7d, 0x66, 0xb2, 0xfc, 0xcd, 0x7b, 0xd1, 0x7f, 0x27, 0xee, 0x90, 0xb4, 0x6c, 0x7c, + res: &v1.BidTrace{ + Slot: 123, + Value: uint256.NewInt(12345), }, }, { @@ -805,21 +806,22 @@ func TestVersionedSubmitBlockRequestMessageHashTreeRoot(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionCapella, Capella: &capella.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ + Slot: 123, Value: uint256.NewInt(12345), }, }, }, - res: phase0.Root{ - 0x6e, 0x21, 0x57, 0xbe, 0x11, 0xe5, 0xda, 0xc3, 0x30, 0x6b, 0xd6, 0x41, 0x61, 0x17, 0x93, 0x30, - 0x53, 0xe8, 0x7d, 0x66, 0xb2, 0xfc, 0xcd, 0x7b, 0xd1, 0x7f, 0x27, 0xee, 0x90, 0xb4, 0x6c, 0x7c, + res: &v1.BidTrace{ + Slot: 123, + Value: uint256.NewInt(12345), }, }, } for _, test := range tests { t.Run(test.name, func(t *testing.T) { - res, err := test.request.MessageHashTreeRoot() + res, err := test.request.BidTrace() if test.err != "" { require.EqualError(t, err, test.err) } else { @@ -1775,7 +1777,7 @@ func TestVersionedSubmitBlockRequestString(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionBellatrix, Bellatrix: &bellatrix.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ Slot: 123, Value: uint256.NewInt(12345), }, @@ -1807,7 +1809,7 @@ func TestVersionedSubmitBlockRequestString(t *testing.T) { request: &spec.VersionedSubmitBlockRequest{ Version: consensusspec.DataVersionCapella, Capella: &capella.SubmitBlockRequest{ - Message: &apiv1.BidTrace{ + Message: &v1.BidTrace{ Slot: 123, Value: uint256.NewInt(12345), },