@lodestar/beacon-node 1.51.0-dev.ec1447da07 → 1.51.0-dev.f33a955402

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.
Files changed (52) hide show
  1. package/lib/api/impl/beacon/blocks/index.d.ts.map +1 -1
  2. package/lib/api/impl/beacon/blocks/index.js +11 -22
  3. package/lib/api/impl/beacon/blocks/index.js.map +1 -1
  4. package/lib/api/impl/validator/index.d.ts.map +1 -1
  5. package/lib/api/impl/validator/index.js +4 -1
  6. package/lib/api/impl/validator/index.js.map +1 -1
  7. package/lib/chain/GetBlobsTracker.d.ts +11 -0
  8. package/lib/chain/GetBlobsTracker.d.ts.map +1 -1
  9. package/lib/chain/GetBlobsTracker.js +83 -27
  10. package/lib/chain/GetBlobsTracker.js.map +1 -1
  11. package/lib/chain/blocks/importExecutionPayload.d.ts +4 -1
  12. package/lib/chain/blocks/importExecutionPayload.d.ts.map +1 -1
  13. package/lib/chain/blocks/importExecutionPayload.js +2 -1
  14. package/lib/chain/blocks/importExecutionPayload.js.map +1 -1
  15. package/lib/chain/blocks/index.js +2 -2
  16. package/lib/chain/blocks/index.js.map +1 -1
  17. package/lib/chain/blocks/payloadEnvelopeProcessor.d.ts +5 -5
  18. package/lib/chain/blocks/payloadEnvelopeProcessor.js +5 -5
  19. package/lib/chain/blocks/verifyBlock.d.ts.map +1 -1
  20. package/lib/chain/blocks/verifyBlock.js +1 -1
  21. package/lib/chain/blocks/verifyBlock.js.map +1 -1
  22. package/lib/chain/blocks/verifyBlocksDataAvailability.d.ts.map +1 -1
  23. package/lib/chain/blocks/verifyBlocksDataAvailability.js +8 -1
  24. package/lib/chain/blocks/verifyBlocksDataAvailability.js.map +1 -1
  25. package/lib/chain/blocks/verifyPayloadsDataAvailability.d.ts +3 -3
  26. package/lib/chain/blocks/verifyPayloadsDataAvailability.d.ts.map +1 -1
  27. package/lib/chain/blocks/verifyPayloadsDataAvailability.js +13 -6
  28. package/lib/chain/blocks/verifyPayloadsDataAvailability.js.map +1 -1
  29. package/lib/chain/errors/blockError.d.ts +1 -1
  30. package/lib/chain/errors/blockError.d.ts.map +1 -1
  31. package/lib/chain/errors/blockError.js +1 -1
  32. package/lib/chain/errors/blockError.js.map +1 -1
  33. package/lib/chain/options.d.ts +0 -1
  34. package/lib/chain/options.d.ts.map +1 -1
  35. package/lib/chain/options.js +0 -1
  36. package/lib/chain/options.js.map +1 -1
  37. package/lib/network/processor/gossipHandlers.d.ts.map +1 -1
  38. package/lib/network/processor/gossipHandlers.js +6 -3
  39. package/lib/network/processor/gossipHandlers.js.map +1 -1
  40. package/package.json +15 -15
  41. package/src/api/impl/beacon/blocks/index.ts +12 -24
  42. package/src/api/impl/validator/index.ts +4 -1
  43. package/src/chain/GetBlobsTracker.ts +95 -38
  44. package/src/chain/blocks/importExecutionPayload.ts +5 -1
  45. package/src/chain/blocks/index.ts +6 -2
  46. package/src/chain/blocks/payloadEnvelopeProcessor.ts +5 -5
  47. package/src/chain/blocks/verifyBlock.ts +1 -0
  48. package/src/chain/blocks/verifyBlocksDataAvailability.ts +10 -1
  49. package/src/chain/blocks/verifyPayloadsDataAvailability.ts +16 -6
  50. package/src/chain/errors/blockError.ts +1 -1
  51. package/src/chain/options.ts +0 -2
  52. package/src/network/processor/gossipHandlers.ts +6 -3
@@ -1,4 +1,6 @@
1
1
  import {DataAvailabilityStatus} from "@lodestar/state-transition";
2
+ import {TimeoutError} from "@lodestar/utils";
3
+ import {BlockError, BlockErrorCode} from "../errors/index.js";
2
4
  import {DAData, DAType, IBlockInput} from "./blockInput/index.js";
3
5
 
4
6
  // we can now wait for full 12 seconds because unavailable block sync will try pulling
