@lodestar/beacon-node 1.44.0-dev.6ef8199cfa → 1.44.0-dev.762dd5f186
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/api/impl/beacon/blocks/index.d.ts.map +1 -1
- package/lib/api/impl/beacon/blocks/index.js +66 -33
- package/lib/api/impl/beacon/blocks/index.js.map +1 -1
- package/lib/api/impl/beacon/pool/index.d.ts.map +1 -1
- package/lib/api/impl/beacon/pool/index.js +1 -26
- package/lib/api/impl/beacon/pool/index.js.map +1 -1
- package/lib/api/impl/config/constants.d.ts +5 -0
- package/lib/api/impl/config/constants.d.ts.map +1 -1
- package/lib/api/impl/config/constants.js +6 -1
- package/lib/api/impl/config/constants.js.map +1 -1
- package/lib/api/impl/debug/index.d.ts.map +1 -1
- package/lib/api/impl/debug/index.js +69 -12
- package/lib/api/impl/debug/index.js.map +1 -1
- package/lib/api/impl/lodestar/index.d.ts.map +1 -1
- package/lib/api/impl/lodestar/index.js +28 -0
- package/lib/api/impl/lodestar/index.js.map +1 -1
- package/lib/api/impl/validator/index.d.ts.map +1 -1
- package/lib/api/impl/validator/index.js +117 -72
- package/lib/api/impl/validator/index.js.map +1 -1
- package/lib/chain/archiveStore/archiveStore.d.ts +0 -1
- package/lib/chain/archiveStore/archiveStore.d.ts.map +1 -1
- package/lib/chain/archiveStore/archiveStore.js +0 -4
- package/lib/chain/archiveStore/archiveStore.js.map +1 -1
- package/lib/chain/blocks/importBlock.d.ts.map +1 -1
- package/lib/chain/blocks/importBlock.js +19 -4
- package/lib/chain/blocks/importBlock.js.map +1 -1
- package/lib/chain/blocks/importExecutionPayload.d.ts.map +1 -1
- package/lib/chain/blocks/importExecutionPayload.js +5 -3
- package/lib/chain/blocks/importExecutionPayload.js.map +1 -1
- package/lib/chain/blocks/verifyExecutionPayloadEnvelope.d.ts.map +1 -1
- package/lib/chain/blocks/verifyExecutionPayloadEnvelope.js +3 -3
- package/lib/chain/blocks/verifyExecutionPayloadEnvelope.js.map +1 -1
- package/lib/chain/chain.d.ts +3 -3
- package/lib/chain/chain.d.ts.map +1 -1
- package/lib/chain/chain.js +11 -3
- package/lib/chain/chain.js.map +1 -1
- package/lib/chain/emitter.d.ts +2 -1
- package/lib/chain/emitter.d.ts.map +1 -1
- package/lib/chain/emitter.js.map +1 -1
- package/lib/chain/errors/blockError.d.ts +0 -7
- package/lib/chain/errors/blockError.d.ts.map +1 -1
- package/lib/chain/errors/blockError.js +0 -3
- package/lib/chain/errors/blockError.js.map +1 -1
- package/lib/chain/errors/executionPayloadBid.d.ts +23 -1
- package/lib/chain/errors/executionPayloadBid.d.ts.map +1 -1
- package/lib/chain/errors/executionPayloadBid.js +4 -0
- package/lib/chain/errors/executionPayloadBid.js.map +1 -1
- package/lib/chain/errors/payloadAttestation.d.ts +6 -0
- package/lib/chain/errors/payloadAttestation.d.ts.map +1 -1
- package/lib/chain/errors/payloadAttestation.js +1 -0
- package/lib/chain/errors/payloadAttestation.js.map +1 -1
- package/lib/chain/forkChoice/index.d.ts +4 -4
- package/lib/chain/forkChoice/index.d.ts.map +1 -1
- package/lib/chain/forkChoice/index.js +24 -11
- package/lib/chain/forkChoice/index.js.map +1 -1
- package/lib/chain/interface.d.ts +2 -2
- package/lib/chain/interface.d.ts.map +1 -1
- package/lib/chain/interface.js.map +1 -1
- package/lib/chain/opPools/executionPayloadBidPool.d.ts +4 -4
- package/lib/chain/opPools/executionPayloadBidPool.d.ts.map +1 -1
- package/lib/chain/opPools/executionPayloadBidPool.js +6 -4
- package/lib/chain/opPools/executionPayloadBidPool.js.map +1 -1
- package/lib/chain/options.d.ts.map +1 -1
- package/lib/chain/options.js +1 -0
- package/lib/chain/options.js.map +1 -1
- package/lib/chain/prepareNextSlot.d.ts.map +1 -1
- package/lib/chain/prepareNextSlot.js +2 -10
- package/lib/chain/prepareNextSlot.js.map +1 -1
- package/lib/chain/produceBlock/produceBlockBody.d.ts +4 -2
- package/lib/chain/produceBlock/produceBlockBody.d.ts.map +1 -1
- package/lib/chain/produceBlock/produceBlockBody.js +81 -27
- package/lib/chain/produceBlock/produceBlockBody.js.map +1 -1
- package/lib/chain/regen/interface.d.ts +2 -1
- package/lib/chain/regen/interface.d.ts.map +1 -1
- package/lib/chain/regen/interface.js +2 -0
- package/lib/chain/regen/interface.js.map +1 -1
- package/lib/chain/regen/queued.d.ts +0 -1
- package/lib/chain/regen/queued.d.ts.map +1 -1
- package/lib/chain/regen/queued.js +0 -4
- package/lib/chain/regen/queued.js.map +1 -1
- package/lib/chain/seenCache/seenPayloadEnvelopeInput.d.ts.map +1 -1
- package/lib/chain/seenCache/seenPayloadEnvelopeInput.js +8 -2
- package/lib/chain/seenCache/seenPayloadEnvelopeInput.js.map +1 -1
- package/lib/chain/stateCache/fifoBlockStateCache.d.ts +0 -5
- package/lib/chain/stateCache/fifoBlockStateCache.d.ts.map +1 -1
- package/lib/chain/stateCache/fifoBlockStateCache.js +0 -5
- package/lib/chain/stateCache/fifoBlockStateCache.js.map +1 -1
- package/lib/chain/stateCache/persistentCheckpointsCache.d.ts +1 -4
- package/lib/chain/stateCache/persistentCheckpointsCache.d.ts.map +1 -1
- package/lib/chain/stateCache/persistentCheckpointsCache.js +5 -2
- package/lib/chain/stateCache/persistentCheckpointsCache.js.map +1 -1
- package/lib/chain/stateCache/types.d.ts +0 -2
- package/lib/chain/stateCache/types.d.ts.map +1 -1
- package/lib/chain/stateCache/types.js.map +1 -1
- package/lib/chain/validation/block.d.ts +5 -1
- package/lib/chain/validation/block.d.ts.map +1 -1
- package/lib/chain/validation/block.js +4 -14
- package/lib/chain/validation/block.js.map +1 -1
- package/lib/chain/validation/executionPayloadBid.d.ts +7 -3
- package/lib/chain/validation/executionPayloadBid.d.ts.map +1 -1
- package/lib/chain/validation/executionPayloadBid.js +81 -16
- package/lib/chain/validation/executionPayloadBid.js.map +1 -1
- package/lib/chain/validation/executionPayloadEnvelope.js +1 -3
- package/lib/chain/validation/executionPayloadEnvelope.js.map +1 -1
- package/lib/chain/validation/payloadAttestationMessage.d.ts.map +1 -1
- package/lib/chain/validation/payloadAttestationMessage.js +24 -4
- package/lib/chain/validation/payloadAttestationMessage.js.map +1 -1
- package/lib/chain/validatorMonitor.d.ts +1 -0
- package/lib/chain/validatorMonitor.d.ts.map +1 -1
- package/lib/chain/validatorMonitor.js +16 -0
- package/lib/chain/validatorMonitor.js.map +1 -1
- package/lib/execution/builder/index.d.ts +1 -2
- package/lib/execution/builder/index.d.ts.map +1 -1
- package/lib/execution/builder/index.js +0 -1
- package/lib/execution/builder/index.js.map +1 -1
- package/lib/execution/engine/http.js +1 -1
- package/lib/execution/engine/http.js.map +1 -1
- package/lib/execution/engine/interface.d.ts +2 -2
- package/lib/execution/engine/interface.d.ts.map +1 -1
- package/lib/execution/engine/interface.js +6 -2
- package/lib/execution/engine/interface.js.map +1 -1
- package/lib/execution/engine/mock.d.ts.map +1 -1
- package/lib/execution/engine/mock.js +3 -5
- package/lib/execution/engine/mock.js.map +1 -1
- package/lib/execution/engine/types.d.ts +15 -7
- package/lib/execution/engine/types.d.ts.map +1 -1
- package/lib/execution/engine/types.js +47 -9
- package/lib/execution/engine/types.js.map +1 -1
- package/lib/metrics/metrics/lodestar.d.ts +5 -1
- package/lib/metrics/metrics/lodestar.d.ts.map +1 -1
- package/lib/metrics/metrics/lodestar.js +14 -3
- package/lib/metrics/metrics/lodestar.js.map +1 -1
- package/lib/network/gossip/topic.d.ts +770 -3
- package/lib/network/gossip/topic.d.ts.map +1 -1
- package/lib/network/interface.d.ts +1 -0
- package/lib/network/interface.d.ts.map +1 -1
- package/lib/network/network.d.ts +1 -0
- package/lib/network/network.d.ts.map +1 -1
- package/lib/network/network.js +5 -0
- package/lib/network/network.js.map +1 -1
- package/lib/network/processor/gossipHandlers.d.ts.map +1 -1
- package/lib/network/processor/gossipHandlers.js +21 -6
- package/lib/network/processor/gossipHandlers.js.map +1 -1
- package/lib/network/processor/index.d.ts +2 -2
- package/lib/network/processor/index.d.ts.map +1 -1
- package/lib/network/processor/index.js +25 -23
- package/lib/network/processor/index.js.map +1 -1
- package/lib/network/reqresp/handlers/beaconBlocksByRange.d.ts.map +1 -1
- package/lib/network/reqresp/handlers/beaconBlocksByRange.js +9 -5
- package/lib/network/reqresp/handlers/beaconBlocksByRange.js.map +1 -1
- package/lib/network/reqresp/handlers/dataColumnSidecarsByRange.d.ts.map +1 -1
- package/lib/network/reqresp/handlers/dataColumnSidecarsByRange.js +13 -3
- package/lib/network/reqresp/handlers/dataColumnSidecarsByRange.js.map +1 -1
- package/lib/network/reqresp/handlers/dataColumnSidecarsByRoot.js +1 -1
- package/lib/network/reqresp/handlers/dataColumnSidecarsByRoot.js.map +1 -1
- package/lib/network/reqresp/handlers/executionPayloadEnvelopesByRange.d.ts +2 -1
- package/lib/network/reqresp/handlers/executionPayloadEnvelopesByRange.d.ts.map +1 -1
- package/lib/network/reqresp/handlers/executionPayloadEnvelopesByRange.js +16 -6
- package/lib/network/reqresp/handlers/executionPayloadEnvelopesByRange.js.map +1 -1
- package/lib/network/reqresp/handlers/executionPayloadEnvelopesByRoot.d.ts +2 -1
- package/lib/network/reqresp/handlers/executionPayloadEnvelopesByRoot.d.ts.map +1 -1
- package/lib/network/reqresp/handlers/executionPayloadEnvelopesByRoot.js +15 -1
- package/lib/network/reqresp/handlers/executionPayloadEnvelopesByRoot.js.map +1 -1
- package/lib/network/reqresp/handlers/index.js +4 -4
- package/lib/network/reqresp/handlers/index.js.map +1 -1
- package/lib/network/reqresp/utils/dataColumnResponseValidation.d.ts.map +1 -1
- package/lib/network/reqresp/utils/dataColumnResponseValidation.js +23 -5
- package/lib/network/reqresp/utils/dataColumnResponseValidation.js.map +1 -1
- package/lib/sync/types.d.ts +9 -1
- package/lib/sync/types.d.ts.map +1 -1
- package/lib/sync/types.js +9 -2
- package/lib/sync/types.js.map +1 -1
- package/lib/sync/unknownBlock.d.ts.map +1 -1
- package/lib/sync/unknownBlock.js +64 -30
- package/lib/sync/unknownBlock.js.map +1 -1
- package/lib/util/dataColumns.d.ts.map +1 -1
- package/lib/util/dataColumns.js +16 -11
- package/lib/util/dataColumns.js.map +1 -1
- package/lib/util/sszBytes.js +1 -1
- package/package.json +15 -17
- package/src/api/impl/beacon/blocks/index.ts +76 -42
- package/src/api/impl/beacon/pool/index.ts +4 -42
- package/src/api/impl/config/constants.ts +10 -0
- package/src/api/impl/debug/index.ts +73 -12
- package/src/api/impl/lodestar/index.ts +30 -0
- package/src/api/impl/validator/index.ts +137 -86
- package/src/chain/archiveStore/archiveStore.ts +0 -5
- package/src/chain/blocks/importBlock.ts +29 -7
- package/src/chain/blocks/importExecutionPayload.ts +8 -2
- package/src/chain/blocks/verifyExecutionPayloadEnvelope.ts +3 -5
- package/src/chain/chain.ts +14 -4
- package/src/chain/emitter.ts +3 -2
- package/src/chain/errors/blockError.ts +0 -4
- package/src/chain/errors/executionPayloadBid.ts +20 -1
- package/src/chain/errors/payloadAttestation.ts +2 -0
- package/src/chain/forkChoice/index.ts +27 -4
- package/src/chain/interface.ts +1 -2
- package/src/chain/opPools/executionPayloadBidPool.ts +10 -9
- package/src/chain/options.ts +1 -0
- package/src/chain/prepareNextSlot.ts +2 -11
- package/src/chain/produceBlock/produceBlockBody.ts +114 -40
- package/src/chain/regen/interface.ts +2 -1
- package/src/chain/regen/queued.ts +0 -5
- package/src/chain/seenCache/seenPayloadEnvelopeInput.ts +8 -3
- package/src/chain/stateCache/fifoBlockStateCache.ts +0 -6
- package/src/chain/stateCache/persistentCheckpointsCache.ts +6 -2
- package/src/chain/stateCache/types.ts +0 -2
- package/src/chain/validation/block.ts +12 -16
- package/src/chain/validation/executionPayloadBid.ts +90 -19
- package/src/chain/validation/executionPayloadEnvelope.ts +1 -3
- package/src/chain/validation/payloadAttestationMessage.ts +26 -4
- package/src/chain/validatorMonitor.ts +18 -0
- package/src/execution/builder/index.ts +1 -4
- package/src/execution/engine/http.ts +1 -1
- package/src/execution/engine/interface.ts +12 -2
- package/src/execution/engine/mock.ts +6 -5
- package/src/execution/engine/types.ts +75 -14
- package/src/metrics/metrics/lodestar.ts +15 -3
- package/src/network/interface.ts +1 -0
- package/src/network/network.ts +11 -0
- package/src/network/processor/gossipHandlers.ts +26 -6
- package/src/network/processor/index.ts +27 -27
- package/src/network/reqresp/handlers/beaconBlocksByRange.ts +12 -5
- package/src/network/reqresp/handlers/dataColumnSidecarsByRange.ts +17 -3
- package/src/network/reqresp/handlers/dataColumnSidecarsByRoot.ts +1 -1
- package/src/network/reqresp/handlers/executionPayloadEnvelopesByRange.ts +22 -6
- package/src/network/reqresp/handlers/executionPayloadEnvelopesByRoot.ts +20 -1
- package/src/network/reqresp/handlers/index.ts +4 -4
- package/src/network/reqresp/utils/dataColumnResponseValidation.ts +22 -5
- package/src/sync/types.ts +11 -2
- package/src/sync/unknownBlock.ts +70 -31
- package/src/util/dataColumns.ts +17 -12
- package/src/util/sszBytes.ts +1 -1
- package/lib/execution/builder/utils.d.ts +0 -5
- package/lib/execution/builder/utils.d.ts.map +0 -1
- package/lib/execution/builder/utils.js +0 -17
- package/lib/execution/builder/utils.js.map +0 -1
- package/src/execution/builder/utils.ts +0 -19
|
@@ -11,7 +11,6 @@ import {
|
|
|
11
11
|
SLOTS_PER_HISTORICAL_ROOT,
|
|
12
12
|
isForkPostBellatrix,
|
|
13
13
|
isForkPostDeneb,
|
|
14
|
-
isForkPostElectra,
|
|
15
14
|
isForkPostFulu,
|
|
16
15
|
isForkPostGloas,
|
|
17
16
|
} from "@lodestar/params";
|
|
@@ -50,6 +49,7 @@ import {
|
|
|
50
49
|
ProduceFullGloas,
|
|
51
50
|
} from "../../../../chain/produceBlock/index.js";
|
|
52
51
|
import {validateGossipBlock} from "../../../../chain/validation/block.js";
|
|
52
|
+
import {validateApiExecutionPayloadBid} from "../../../../chain/validation/executionPayloadBid.js";
|
|
53
53
|
import {validateApiExecutionPayloadEnvelope} from "../../../../chain/validation/executionPayloadEnvelope.js";
|
|
54
54
|
import {OpSource} from "../../../../chain/validatorMonitor.js";
|
|
55
55
|
import {
|
|
@@ -93,7 +93,7 @@ export function getBeaconBlockApi({
|
|
|
93
93
|
ApiModules,
|
|
94
94
|
"chain" | "config" | "metrics" | "network" | "db"
|
|
95
95
|
>): ApplicationMethods<routes.beacon.block.Endpoints> {
|
|
96
|
-
const
|
|
96
|
+
const publishBlockV2: ApplicationMethods<routes.beacon.block.Endpoints>["publishBlockV2"] = async (
|
|
97
97
|
{signedBlockContents, broadcastValidation},
|
|
98
98
|
_context,
|
|
99
99
|
opts: PublishBlockOpts = {}
|
|
@@ -204,11 +204,19 @@ export function getBeaconBlockApi({
|
|
|
204
204
|
try {
|
|
205
205
|
await validateGossipBlock(config, chain, signedBlock, fork);
|
|
206
206
|
} catch (error) {
|
|
207
|
-
if (error instanceof BlockGossipError
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
207
|
+
if (error instanceof BlockGossipError) {
|
|
208
|
+
switch (error.type.code) {
|
|
209
|
+
case BlockErrorCode.ALREADY_KNOWN:
|
|
210
|
+
// Block has already been seen, e.g. via gossip racing the publish API. Benign.
|
|
211
|
+
chain.logger.debug("Ignoring already-known block during publishing", valLogMeta);
|
|
212
|
+
return;
|
|
213
|
+
case BlockErrorCode.REPEAT_PROPOSAL:
|
|
214
|
+
// The proposer already produced a block for this slot. For a solo setup this is a
|
|
215
|
+
// notable signal (duplicate-proposal attempt). For fallback / DVT setups it is
|
|
216
|
+
// expected on every block where another node published first.
|
|
217
|
+
chain.logger.warn("Ignoring repeat-proposal block during publishing", valLogMeta);
|
|
218
|
+
return;
|
|
219
|
+
}
|
|
212
220
|
}
|
|
213
221
|
|
|
214
222
|
chain.logger.error("Gossip validations failed while publishing the block", valLogMeta, error as Error);
|
|
@@ -397,8 +405,8 @@ export function getBeaconBlockApi({
|
|
|
397
405
|
}
|
|
398
406
|
};
|
|
399
407
|
|
|
400
|
-
const
|
|
401
|
-
{signedBlindedBlock},
|
|
408
|
+
const publishBlindedBlockV2: ApplicationMethods<routes.beacon.block.Endpoints>["publishBlindedBlockV2"] = async (
|
|
409
|
+
{signedBlindedBlock, broadcastValidation},
|
|
402
410
|
context,
|
|
403
411
|
opts: PublishBlockOpts = {}
|
|
404
412
|
) => {
|
|
@@ -428,7 +436,7 @@ export function getBeaconBlockApi({
|
|
|
428
436
|
);
|
|
429
437
|
|
|
430
438
|
chain.logger.info("Publishing assembled block", {slot, blockRoot, source});
|
|
431
|
-
return
|
|
439
|
+
return publishBlockV2({signedBlockContents, broadcastValidation}, {...context, sszBytes: null}, opts);
|
|
432
440
|
}
|
|
433
441
|
|
|
434
442
|
const source = ProducedBlockSource.builder;
|
|
@@ -454,7 +462,11 @@ export function getBeaconBlockApi({
|
|
|
454
462
|
//
|
|
455
463
|
// see: https://github.com/ChainSafe/lodestar/issues/5404
|
|
456
464
|
chain.logger.info("Publishing assembled block", {slot, blockRoot, source});
|
|
457
|
-
return
|
|
465
|
+
return publishBlockV2(
|
|
466
|
+
{signedBlockContents, broadcastValidation},
|
|
467
|
+
{...context, sszBytes: null},
|
|
468
|
+
{...opts, ignoreIfKnown: true}
|
|
469
|
+
);
|
|
458
470
|
}
|
|
459
471
|
};
|
|
460
472
|
|
|
@@ -589,23 +601,6 @@ export function getBeaconBlockApi({
|
|
|
589
601
|
};
|
|
590
602
|
},
|
|
591
603
|
|
|
592
|
-
async getBlockAttestations({blockId}) {
|
|
593
|
-
const {block, executionOptimistic, finalized} = await getBlockResponse(chain, blockId);
|
|
594
|
-
const fork = config.getForkName(block.message.slot);
|
|
595
|
-
|
|
596
|
-
if (isForkPostElectra(fork)) {
|
|
597
|
-
throw new ApiError(
|
|
598
|
-
400,
|
|
599
|
-
`Use getBlockAttestationsV2 to retrieve block attestations for post-electra fork=${fork}`
|
|
600
|
-
);
|
|
601
|
-
}
|
|
602
|
-
|
|
603
|
-
return {
|
|
604
|
-
data: block.message.body.attestations,
|
|
605
|
-
meta: {executionOptimistic, finalized},
|
|
606
|
-
};
|
|
607
|
-
},
|
|
608
|
-
|
|
609
604
|
async getBlockAttestationsV2({blockId}) {
|
|
610
605
|
const {block, executionOptimistic, finalized} = await getBlockResponse(chain, blockId);
|
|
611
606
|
return {
|
|
@@ -653,16 +648,8 @@ export function getBeaconBlockApi({
|
|
|
653
648
|
};
|
|
654
649
|
},
|
|
655
650
|
|
|
656
|
-
|
|
657
|
-
|
|
658
|
-
|
|
659
|
-
async publishBlindedBlockV2(args, context, opts) {
|
|
660
|
-
await publishBlindedBlock(args, context, opts);
|
|
661
|
-
},
|
|
662
|
-
|
|
663
|
-
async publishBlockV2(args, context, opts) {
|
|
664
|
-
await publishBlock(args, context, opts);
|
|
665
|
-
},
|
|
651
|
+
publishBlockV2,
|
|
652
|
+
publishBlindedBlockV2,
|
|
666
653
|
|
|
667
654
|
async publishExecutionPayloadEnvelope({signedExecutionPayloadEnvelope}) {
|
|
668
655
|
const seenTimestampSec = Date.now() / 1000;
|
|
@@ -677,9 +664,20 @@ export function getBeaconBlockApi({
|
|
|
677
664
|
}
|
|
678
665
|
|
|
679
666
|
// TODO GLOAS: review checks, do we want to implement `broadcast_validation`?
|
|
680
|
-
|
|
667
|
+
let block = chain.forkChoice.getBlockHex(blockRootHex, PayloadStatus.EMPTY);
|
|
681
668
|
if (block === null) {
|
|
682
|
-
|
|
669
|
+
// Only wait if the envelope is for the current slot
|
|
670
|
+
if (chain.clock.isCurrentSlotGivenGossipDisparity(slot)) {
|
|
671
|
+
chain.logger.debug("Execution payload envelope received before block, waiting for block to be imported", {
|
|
672
|
+
blockRoot: blockRootHex,
|
|
673
|
+
slot,
|
|
674
|
+
});
|
|
675
|
+
await chain.waitForBlock(slot, blockRootHex);
|
|
676
|
+
block = chain.forkChoice.getBlockHex(blockRootHex, PayloadStatus.EMPTY);
|
|
677
|
+
}
|
|
678
|
+
if (block === null) {
|
|
679
|
+
throw new ApiError(404, `Block not found for beacon block root ${blockRootHex}`);
|
|
680
|
+
}
|
|
683
681
|
}
|
|
684
682
|
if (block.slot !== slot) {
|
|
685
683
|
throw new ApiError(400, `Envelope slot ${slot} does not match block slot ${block.slot}`);
|
|
@@ -726,10 +724,11 @@ export function getBeaconBlockApi({
|
|
|
726
724
|
await sleep(msToBlockSlot);
|
|
727
725
|
}
|
|
728
726
|
|
|
729
|
-
// TODO GLOAS: if block and payload are submitted in parallel, payloadInput may not yet exist.
|
|
730
|
-
// A queuing mechanism is needed to handle this case. See https://github.com/ChainSafe/lodestar/issues/8915
|
|
731
727
|
const payloadInput = chain.seenPayloadEnvelopeInputCache.get(blockRootHex);
|
|
732
728
|
if (!payloadInput) {
|
|
729
|
+
// The block is awaited above (queuing if the envelope arrived first), and both the API and
|
|
730
|
+
// gossip import paths seed the PayloadEnvelopeInput before importing the block, so the input
|
|
731
|
+
// should exist here.
|
|
733
732
|
throw new ApiError(404, `PayloadEnvelopeInput not found for block root ${blockRootHex}`);
|
|
734
733
|
}
|
|
735
734
|
|
|
@@ -825,6 +824,41 @@ export function getBeaconBlockApi({
|
|
|
825
824
|
});
|
|
826
825
|
},
|
|
827
826
|
|
|
827
|
+
async publishExecutionPayloadBid({signedExecutionPayloadBid}) {
|
|
828
|
+
const bid = signedExecutionPayloadBid.message;
|
|
829
|
+
const slot = bid.slot;
|
|
830
|
+
const fork = config.getForkName(slot);
|
|
831
|
+
|
|
832
|
+
if (!isForkPostGloas(fork)) {
|
|
833
|
+
throw new ApiError(400, `publishExecutionPayloadBid not supported for pre-gloas fork=${fork}`);
|
|
834
|
+
}
|
|
835
|
+
|
|
836
|
+
await validateApiExecutionPayloadBid(chain, signedExecutionPayloadBid);
|
|
837
|
+
|
|
838
|
+
try {
|
|
839
|
+
const insertOutcome = chain.executionPayloadBidPool.add(signedExecutionPayloadBid);
|
|
840
|
+
metrics?.opPool.executionPayloadBidPool.apiInsertOutcome.inc({insertOutcome});
|
|
841
|
+
} catch (e) {
|
|
842
|
+
chain.logger.error("Error adding to executionPayloadBid pool", {}, e as Error);
|
|
843
|
+
}
|
|
844
|
+
|
|
845
|
+
const sentPeers = await network.publishSignedExecutionPayloadBid(signedExecutionPayloadBid);
|
|
846
|
+
|
|
847
|
+
chain.emitter.emit(routes.events.EventType.executionPayloadBid, {
|
|
848
|
+
version: fork,
|
|
849
|
+
data: signedExecutionPayloadBid,
|
|
850
|
+
});
|
|
851
|
+
|
|
852
|
+
chain.logger.info("Published execution payload bid", {
|
|
853
|
+
slot,
|
|
854
|
+
builderIndex: bid.builderIndex,
|
|
855
|
+
blockHash: toRootHex(bid.blockHash),
|
|
856
|
+
parentBlockHash: toRootHex(bid.parentBlockHash),
|
|
857
|
+
value: bid.value,
|
|
858
|
+
sentPeers,
|
|
859
|
+
});
|
|
860
|
+
},
|
|
861
|
+
|
|
828
862
|
async getSignedExecutionPayloadEnvelope({blockId}, context) {
|
|
829
863
|
const {block, executionOptimistic, finalized} = await getBlockResponse(chain, blockId);
|
|
830
864
|
const slot = block.message.slot;
|
|
@@ -9,7 +9,7 @@ import {
|
|
|
9
9
|
isForkPostGloas,
|
|
10
10
|
} from "@lodestar/params";
|
|
11
11
|
import {isStatePostAltair} from "@lodestar/state-transition";
|
|
12
|
-
import {
|
|
12
|
+
import {Epoch, SingleAttestation, isElectraAttestation, ssz, sszTypesFor} from "@lodestar/types";
|
|
13
13
|
import {toRootHex} from "@lodestar/utils";
|
|
14
14
|
import {
|
|
15
15
|
AttestationError,
|
|
@@ -40,25 +40,6 @@ export function getBeaconPoolApi({
|
|
|
40
40
|
network,
|
|
41
41
|
}: Pick<ApiModules, "chain" | "logger" | "metrics" | "network">): ApplicationMethods<routes.beacon.pool.Endpoints> {
|
|
42
42
|
return {
|
|
43
|
-
async getPoolAttestations({slot, committeeIndex}) {
|
|
44
|
-
// Already filtered by slot
|
|
45
|
-
let attestations: Attestation[] = chain.aggregatedAttestationPool.getAll(slot);
|
|
46
|
-
const fork = chain.config.getForkName(slot ?? chain.clock.currentSlot);
|
|
47
|
-
|
|
48
|
-
if (isForkPostElectra(fork)) {
|
|
49
|
-
throw new ApiError(
|
|
50
|
-
400,
|
|
51
|
-
`Use getPoolAttestationsV2 to retrieve pool attestations for post-electra fork=${fork}`
|
|
52
|
-
);
|
|
53
|
-
}
|
|
54
|
-
|
|
55
|
-
if (committeeIndex !== undefined) {
|
|
56
|
-
attestations = attestations.filter((attestation) => committeeIndex === attestation.data.index);
|
|
57
|
-
}
|
|
58
|
-
|
|
59
|
-
return {data: attestations};
|
|
60
|
-
},
|
|
61
|
-
|
|
62
43
|
async getPoolAttestationsV2({slot, committeeIndex}) {
|
|
63
44
|
// Already filtered by slot
|
|
64
45
|
let attestations = chain.aggregatedAttestationPool.getAll(slot);
|
|
@@ -134,19 +115,6 @@ export function getBeaconPoolApi({
|
|
|
134
115
|
}
|
|
135
116
|
},
|
|
136
117
|
|
|
137
|
-
async getPoolAttesterSlashings() {
|
|
138
|
-
const fork = chain.config.getForkName(chain.clock.currentSlot);
|
|
139
|
-
|
|
140
|
-
if (isForkPostElectra(fork)) {
|
|
141
|
-
throw new ApiError(
|
|
142
|
-
400,
|
|
143
|
-
`Use getPoolAttesterSlashingsV2 to retrieve pool attester slashings for post-electra fork=${fork}`
|
|
144
|
-
);
|
|
145
|
-
}
|
|
146
|
-
|
|
147
|
-
return {data: chain.opPool.getAllAttesterSlashings()};
|
|
148
|
-
},
|
|
149
|
-
|
|
150
118
|
async getPoolAttesterSlashingsV2() {
|
|
151
119
|
const fork = chain.config.getForkName(chain.clock.currentSlot);
|
|
152
120
|
return {data: chain.opPool.getAllAttesterSlashings(), meta: {version: fork}};
|
|
@@ -164,10 +132,6 @@ export function getBeaconPoolApi({
|
|
|
164
132
|
return {data: chain.opPool.getAllBlsToExecutionChanges().map(({data}) => data)};
|
|
165
133
|
},
|
|
166
134
|
|
|
167
|
-
async submitPoolAttestations({signedAttestations}) {
|
|
168
|
-
await this.submitPoolAttestationsV2({signedAttestations});
|
|
169
|
-
},
|
|
170
|
-
|
|
171
135
|
async submitPoolAttestationsV2({signedAttestations}) {
|
|
172
136
|
const fork = chain.config.getForkName(chain.clock.currentSlot);
|
|
173
137
|
const seenTimestampSec = Date.now() / 1000;
|
|
@@ -247,10 +211,6 @@ export function getBeaconPoolApi({
|
|
|
247
211
|
}
|
|
248
212
|
},
|
|
249
213
|
|
|
250
|
-
async submitPoolAttesterSlashings({attesterSlashing}) {
|
|
251
|
-
await this.submitPoolAttesterSlashingsV2({attesterSlashing});
|
|
252
|
-
},
|
|
253
|
-
|
|
254
214
|
async submitPoolAttesterSlashingsV2({attesterSlashing}) {
|
|
255
215
|
await validateApiAttesterSlashing(chain, attesterSlashing);
|
|
256
216
|
const fork = chain.config.getForkName(Number(attesterSlashing.attestation1.data.slot));
|
|
@@ -328,8 +288,10 @@ export function getBeaconPoolApi({
|
|
|
328
288
|
|
|
329
289
|
chain.forkChoice.notifyPtcMessages(
|
|
330
290
|
toRootHex(payloadAttestationMessage.data.beaconBlockRoot),
|
|
291
|
+
payloadAttestationMessage.data.slot,
|
|
331
292
|
validatorCommitteeIndices,
|
|
332
|
-
payloadAttestationMessage.data.payloadPresent
|
|
293
|
+
payloadAttestationMessage.data.payloadPresent,
|
|
294
|
+
payloadAttestationMessage.data.blobDataAvailable
|
|
333
295
|
);
|
|
334
296
|
|
|
335
297
|
await network.publishPayloadAttestationMessage(payloadAttestationMessage);
|
|
@@ -5,6 +5,8 @@ import {
|
|
|
5
5
|
BASE_REWARDS_PER_EPOCH,
|
|
6
6
|
BLOB_TX_TYPE,
|
|
7
7
|
BLS_WITHDRAWAL_PREFIX,
|
|
8
|
+
BUILDER_DEPOSIT_REQUEST_TYPE,
|
|
9
|
+
BUILDER_EXIT_REQUEST_TYPE,
|
|
8
10
|
BUILDER_INDEX_FLAG,
|
|
9
11
|
BUILDER_INDEX_SELF_BUILD,
|
|
10
12
|
BUILDER_PAYMENT_THRESHOLD_DENOMINATOR,
|
|
@@ -21,6 +23,7 @@ import {
|
|
|
21
23
|
DOMAIN_BEACON_BUILDER,
|
|
22
24
|
DOMAIN_BEACON_PROPOSER,
|
|
23
25
|
DOMAIN_BLS_TO_EXECUTION_CHANGE,
|
|
26
|
+
DOMAIN_BUILDER_DEPOSIT,
|
|
24
27
|
DOMAIN_CONTRIBUTION_AND_PROOF,
|
|
25
28
|
DOMAIN_DEPOSIT,
|
|
26
29
|
DOMAIN_PROPOSER_PREFERENCES,
|
|
@@ -38,6 +41,7 @@ import {
|
|
|
38
41
|
JUSTIFICATION_BITS_LENGTH,
|
|
39
42
|
MAX_CONCURRENT_REQUESTS,
|
|
40
43
|
NODE_ID_BITS,
|
|
44
|
+
PAYLOAD_BUILDER_VERSION,
|
|
41
45
|
PROPOSER_WEIGHT,
|
|
42
46
|
SYNC_COMMITTEE_SUBNET_COUNT,
|
|
43
47
|
SYNC_REWARD_WEIGHT,
|
|
@@ -53,6 +57,7 @@ import {
|
|
|
53
57
|
VERSIONED_HASH_VERSION_KZG,
|
|
54
58
|
WEIGHT_DENOMINATOR,
|
|
55
59
|
WITHDRAWAL_REQUEST_TYPE,
|
|
60
|
+
ZERO_HASH_HEX,
|
|
56
61
|
} from "@lodestar/params";
|
|
57
62
|
|
|
58
63
|
/**
|
|
@@ -69,6 +74,7 @@ export const specConstants = {
|
|
|
69
74
|
DEPOSIT_CONTRACT_TREE_DEPTH,
|
|
70
75
|
JUSTIFICATION_BITS_LENGTH,
|
|
71
76
|
ENDIANNESS: "little",
|
|
77
|
+
EMPTY_BLOCK_HASH: ZERO_HASH_HEX,
|
|
72
78
|
// ## Withdrawal prefixes
|
|
73
79
|
BLS_WITHDRAWAL_PREFIX: toHexByte(BLS_WITHDRAWAL_PREFIX),
|
|
74
80
|
ETH1_ADDRESS_WITHDRAWAL_PREFIX: toHexByte(ETH1_ADDRESS_WITHDRAWAL_PREFIX),
|
|
@@ -138,6 +144,10 @@ export const specConstants = {
|
|
|
138
144
|
BUILDER_INDEX_SELF_BUILD,
|
|
139
145
|
BUILDER_PAYMENT_THRESHOLD_NUMERATOR,
|
|
140
146
|
BUILDER_PAYMENT_THRESHOLD_DENOMINATOR,
|
|
147
|
+
PAYLOAD_BUILDER_VERSION,
|
|
148
|
+
DOMAIN_BUILDER_DEPOSIT,
|
|
149
|
+
BUILDER_DEPOSIT_REQUEST_TYPE: toHexByte(BUILDER_DEPOSIT_REQUEST_TYPE),
|
|
150
|
+
BUILDER_EXIT_REQUEST_TYPE: toHexByte(BUILDER_EXIT_REQUEST_TYPE),
|
|
141
151
|
};
|
|
142
152
|
|
|
143
153
|
/** Convert single-byte numbers to hex strings for API spec compliance */
|
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
import {routes} from "@lodestar/api";
|
|
2
2
|
import {ApplicationMethods} from "@lodestar/api/server";
|
|
3
|
-
import {ExecutionStatus} from "@lodestar/fork-choice";
|
|
3
|
+
import {ExecutionStatus, PayloadStatus} from "@lodestar/fork-choice";
|
|
4
4
|
import {ForkPostDeneb, ZERO_HASH_HEX, isForkPostDeneb, isForkPostFulu} from "@lodestar/params";
|
|
5
|
+
import {computeTimeAtSlot} from "@lodestar/state-transition";
|
|
5
6
|
import {BeaconState, DataColumnSidecar, DataColumnSidecars, type SignedBeaconBlock, sszTypesFor} from "@lodestar/types";
|
|
6
7
|
import {toRootHex} from "@lodestar/utils";
|
|
7
8
|
import {getBlobKzgCommitments} from "../../../util/dataColumns.js";
|
|
@@ -12,6 +13,29 @@ import {getStateResponseWithRegen} from "../beacon/state/utils.js";
|
|
|
12
13
|
import {ApiModules} from "../types.js";
|
|
13
14
|
import {assertUniqueItems} from "../utils.js";
|
|
14
15
|
|
|
16
|
+
function toForkChoiceValidity(status: ExecutionStatus): "valid" | "invalid" | "optimistic" {
|
|
17
|
+
switch (status) {
|
|
18
|
+
case ExecutionStatus.Valid:
|
|
19
|
+
return "valid";
|
|
20
|
+
case ExecutionStatus.Invalid:
|
|
21
|
+
return "invalid";
|
|
22
|
+
case ExecutionStatus.Syncing:
|
|
23
|
+
case ExecutionStatus.PreMerge:
|
|
24
|
+
return "optimistic";
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
function toPayloadStatusName(status: PayloadStatus): "pending" | "empty" | "full" {
|
|
29
|
+
switch (status) {
|
|
30
|
+
case PayloadStatus.PENDING:
|
|
31
|
+
return "pending";
|
|
32
|
+
case PayloadStatus.EMPTY:
|
|
33
|
+
return "empty";
|
|
34
|
+
case PayloadStatus.FULL:
|
|
35
|
+
return "full";
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
|
|
15
39
|
export function getDebugApi({
|
|
16
40
|
chain,
|
|
17
41
|
config,
|
|
@@ -40,23 +64,60 @@ export function getDebugApi({
|
|
|
40
64
|
justifiedEpoch: node.justifiedEpoch,
|
|
41
65
|
finalizedEpoch: node.finalizedEpoch,
|
|
42
66
|
weight: node.weight,
|
|
43
|
-
validity: (
|
|
44
|
-
switch (node.executionStatus) {
|
|
45
|
-
case ExecutionStatus.Valid:
|
|
46
|
-
return "valid";
|
|
47
|
-
case ExecutionStatus.Invalid:
|
|
48
|
-
return "invalid";
|
|
49
|
-
case ExecutionStatus.Syncing:
|
|
50
|
-
case ExecutionStatus.PreMerge:
|
|
51
|
-
return "optimistic";
|
|
52
|
-
}
|
|
53
|
-
})(),
|
|
67
|
+
validity: toForkChoiceValidity(node.executionStatus),
|
|
54
68
|
executionBlockHash: node.executionPayloadBlockHash ?? ZERO_HASH_HEX,
|
|
55
69
|
})),
|
|
56
70
|
},
|
|
57
71
|
};
|
|
58
72
|
},
|
|
59
73
|
|
|
74
|
+
async getDebugForkChoiceV2() {
|
|
75
|
+
const {forkChoice} = chain;
|
|
76
|
+
return {
|
|
77
|
+
data: {
|
|
78
|
+
justifiedCheckpoint: forkChoice.getJustifiedCheckpoint(),
|
|
79
|
+
finalizedCheckpoint: forkChoice.getFinalizedCheckpoint(),
|
|
80
|
+
forkChoiceNodes: forkChoice.getAllNodes().map((node) => {
|
|
81
|
+
// Payload-specific fields apply only to a revealed Gloas payload = the FULL variant of a
|
|
82
|
+
// Gloas block
|
|
83
|
+
const ptc = node.payloadStatus === PayloadStatus.FULL ? forkChoice.getPTCVoteCounts(node.blockRoot) : null;
|
|
84
|
+
return {
|
|
85
|
+
payloadStatus: toPayloadStatusName(node.payloadStatus),
|
|
86
|
+
slot: node.slot,
|
|
87
|
+
blockRoot: node.blockRoot,
|
|
88
|
+
parentRoot: node.parentRoot,
|
|
89
|
+
weight: node.weight,
|
|
90
|
+
validity: toForkChoiceValidity(node.executionStatus),
|
|
91
|
+
executionBlockHash: node.executionPayloadBlockHash ?? ZERO_HASH_HEX,
|
|
92
|
+
extraData: {
|
|
93
|
+
executionOptimistic: isOptimisticBlock(node),
|
|
94
|
+
timestamp: computeTimeAtSlot(config, node.slot, chain.genesisTime),
|
|
95
|
+
target: node.targetRoot,
|
|
96
|
+
justifiedEpoch: node.justifiedEpoch,
|
|
97
|
+
finalizedEpoch: node.finalizedEpoch,
|
|
98
|
+
unrealizedJustifiedEpoch: node.unrealizedJustifiedEpoch,
|
|
99
|
+
unrealizedFinalizedEpoch: node.unrealizedFinalizedEpoch,
|
|
100
|
+
payloadAttesterCount: ptc?.attesterCount ?? null,
|
|
101
|
+
payloadAvailabilityYesCount: ptc?.payloadPresentCount ?? null,
|
|
102
|
+
payloadDataAvailabilityYesCount: ptc?.dataAvailableCount ?? null,
|
|
103
|
+
gasLimit:
|
|
104
|
+
node.payloadStatus === PayloadStatus.FULL && "executionPayloadGasLimit" in node
|
|
105
|
+
? node.executionPayloadGasLimit
|
|
106
|
+
: null,
|
|
107
|
+
},
|
|
108
|
+
};
|
|
109
|
+
}),
|
|
110
|
+
extraData: {
|
|
111
|
+
unrealizedJustifiedCheckpoint: forkChoice.getUnrealizedJustifiedCheckpoint(),
|
|
112
|
+
unrealizedFinalizedCheckpoint: forkChoice.getUnrealizedFinalizedCheckpoint(),
|
|
113
|
+
proposerBoostRoot: forkChoice.getProposerBoostRoot(),
|
|
114
|
+
previousProposerBoostRoot: forkChoice.getPreviousProposerBoostRoot(),
|
|
115
|
+
headRoot: forkChoice.getHeadRoot(),
|
|
116
|
+
},
|
|
117
|
+
},
|
|
118
|
+
};
|
|
119
|
+
},
|
|
120
|
+
|
|
60
121
|
async getProtoArrayNodes() {
|
|
61
122
|
const nodes = chain.forkChoice.getAllNodes().map((node) => ({
|
|
62
123
|
// if node has executionPayloadNumber, it will overwrite the below default
|
|
@@ -280,6 +280,36 @@ export function getLodestarApi({
|
|
|
280
280
|
};
|
|
281
281
|
},
|
|
282
282
|
|
|
283
|
+
async getFastConfirmationInfo() {
|
|
284
|
+
const confirmedRoot = chain.forkChoice.getConfirmedRoot();
|
|
285
|
+
const confirmedBlock = chain.forkChoice.getConfirmedBlock();
|
|
286
|
+
const justifiedCheckpoint = chain.forkChoice.getJustifiedCheckpoint();
|
|
287
|
+
const finalizedCheckpoint = chain.forkChoice.getFinalizedCheckpoint();
|
|
288
|
+
const headRoot = chain.forkChoice.getHeadRoot();
|
|
289
|
+
const head = chain.forkChoice.getHead();
|
|
290
|
+
|
|
291
|
+
return {
|
|
292
|
+
data: {
|
|
293
|
+
confirmed: {
|
|
294
|
+
rootHex: confirmedRoot,
|
|
295
|
+
slot: confirmedBlock?.slot ?? null,
|
|
296
|
+
},
|
|
297
|
+
head: {
|
|
298
|
+
rootHex: headRoot,
|
|
299
|
+
slot: head.slot,
|
|
300
|
+
},
|
|
301
|
+
justifiedCheckpoint: {
|
|
302
|
+
rootHex: justifiedCheckpoint.rootHex,
|
|
303
|
+
epoch: justifiedCheckpoint.epoch,
|
|
304
|
+
},
|
|
305
|
+
finalizedCheckpoint: {
|
|
306
|
+
rootHex: finalizedCheckpoint.rootHex,
|
|
307
|
+
epoch: finalizedCheckpoint.epoch,
|
|
308
|
+
},
|
|
309
|
+
},
|
|
310
|
+
};
|
|
311
|
+
},
|
|
312
|
+
|
|
283
313
|
async getAttesterSlashingsFromBlocks({signedBlocks}) {
|
|
284
314
|
const attestations = new Map<Epoch, Attestation[]>();
|
|
285
315
|
|