diff --git a/README.md b/README.md index 202d9cb6..bbb9c2de 100644 --- a/README.md +++ b/README.md @@ -43,10 +43,11 @@ The relay consists of three main components, which are designed to run and scale - The relay services need access to one or more beacon node for event subscriptions (in particular the `head` and `payload_attributes` topics). - You can specify multiple beacon nodes by providing a comma separated list of beacon node URIs. -- The beacon nodes need to support the []`payload_attributes` SSE event](https://github.com/ethereum/beacon-APIs/pull/305). +- The beacon nodes need to support the [`payload_attributes` SSE event](https://github.com/ethereum/beacon-APIs/pull/305). +- Support the [v2 publish block endpoint](https://github.com/ethereum/beacon-APIs/pull/317) - As of now, this is either: - - **Lighthouse+** (with `--always-prepare-payload` and `--prepare-payload-lookahead 12000` flags, and some junk feeRecipeint), with the [validate-before-broadcast patch](https://github.com/sigp/lighthouse/pull/4168). Here's a [quick guide](https://gist.github.com/metachris/bcae9ae42e2fc834804241f991351c4e) for setting up Lighthouse. - - **Prysm** with the [validate-before-broadcast patch](https://github.com/prysmaticlabs/prysm/pull/12335) + - **Lighthouse+** [v4.3.0](https://github.com/sigp/lighthouse/releases) or later. Here's a [quick guide](https://gist.github.com/metachris/bcae9ae42e2fc834804241f991351c4e) for setting up Lighthouse. + - **Prysm** [v4.0.6](https://github.com/prysmaticlabs/prysm/releases) or later. **Relays are strongly advised to run multiple beacon nodes!** * The reason is that on getPayload, the block has to be validated and broadcast by a local beacon node before it is returned to the proposer. @@ -129,6 +130,7 @@ redis-cli DEL boost-relay/sepolia:validators-registration boost-relay/sepolia:va * `API_SHUTDOWN_STOP_SENDING_BIDS` - whether API should stop sending bids during shutdown (nly useful in single-instance/testnet setups, default: `false`) * `BLOCKSIM_MAX_CONCURRENT` - maximum number of concurrent block-sim requests (0 for no maximum, default: `4`) * `BLOCKSIM_TIMEOUT_MS` - builder block submission validation request timeout (default: `3000`) +* `BROADCAST_MODE` - which broadcast mode to use for block publishing (default: `consensus_and_equivocation`) * `DB_DONT_APPLY_SCHEMA` - disable applying DB schema on startup (useful for connecting data API to read-only replica) * `DB_TABLE_PREFIX` - prefix to use for db tables (default uses `dev`) * `GETPAYLOAD_RETRY_TIMEOUT_MS` - getPayload retry getting a payload if first try failed (default: `100`) diff --git a/beaconclient/mock_beacon_instance.go b/beaconclient/mock_beacon_instance.go index 95902de5..4dc38986 100644 --- a/beaconclient/mock_beacon_instance.go +++ b/beaconclient/mock_beacon_instance.go @@ -107,7 +107,7 @@ func (c *MockBeaconInstance) addDelay() { } } -func (c *MockBeaconInstance) PublishBlock(block *common.SignedBeaconBlock, broadcastValidation BroadcastValidation) (code int, err error) { +func (c *MockBeaconInstance) PublishBlock(block *common.SignedBeaconBlock, broadcaseMode BroadcastMode) (code int, err error) { return 0, nil } diff --git a/beaconclient/multi_beacon_client.go b/beaconclient/multi_beacon_client.go index 7d731022..808e8231 100644 --- a/beaconclient/multi_beacon_client.go +++ b/beaconclient/multi_beacon_client.go @@ -20,15 +20,15 @@ var ( ErrBeaconBlock202 = errors.New("beacon block failed validation but was still broadcast (202)") ) -type BroadcastValidation int +type BroadcastMode int const ( - Gossip BroadcastValidation = iota // lightweight gossip checks only - Consensus // full consensus checks, including validation of all signatures and blocks fields - ConsensusAndEquivocation // the same as `consensus`, with an extra equivocation check + Gossip BroadcastMode = iota // lightweight gossip checks only + Consensus // full consensus checks, including validation of all signatures and blocks fields + ConsensusAndEquivocation // the same as `consensus`, with an extra equivocation check ) -func (b BroadcastValidation) String() string { +func (b BroadcastMode) String() string { return [...]string{"gossip", "consensus", "consensus_and_equivocation"}[b] } @@ -60,7 +60,7 @@ type IBeaconInstance interface { GetStateValidators(stateID string) (*GetStateValidatorsResponse, error) GetProposerDuties(epoch uint64) (*ProposerDutiesResponse, error) GetURI() string - PublishBlock(block *common.SignedBeaconBlock, broadcastValidation BroadcastValidation) (code int, err error) + PublishBlock(block *common.SignedBeaconBlock, broadcastMode BroadcastMode) (code int, err error) GetGenesis() (*GetGenesisResponse, error) GetSpec() (spec *GetSpecResponse, err error) GetForkSchedule() (spec *GetForkScheduleResponse, err error) @@ -76,7 +76,8 @@ type MultiBeaconClient struct { // feature flags ffAllowSyncingBeaconNode bool - ffBroadcastValidation BroadcastValidation + + broadcastMode BroadcastMode } func NewMultiBeaconClient(log *logrus.Entry, beaconInstances []IBeaconInstance) *MultiBeaconClient { @@ -85,7 +86,7 @@ func NewMultiBeaconClient(log *logrus.Entry, beaconInstances []IBeaconInstance) beaconInstances: beaconInstances, bestBeaconIndex: *uberatomic.NewInt64(0), ffAllowSyncingBeaconNode: false, - ffBroadcastValidation: ConsensusAndEquivocation, + broadcastMode: ConsensusAndEquivocation, } // feature flags @@ -94,15 +95,15 @@ func NewMultiBeaconClient(log *logrus.Entry, beaconInstances []IBeaconInstance) client.ffAllowSyncingBeaconNode = true } - if os.Getenv("BROADCAST_VALIDATION") != "" { - broadcastValidationStr := os.Getenv("BROADCAST_VALIDATION") - broadcastValidation, ok := parseBroadcastValidationString(broadcastValidationStr) + broadcastModeStr := os.Getenv("BROADCAST_MODE") + if broadcastModeStr != "" { + broadcastMode, ok := parseBroadcastModeString(broadcastModeStr) if !ok { - msg := fmt.Sprintf("env: BROADCAST_VALIDATION: invalid value %s, leaving to default value %s", broadcastValidationStr, client.ffBroadcastValidation.String()) + msg := fmt.Sprintf("env: BROADCAST_MODE: invalid value %s, leaving to default value %s", broadcastModeStr, client.broadcastMode.String()) client.log.Warn(msg) } else { - client.log.Info(fmt.Sprintf("env: BROADCAST_VALIDATION: setting validation to %s", broadcastValidation.String())) - client.ffBroadcastValidation = broadcastValidation + client.log.Info(fmt.Sprintf("env: BROADCAST_MODE: setting mode to %s", broadcastMode.String())) + client.broadcastMode = broadcastMode } } @@ -269,7 +270,7 @@ func (c *MultiBeaconClient) PublishBlock(block *common.SignedBeaconBlock) (code log := log.WithField("uri", client.GetURI()) log.Debug("publishing block") go func(index int, client IBeaconInstance) { - code, err := client.PublishBlock(block, c.ffBroadcastValidation) + code, err := client.PublishBlock(block, c.broadcastMode) resChans <- publishResp{ index: index, code: code, diff --git a/beaconclient/prod_beacon_instance.go b/beaconclient/prod_beacon_instance.go index 441eb0a9..fb418f71 100644 --- a/beaconclient/prod_beacon_instance.go +++ b/beaconclient/prod_beacon_instance.go @@ -256,8 +256,8 @@ func (c *ProdBeaconInstance) GetURI() string { return c.beaconURI } -func (c *ProdBeaconInstance) PublishBlock(block *common.SignedBeaconBlock, broadcastValidation BroadcastValidation) (code int, err error) { - uri := fmt.Sprintf("%s/eth/v2/beacon/blocks?broadcast_validation=%s", c.beaconURI, broadcastValidation.String()) +func (c *ProdBeaconInstance) PublishBlock(block *common.SignedBeaconBlock, broadcastMode BroadcastMode) (code int, err error) { + uri := fmt.Sprintf("%s/eth/v2/beacon/blocks?broadcast_validation=%s", c.beaconURI, broadcastMode.String()) headers := http.Header{} headers.Add("Eth-Consensus-Version", common.ForkVersionStringCapella) return fetchBeacon(http.MethodPost, uri, block, nil, nil, headers) diff --git a/beaconclient/util.go b/beaconclient/util.go index 6d2fd289..7301dd21 100644 --- a/beaconclient/util.go +++ b/beaconclient/util.go @@ -20,13 +20,13 @@ var ( StateIDJustified = "justified" ) -func parseBroadcastValidationString(s string) (BroadcastValidation, bool) { - broadcastValidationMap := map[string]BroadcastValidation{ +func parseBroadcastModeString(s string) (BroadcastMode, bool) { + broadcastModeMap := map[string]BroadcastMode{ "gossip": Gossip, "consensus": Consensus, "consensus_and_equivocation": ConsensusAndEquivocation, } - b, ok := broadcastValidationMap[strings.ToLower(s)] + b, ok := broadcastModeMap[strings.ToLower(s)] return b, ok }