@@ -22,7 +24,14 @@ export async function verifyBlocksDataAvailability(
22
24
  for (const blockInput of blocks) {
23
25
  // block verification is triggered on a verified gossip block so we only need to wait for all data
24
26
  if (!blockInput.hasAllData()) {
25
- promises.push(blockInput.waitForAllData(BLOB_AVAILABILITY_TIMEOUT, signal));
27
+ promises.push(
28
+ blockInput.waitForAllData(BLOB_AVAILABILITY_TIMEOUT, signal).catch((e) => {
29
+ if (e instanceof TimeoutError) {
30
+ throw new BlockError(blockInput.getBlock(), {code: BlockErrorCode.DATA_UNAVAILABLE});
31
+ }
32
+ throw e;
33
+ })
34
+ );
26
35
  }
27
36
  }
28
37
  await Promise.all(promises);
@@ -1,18 +1,18 @@
1
+ import {ChainForkConfig} from "@lodestar/config";
1
2
  import {DataAvailabilityStatus} from "@lodestar/state-transition";
2
3
  import {gloas} from "@lodestar/types";
4
+ import {TimeoutError} from "@lodestar/utils";
3
5
  import {PayloadEnvelopeInput} from "../seenCache/seenPayloadEnvelopeInput.js";
4
-
5
- // we can now wait for full 12 seconds because sync and reconstruction will try pulling
6
- // the data columns from the network anyway while the envelope is being processed
7
- export const PAYLOAD_DATA_AVAILABILITY_TIMEOUT = 12_000;
6
+ import {PayloadError, PayloadErrorCode} from "./importExecutionPayload.js";
8
7
 
9
8
  /**
10
9
  * Verifies that all payload envelope inputs have their data columns available.
11
- * - Waits a max of PAYLOAD_DATA_AVAILABILITY_TIMEOUT for all data to be available
10
+ * - Waits a max of one slot duration of the payload's fork for all data to be available
12
11
  * - Returns the time at which all data was available
13
12
  * - Returns the data availability status for each payload input
14
13
  */
15
14
  export async function verifyPayloadsDataAvailability(
15
+ config: ChainForkConfig,
16
16
  payloadInputs: PayloadEnvelopeInput[],
17
17
  signal: AbortSignal
18
18
  ): Promise<{
@@ -22,7 +22,17 @@ export async function verifyPayloadsDataAvailability(
22
22
  const promises: Promise<gloas.DataColumnSidecar[]>[] = [];
23
23
  for (const payloadInput of payloadInputs) {
24
24
  if (!payloadInput.hasAllData()) {
25
- promises.push(payloadInput.waitForAllData(PAYLOAD_DATA_AVAILABILITY_TIMEOUT, signal));
25
+ // Sync and reconstruction keep pulling the data columns from the network while we wait. The wait is
26
+ // capped at one slot because the payload queue is serial: a longer wait lets consecutive unavailable
27
+ // payloads push every later payload import further behind with each slot.
28
+ promises.push(
29
+ payloadInput.waitForAllData(config.getSlotDurationMs(payloadInput.forkName), signal).catch((e) => {
30
+ if (e instanceof TimeoutError) {
31
+ throw new PayloadError(payloadInput, {code: PayloadErrorCode.DATA_UNAVAILABLE});
32
+ }
33
+ throw e;
34
+ })
35
+ );
26
36
  }
27
37
  }
28
38
  await Promise.all(promises);
@@ -72,7 +72,7 @@ export enum BlockErrorCode {
72
72
  * whoever served the block MAY be downscored. Mirrors PayloadErrorCode.EXECUTION_ENGINE_INVALID.
73
73
  */
74
74
  EXECUTION_ENGINE_INVALID = "BLOCK_ERROR_EXECUTION_INVALID",
75
- /** The blobs are unavailable */
75
+ /** The blob or column data did not arrive within the availability wait */
76
76
  DATA_UNAVAILABLE = "BLOCK_ERROR_DATA_UNAVAILABLE",
77
77
  /** Block contains too many kzg commitments */
78
78
  TOO_MANY_KZG_COMMITMENTS = "BLOCK_ERROR_TOO_MANY_KZG_COMMITMENTS",
@@ -48,7 +48,6 @@ export type IChainOptions = BlockProcessOpts &
48
48
  /** Max number of produced block roots (blinded or full) cached for broadcast validations */
49
49
  maxCachedProducedRoots?: number;
50
50
  initialCustodyGroupCount?: number;
51
- broadcastValidationStrictness?: string;
52
51
  minSameMessageSignatureSetsToBatch: number;
53
52
  archiveDateEpochs?: number;
54
53
  nHistoricalStatesFileDataStore?: boolean;
@@ -121,7 +120,6 @@ export const defaultChainOptions: IChainOptions = {
121
120
  // for attestation validation, having this value ensures we don't have to regen states most of the time
122
121
  maxSkipSlots: 32,
123
122
  disableProposerSlashings: false,
124
- broadcastValidationStrictness: "warn",
125
123
  // should be less than or equal to MIN_SIGNATURE_SETS_TO_BATCH_VERIFY
126
124
  // batching too much may block the I/O thread so if useWorker=false, suggest this value to be 32
127
125
  // since this batch attestation work is designed to work with useWorker=true, make this the lowest value
@@ -718,11 +718,10 @@ function getSequentialHandlers(modules: ValidatorFnsModules, options: GossipHand
718
718
 
719
719
  if (e instanceof BlockError) {
720
720
  switch (e.type.code) {
721
- case BlockErrorCode.DATA_UNAVAILABLE: {
722
- // Error is quite frequent and not critical
721
+ case BlockErrorCode.DATA_UNAVAILABLE:
722
+ // Data did not arrive in time, BlockInputSync keeps pulling it and retries the import
723
723
  logLevel = LogLevel.debug;
724
724
  break;
725
- }
726
725
  // ALREADY_KNOWN should not happen with ignoreIfKnown=true above
727
726
  // PARENT_BLOCK_UNKNOWN should not happen, we handled this in validateBeaconBlock() function above
728
727
  case BlockErrorCode.ALREADY_KNOWN:
@@ -1358,6 +1357,10 @@ function getSequentialHandlers(modules: ValidatorFnsModules, options: GossipHand
1358
1357
 
1359
1358
  if (e instanceof PayloadError) {
1360
1359
  switch (e.type.code) {
1360
+ case PayloadErrorCode.DATA_UNAVAILABLE:
1361
+ // Columns did not arrive in time, BlockInputSync keeps pulling them and retries the import
1362
+ logLevel = LogLevel.debug;
1363
+ break;
1361
1364
  // BLOCK_NOT_IN_FORK_CHOICE should not happen, validateGossipExecutionPayloadEnvelope above
1362
1365
  // already verified the block is in fork choice
1363
1366
  case PayloadErrorCode.BLOCK_NOT_IN_FORK_CHOICE: