allow payload builder client to be function of validator/proposer (#5015)

* allow payload builder client to be function of validator/proposer

* fileExists has side effects on Windows and only Windows

* another not-always-func
This commit is contained in:
tersec 2023-06-02 11:06:33 +00:00 committed by GitHub
parent 005a35597f
commit e8e67ec771
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 54 additions and 47 deletions

View File

@ -115,7 +115,8 @@ template rng*(node: BeaconNode): ref HmacDrbgContext =
proc currentSlot*(node: BeaconNode): Slot = proc currentSlot*(node: BeaconNode): Slot =
node.beaconClock.now.slotOrZero node.beaconClock.now.slotOrZero
proc getPayloadBuilderClient*(node: BeaconNode): RestResult[RestClientRef] = proc getPayloadBuilderClient*(
node: BeaconNode, validator_index: uint64): RestResult[RestClientRef] =
if node.config.payloadBuilderEnable: if node.config.payloadBuilderEnable:
# Logging done in caller # Logging done in caller
let res = RestClientRef.new(node.config.payloadBuilderUrl) let res = RestClientRef.new(node.config.payloadBuilderUrl)

View File

@ -886,21 +886,21 @@ proc installBeaconApiHandlers*(router: var RestRouter, node: BeaconNode) =
currentEpochFork.toString != version: currentEpochFork.toString != version:
return RestApiResponse.jsonError(Http400, BlockIncorrectFork) return RestApiResponse.jsonError(Http400, BlockIncorrectFork)
let payloadBuilderClient = node.getPayloadBuilderClient().valueOr:
return RestApiResponse.jsonError(
Http400, "Unable to initialize payload builder client: " & $error)
case currentEpochFork case currentEpochFork
of ConsensusFork.Deneb: of ConsensusFork.Deneb:
return RestApiResponse.jsonError(Http500, $denebImplementationMissing) return RestApiResponse.jsonError(Http500, $denebImplementationMissing)
of ConsensusFork.Capella: of ConsensusFork.Capella:
let res = let
block: restBlock = decodeBodyJsonOrSsz(
let restBlock = decodeBodyJsonOrSsz( capella_mev.SignedBlindedBeaconBlock, body).valueOr:
capella_mev.SignedBlindedBeaconBlock, body).valueOr: return RestApiResponse.jsonError(Http400, InvalidBlockObjectError,
return RestApiResponse.jsonError(Http400, InvalidBlockObjectError, $error)
$error) payloadBuilderClient = node.getPayloadBuilderClient(
await node.unblindAndRouteBlockMEV(payloadBuilderClient, restBlock) restBlock.message.proposer_index).valueOr:
return RestApiResponse.jsonError(
Http400, "Unable to initialize payload builder client: " & $error)
res = await node.unblindAndRouteBlockMEV(
payloadBuilderClient, restBlock)
if res.isErr(): if res.isErr():
return RestApiResponse.jsonError( return RestApiResponse.jsonError(
@ -910,13 +910,17 @@ proc installBeaconApiHandlers*(router: var RestRouter, node: BeaconNode) =
return RestApiResponse.jsonMsgResponse(BlockValidationSuccess) return RestApiResponse.jsonMsgResponse(BlockValidationSuccess)
of ConsensusFork.Bellatrix: of ConsensusFork.Bellatrix:
let res = let
block: restBlock = decodeBodyJsonOrSsz(
let restBlock = decodeBodyJsonOrSsz( bellatrix_mev.SignedBlindedBeaconBlock, body).valueOr:
bellatrix_mev.SignedBlindedBeaconBlock, body).valueOr: return RestApiResponse.jsonError(Http400, InvalidBlockObjectError,
return RestApiResponse.jsonError(Http400, InvalidBlockObjectError, $error)
$error) payloadBuilderClient = node.getPayloadBuilderClient(
await node.unblindAndRouteBlockMEV(payloadBuilderClient, restBlock) restBlock.message.proposer_index).valueOr:
return RestApiResponse.jsonError(
Http400, "Unable to initialize payload builder client: " & $error)
res = await node.unblindAndRouteBlockMEV(
payloadBuilderClient, restBlock)
if res.isErr(): if res.isErr():
return RestApiResponse.jsonError( return RestApiResponse.jsonError(

View File

@ -509,7 +509,8 @@ proc installValidatorApiHandlers*(router: var RestRouter, node: BeaconNode) =
RestApiResponse.jsonError(Http500, InvalidAcceptError) RestApiResponse.jsonError(Http500, InvalidAcceptError)
let let
payloadBuilderClient = node.getPayloadBuilderClient().valueOr: payloadBuilderClient = node.getPayloadBuilderClient(
proposer.distinctBase).valueOr:
return RestApiResponse.jsonError( return RestApiResponse.jsonError(
Http500, "Unable to initialize payload builder client: " & $error) Http500, "Unable to initialize payload builder client: " & $error)
contextFork = node.dag.cfg.consensusForkAtEpoch(node.currentSlot.epoch) contextFork = node.dag.cfg.consensusForkAtEpoch(node.currentSlot.epoch)

View File

@ -92,7 +92,7 @@ const
"passwords" / "10-million-password-list-top-100000.txt", "passwords" / "10-million-password-list-top-100000.txt",
minWordLen = minPasswordLen) minWordLen = minPasswordLen)
proc dispose*(decryptor: var MultipleKeystoresDecryptor) = func dispose*(decryptor: var MultipleKeystoresDecryptor) =
burnMem(decryptor.previouslyUsedPassword) burnMem(decryptor.previouslyUsedPassword)
func init*(T: type KeymanagerHost, func init*(T: type KeymanagerHost,
@ -134,8 +134,8 @@ func init*(T: type KeystoreData,
pubkey: privateKey.toPubKey().toPubKey() pubkey: privateKey.toPubKey().toPubKey()
) )
func init*(T: type KeystoreData, keystore: RemoteKeystore, func init(T: type KeystoreData, keystore: RemoteKeystore,
handle: FileLockHandle): Result[T, cstring] {.raises: [Defect].} = handle: FileLockHandle): Result[T, cstring] {.raises: [Defect].} =
let cookedKey = keystore.pubkey.load().valueOr: let cookedKey = keystore.pubkey.load().valueOr:
return err("Invalid validator's public key") return err("Invalid validator's public key")
@ -162,9 +162,9 @@ func init*(T: type KeystoreData, keystore: RemoteKeystore,
remoteType: RemoteSignerType.VerifyingWeb3Signer, remoteType: RemoteSignerType.VerifyingWeb3Signer,
provenBlockProperties: keystore.provenBlockProperties) provenBlockProperties: keystore.provenBlockProperties)
func init*(T: type KeystoreData, cookedKey: CookedPubKey, func init(T: type KeystoreData, cookedKey: CookedPubKey,
remotes: seq[RemoteSignerInfo], threshold: uint32, remotes: seq[RemoteSignerInfo], threshold: uint32,
handle: FileLockHandle): T = handle: FileLockHandle): T =
KeystoreData( KeystoreData(
kind: KeystoreKind.Remote, kind: KeystoreKind.Remote,
handle: handle, handle: handle,
@ -178,7 +178,7 @@ func init(T: type AddValidatorFailure, status: AddValidatorStatus,
msg = ""): AddValidatorFailure {.raises: [Defect].} = msg = ""): AddValidatorFailure {.raises: [Defect].} =
AddValidatorFailure(status: status, message: msg) AddValidatorFailure(status: status, message: msg)
func toKeystoreKind*(kind: ValidatorKind): KeystoreKind {.raises: [Defect].} = func toKeystoreKind(kind: ValidatorKind): KeystoreKind {.raises: [Defect].} =
case kind case kind
of ValidatorKind.Local: of ValidatorKind.Local:
KeystoreKind.Local KeystoreKind.Local
@ -240,7 +240,7 @@ proc checkAndCreateDataDir*(dataDir: string): bool =
return true return true
proc checkSensitivePathPermissions*(dirFilePath: string): bool = proc checkSensitivePathPermissions(dirFilePath: string): bool =
## If ``dirFilePath`` is file, then check if file has only ## If ``dirFilePath`` is file, then check if file has only
## ##
## - "(600) rwx------" permissions on Posix (Linux, MacOS, BSD) ## - "(600) rwx------" permissions on Posix (Linux, MacOS, BSD)
@ -392,7 +392,7 @@ proc keyboardGetPassword[T](prompt: string, attempts: int,
dec(remainingAttempts) dec(remainingAttempts)
err("Failed to decrypt keystore") err("Failed to decrypt keystore")
proc loadSecretFile*(path: string): KsResult[KeystorePass] {. proc loadSecretFile(path: string): KsResult[KeystorePass] {.
raises: [Defect].} = raises: [Defect].} =
let res = readAllChars(path) let res = readAllChars(path)
if res.isErr(): if res.isErr():
@ -618,7 +618,7 @@ proc removeValidator*(pool: var ValidatorPool,
pool.removeValidator(publicKey) pool.removeValidator(publicKey)
ok(res.value()) ok(res.value())
proc checkKeyName*(keyName: string): bool = func checkKeyName(keyName: string): bool =
const keyAlphabet = {'a'..'f', 'A'..'F', '0'..'9'} const keyAlphabet = {'a'..'f', 'A'..'F', '0'..'9'}
if len(keyName) != KeyNameSize: if len(keyName) != KeyNameSize:
return false return false
@ -629,7 +629,7 @@ proc checkKeyName*(keyName: string): bool =
return false return false
true true
proc existsKeystore*(keystoreDir: string, keyKind: KeystoreKind): bool {. proc existsKeystore(keystoreDir: string, keyKind: KeystoreKind): bool {.
raises: [Defect].} = raises: [Defect].} =
case keyKind case keyKind
of KeystoreKind.Local: of KeystoreKind.Local:
@ -637,8 +637,8 @@ proc existsKeystore*(keystoreDir: string, keyKind: KeystoreKind): bool {.
of KeystoreKind.Remote: of KeystoreKind.Remote:
fileExists(keystoreDir / RemoteKeystoreFileName) fileExists(keystoreDir / RemoteKeystoreFileName)
proc existsKeystore*(keystoreDir: string, proc existsKeystore(keystoreDir: string,
keysMask: set[KeystoreKind]): bool {.raises: [Defect].} = keysMask: set[KeystoreKind]): bool {.raises: [Defect].} =
if KeystoreKind.Local in keysMask: if KeystoreKind.Local in keysMask:
if existsKeystore(keystoreDir, KeystoreKind.Local): if existsKeystore(keystoreDir, KeystoreKind.Local):
return true return true
@ -820,7 +820,7 @@ type
DuplicateKeystoreFile: DuplicateKeystoreFile:
error*: string error*: string
proc mapErrTo*[T, E](r: Result[T, E], v: static KeystoreGenerationErrorKind): func mapErrTo*[T, E](r: Result[T, E], v: static KeystoreGenerationErrorKind):
Result[T, KeystoreGenerationError] = Result[T, KeystoreGenerationError] =
r.mapErr(proc (e: E): KeystoreGenerationError = r.mapErr(proc (e: E): KeystoreGenerationError =
KeystoreGenerationError(kind: v, error: $e)) KeystoreGenerationError(kind: v, error: $e))
@ -948,7 +948,7 @@ proc createLocalValidatorFiles*(
success = true success = true
ok() ok()
proc createLockedLocalValidatorFiles*( proc createLockedLocalValidatorFiles(
secretsDir, validatorsDir, keystoreDir, secretsDir, validatorsDir, keystoreDir,
secretFile, passwordAsString, keystoreFile, secretFile, passwordAsString, keystoreFile,
encodedStorage: string encodedStorage: string
@ -1022,7 +1022,7 @@ proc createRemoteValidatorFiles*(
success = true success = true
ok() ok()
proc createLockedRemoteValidatorFiles*( proc createLockedRemoteValidatorFiles(
validatorsDir, keystoreDir, keystoreFile, encodedStorage: string validatorsDir, keystoreDir, keystoreFile, encodedStorage: string
): Result[FileLockHandle, KeystoreGenerationError] {.raises: [Defect].} = ): Result[FileLockHandle, KeystoreGenerationError] {.raises: [Defect].} =
var var
@ -1089,7 +1089,7 @@ proc saveKeystore*(
keystoreFile, encodedStorage) keystoreFile, encodedStorage)
ok() ok()
proc saveLockedKeystore*( proc saveLockedKeystore(
rng: var HmacDrbgContext, rng: var HmacDrbgContext,
validatorsDir, secretsDir: string, validatorsDir, secretsDir: string,
signingKey: ValidatorPrivKey, signingKey: ValidatorPrivKey,
@ -1130,7 +1130,7 @@ proc saveLockedKeystore*(
keystoreFile, encodedStorage) keystoreFile, encodedStorage)
ok(lock) ok(lock)
proc saveKeystore*( proc saveKeystore(
validatorsDir: string, validatorsDir: string,
publicKey: ValidatorPubKey, publicKey: ValidatorPubKey,
urls: seq[RemoteSignerInfo], urls: seq[RemoteSignerInfo],
@ -1172,7 +1172,7 @@ proc saveKeystore*(
encodedStorage) encodedStorage)
ok() ok()
proc saveLockedKeystore*( proc saveLockedKeystore(
validatorsDir: string, validatorsDir: string,
publicKey: ValidatorPubKey, publicKey: ValidatorPubKey,
urls: seq[RemoteSignerInfo], urls: seq[RemoteSignerInfo],
@ -1222,7 +1222,7 @@ proc saveKeystore*(
let remoteInfo = RemoteSignerInfo(url: url, id: 0) let remoteInfo = RemoteSignerInfo(url: url, id: 0)
saveKeystore(validatorsDir, publicKey, @[remoteInfo], 1) saveKeystore(validatorsDir, publicKey, @[remoteInfo], 1)
proc saveLockedKeystore*( proc saveLockedKeystore(
validatorsDir: string, validatorsDir: string,
publicKey: ValidatorPubKey, publicKey: ValidatorPubKey,
url: HttpHostUri url: HttpHostUri
@ -1338,12 +1338,12 @@ func validatorKeystoreDir(host: KeymanagerHost,
pubkey: ValidatorPubKey): string = pubkey: ValidatorPubKey): string =
host.validatorsDir.validatorKeystoreDir(pubkey) host.validatorsDir.validatorKeystoreDir(pubkey)
func feeRecipientPath*(host: KeymanagerHost, func feeRecipientPath(host: KeymanagerHost,
pubkey: ValidatorPubKey): string = pubkey: ValidatorPubKey): string =
host.validatorsDir.feeRecipientPath(pubkey) host.validatorsDir.feeRecipientPath(pubkey)
func gasLimitPath*(host: KeymanagerHost, func gasLimitPath(host: KeymanagerHost,
pubkey: ValidatorPubKey): string = pubkey: ValidatorPubKey): string =
host.validatorsDir.gasLimitPath(pubkey) host.validatorsDir.gasLimitPath(pubkey)
proc removeFeeRecipientFile*(host: KeymanagerHost, proc removeFeeRecipientFile*(host: KeymanagerHost,
@ -1535,7 +1535,7 @@ proc generateDeposits*(cfg: RuntimeConfig,
ok deposits ok deposits
proc saveWallet*(wallet: Wallet, outWalletPath: string): Result[void, string] = proc saveWallet(wallet: Wallet, outWalletPath: string): Result[void, string] =
let walletDir = splitFile(outWalletPath).dir let walletDir = splitFile(outWalletPath).dir
var encodedWallet: string var encodedWallet: string
try: try:

View File

@ -793,7 +793,8 @@ proc proposeBlockAux(
# Collect bids # Collect bids
var payloadBuilderClient: RestClientRef var payloadBuilderClient: RestClientRef
let payloadBuilderClientMaybe = node.getPayloadBuilderClient() let payloadBuilderClientMaybe = node.getPayloadBuilderClient(
validator_index.distinctBase)
if payloadBuilderClientMaybe.isErr: if payloadBuilderClientMaybe.isErr:
warn "Unable to initialize payload builder client while proposing block", warn "Unable to initialize payload builder client while proposing block",
err = payloadBuilderClientMaybe.error err = payloadBuilderClientMaybe.error
@ -1399,7 +1400,7 @@ proc registerValidators*(node: BeaconNode, epoch: Epoch) {.async.} =
const HttpOk = 200 const HttpOk = 200
let payloadBuilderClient = node.getPayloadBuilderClient().valueOr: let payloadBuilderClient = node.getPayloadBuilderClient(0).valueOr:
debug "Unable to initialize payload builder client while registering validators", debug "Unable to initialize payload builder client while registering validators",
err = error err = error
return return