|
|
|
@ -161,18 +161,19 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void withAllowedDepositRequestsAndContractAddress_DepositRequestsAreParsed() { |
|
|
|
|
final AbstractBlockCreator blockCreator = |
|
|
|
|
final CreateOn miningOn = |
|
|
|
|
blockCreatorWithAllowedDepositRequests(DEFAULT_DEPOSIT_CONTRACT_ADDRESS); |
|
|
|
|
|
|
|
|
|
final BlockCreationResult blockCreationResult = |
|
|
|
|
blockCreator.createBlock( |
|
|
|
|
miningOn.blockCreator.createBlock( |
|
|
|
|
Optional.empty(), |
|
|
|
|
Optional.empty(), |
|
|
|
|
Optional.of(emptyList()), |
|
|
|
|
Optional.empty(), |
|
|
|
|
Optional.empty(), |
|
|
|
|
1L, |
|
|
|
|
false); |
|
|
|
|
false, |
|
|
|
|
miningOn.parentHeader); |
|
|
|
|
|
|
|
|
|
List<Request> depositRequests = emptyList(); |
|
|
|
|
final Hash requestsRoot = BodyValidation.requestsRoot(depositRequests); |
|
|
|
@ -182,17 +183,18 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void withAllowedDepositRequestsAndNoContractAddress_DepositRequestsAreNotParsed() { |
|
|
|
|
final AbstractBlockCreator blockCreator = blockCreatorWithAllowedDepositRequests(null); |
|
|
|
|
final CreateOn miningOn = blockCreatorWithAllowedDepositRequests(null); |
|
|
|
|
|
|
|
|
|
final BlockCreationResult blockCreationResult = |
|
|
|
|
blockCreator.createBlock( |
|
|
|
|
miningOn.blockCreator.createBlock( |
|
|
|
|
Optional.empty(), |
|
|
|
|
Optional.empty(), |
|
|
|
|
Optional.of(emptyList()), |
|
|
|
|
Optional.empty(), |
|
|
|
|
Optional.empty(), |
|
|
|
|
1L, |
|
|
|
|
false); |
|
|
|
|
false, |
|
|
|
|
miningOn.parentHeader); |
|
|
|
|
|
|
|
|
|
assertThat(blockCreationResult.getBlock().getHeader().getRequestsRoot()).isEmpty(); |
|
|
|
|
assertThat(blockCreationResult.getBlock().getBody().getRequests()).isEmpty(); |
|
|
|
@ -200,53 +202,28 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void withProhibitedDepositRequests_DepositRequestsAreNotParsed() { |
|
|
|
|
final AbstractBlockCreator blockCreator = blockCreatorWithProhibitedDepositRequests(); |
|
|
|
|
|
|
|
|
|
final CreateOn miningOn = blockCreatorWithProhibitedDepositRequests(); |
|
|
|
|
|
|
|
|
|
final BlockCreationResult blockCreationResult = |
|
|
|
|
blockCreator.createBlock( |
|
|
|
|
miningOn.blockCreator.createBlock( |
|
|
|
|
Optional.empty(), |
|
|
|
|
Optional.empty(), |
|
|
|
|
Optional.of(emptyList()), |
|
|
|
|
Optional.empty(), |
|
|
|
|
Optional.empty(), |
|
|
|
|
1L, |
|
|
|
|
false); |
|
|
|
|
false, |
|
|
|
|
miningOn.parentHeader); |
|
|
|
|
|
|
|
|
|
assertThat(blockCreationResult.getBlock().getHeader().getRequestsRoot()).isEmpty(); |
|
|
|
|
assertThat(blockCreationResult.getBlock().getBody().getRequests()).isEmpty(); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
private AbstractBlockCreator blockCreatorWithAllowedDepositRequests( |
|
|
|
|
final Address depositContractAddress) { |
|
|
|
|
final ProtocolSpecAdapters protocolSpecAdapters = |
|
|
|
|
ProtocolSpecAdapters.create( |
|
|
|
|
0, |
|
|
|
|
specBuilder -> |
|
|
|
|
specBuilder |
|
|
|
|
.requestsValidator( |
|
|
|
|
new RequestsValidatorCoordinator.Builder() |
|
|
|
|
.addValidator( |
|
|
|
|
RequestType.DEPOSIT, |
|
|
|
|
new DepositRequestValidator((depositContractAddress))) |
|
|
|
|
.build()) |
|
|
|
|
.requestProcessorCoordinator( |
|
|
|
|
new RequestProcessorCoordinator.Builder() |
|
|
|
|
.addProcessor( |
|
|
|
|
RequestType.DEPOSIT, |
|
|
|
|
new DepositRequestProcessor(depositContractAddress)) |
|
|
|
|
.build())); |
|
|
|
|
return createBlockCreator(protocolSpecAdapters); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
private AbstractBlockCreator blockCreatorWithProhibitedDepositRequests() { |
|
|
|
|
final ProtocolSpecAdapters protocolSpecAdapters = |
|
|
|
|
ProtocolSpecAdapters.create(0, specBuilder -> specBuilder); |
|
|
|
|
return createBlockCreator(protocolSpecAdapters); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void withProcessorAndEmptyWithdrawals_NoWithdrawalsAreProcessed() { |
|
|
|
|
final AbstractBlockCreator blockCreator = blockCreatorWithWithdrawalsProcessor(); |
|
|
|
|
final CreateOn miningOn = blockCreatorWithWithdrawalsProcessor(); |
|
|
|
|
final AbstractBlockCreator blockCreator = miningOn.blockCreator; |
|
|
|
|
final BlockCreationResult blockCreationResult = |
|
|
|
|
blockCreator.createBlock( |
|
|
|
|
Optional.empty(), |
|
|
|
@ -255,7 +232,8 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
Optional.empty(), |
|
|
|
|
Optional.empty(), |
|
|
|
|
1L, |
|
|
|
|
false); |
|
|
|
|
false, |
|
|
|
|
miningOn.parentHeader); |
|
|
|
|
verify(withdrawalsProcessor, never()).processWithdrawals(any(), any()); |
|
|
|
|
assertThat(blockCreationResult.getBlock().getHeader().getWithdrawalsRoot()).isEmpty(); |
|
|
|
|
assertThat(blockCreationResult.getBlock().getBody().getWithdrawals()).isEmpty(); |
|
|
|
@ -263,7 +241,8 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void withNoProcessorAndEmptyWithdrawals_NoWithdrawalsAreNotProcessed() { |
|
|
|
|
final AbstractBlockCreator blockCreator = blockCreatorWithoutWithdrawalsProcessor(); |
|
|
|
|
final CreateOn miningOn = blockCreatorWithoutWithdrawalsProcessor(); |
|
|
|
|
final AbstractBlockCreator blockCreator = miningOn.blockCreator; |
|
|
|
|
final BlockCreationResult blockCreationResult = |
|
|
|
|
blockCreator.createBlock( |
|
|
|
|
Optional.empty(), |
|
|
|
@ -272,7 +251,8 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
Optional.empty(), |
|
|
|
|
Optional.empty(), |
|
|
|
|
1L, |
|
|
|
|
false); |
|
|
|
|
false, |
|
|
|
|
miningOn.parentHeader); |
|
|
|
|
verify(withdrawalsProcessor, never()).processWithdrawals(any(), any()); |
|
|
|
|
assertThat(blockCreationResult.getBlock().getHeader().getWithdrawalsRoot()).isEmpty(); |
|
|
|
|
assertThat(blockCreationResult.getBlock().getBody().getWithdrawals()).isEmpty(); |
|
|
|
@ -280,7 +260,8 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void withProcessorAndWithdrawals_WithdrawalsAreProcessed() { |
|
|
|
|
final AbstractBlockCreator blockCreator = blockCreatorWithWithdrawalsProcessor(); |
|
|
|
|
final CreateOn miningOn = blockCreatorWithWithdrawalsProcessor(); |
|
|
|
|
final AbstractBlockCreator blockCreator = miningOn.blockCreator; |
|
|
|
|
final List<Withdrawal> withdrawals = |
|
|
|
|
List.of(new Withdrawal(UInt64.ONE, UInt64.ONE, Address.fromHexString("0x1"), GWei.ONE)); |
|
|
|
|
final BlockCreationResult blockCreationResult = |
|
|
|
@ -291,7 +272,8 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
Optional.empty(), |
|
|
|
|
Optional.empty(), |
|
|
|
|
1L, |
|
|
|
|
false); |
|
|
|
|
false, |
|
|
|
|
miningOn.parentHeader); |
|
|
|
|
|
|
|
|
|
final Hash withdrawalsRoot = BodyValidation.withdrawalsRoot(withdrawals); |
|
|
|
|
verify(withdrawalsProcessor).processWithdrawals(eq(withdrawals), any()); |
|
|
|
@ -302,7 +284,8 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void withNoProcessorAndWithdrawals_WithdrawalsAreNotProcessed() { |
|
|
|
|
final AbstractBlockCreator blockCreator = blockCreatorWithoutWithdrawalsProcessor(); |
|
|
|
|
final CreateOn miningOn = blockCreatorWithoutWithdrawalsProcessor(); |
|
|
|
|
final AbstractBlockCreator blockCreator = miningOn.blockCreator; |
|
|
|
|
final List<Withdrawal> withdrawals = |
|
|
|
|
List.of(new Withdrawal(UInt64.ONE, UInt64.ONE, Address.fromHexString("0x1"), GWei.ONE)); |
|
|
|
|
final BlockCreationResult blockCreationResult = |
|
|
|
@ -313,7 +296,8 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
Optional.empty(), |
|
|
|
|
Optional.empty(), |
|
|
|
|
1L, |
|
|
|
|
false); |
|
|
|
|
false, |
|
|
|
|
miningOn.parentHeader); |
|
|
|
|
verify(withdrawalsProcessor, never()).processWithdrawals(any(), any()); |
|
|
|
|
assertThat(blockCreationResult.getBlock().getHeader().getWithdrawalsRoot()).isEmpty(); |
|
|
|
|
assertThat(blockCreationResult.getBlock().getBody().getWithdrawals()).isEmpty(); |
|
|
|
@ -321,7 +305,8 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
public void computesGasUsageFromIncludedTransactions() { |
|
|
|
|
final AbstractBlockCreator blockCreator = blockCreatorWithBlobGasSupport(); |
|
|
|
|
final CreateOn miningOn = blockCreatorWithBlobGasSupport(); |
|
|
|
|
final AbstractBlockCreator blockCreator = miningOn.blockCreator; |
|
|
|
|
BlobTestFixture blobTestFixture = new BlobTestFixture(); |
|
|
|
|
BlobsWithCommitments bwc = blobTestFixture.createBlobsWithCommitments(6); |
|
|
|
|
TransactionTestFixture ttf = new TransactionTestFixture(); |
|
|
|
@ -345,14 +330,15 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
Optional.empty(), |
|
|
|
|
Optional.empty(), |
|
|
|
|
1L, |
|
|
|
|
false); |
|
|
|
|
false, |
|
|
|
|
miningOn.parentHeader); |
|
|
|
|
long blobGasUsage = blockCreationResult.getBlock().getHeader().getGasUsed(); |
|
|
|
|
assertThat(blobGasUsage).isNotZero(); |
|
|
|
|
BlobGas excessBlobGas = blockCreationResult.getBlock().getHeader().getExcessBlobGas().get(); |
|
|
|
|
assertThat(excessBlobGas).isNotNull(); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
private AbstractBlockCreator blockCreatorWithBlobGasSupport() { |
|
|
|
|
private CreateOn blockCreatorWithBlobGasSupport() { |
|
|
|
|
final var alwaysValidTransactionValidatorFactory = mock(TransactionValidatorFactory.class); |
|
|
|
|
when(alwaysValidTransactionValidatorFactory.get()) |
|
|
|
|
.thenReturn(new AlwaysValidTransactionValidator()); |
|
|
|
@ -369,20 +355,49 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
return createBlockCreator(protocolSpecAdapters); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
private AbstractBlockCreator blockCreatorWithWithdrawalsProcessor() { |
|
|
|
|
private CreateOn blockCreatorWithProhibitedDepositRequests() { |
|
|
|
|
final ProtocolSpecAdapters protocolSpecAdapters = |
|
|
|
|
ProtocolSpecAdapters.create(0, specBuilder -> specBuilder); |
|
|
|
|
return createBlockCreator(protocolSpecAdapters); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
private CreateOn blockCreatorWithWithdrawalsProcessor() { |
|
|
|
|
final ProtocolSpecAdapters protocolSpecAdapters = |
|
|
|
|
ProtocolSpecAdapters.create( |
|
|
|
|
0, specBuilder -> specBuilder.withdrawalsProcessor(withdrawalsProcessor)); |
|
|
|
|
return createBlockCreator(protocolSpecAdapters); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
private AbstractBlockCreator blockCreatorWithoutWithdrawalsProcessor() { |
|
|
|
|
private CreateOn blockCreatorWithoutWithdrawalsProcessor() { |
|
|
|
|
final ProtocolSpecAdapters protocolSpecAdapters = |
|
|
|
|
ProtocolSpecAdapters.create(0, specBuilder -> specBuilder.withdrawalsProcessor(null)); |
|
|
|
|
return createBlockCreator(protocolSpecAdapters); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
private AbstractBlockCreator createBlockCreator(final ProtocolSpecAdapters protocolSpecAdapters) { |
|
|
|
|
private CreateOn blockCreatorWithAllowedDepositRequests(final Address depositContractAddress) { |
|
|
|
|
final ProtocolSpecAdapters protocolSpecAdapters = |
|
|
|
|
ProtocolSpecAdapters.create( |
|
|
|
|
0, |
|
|
|
|
specBuilder -> |
|
|
|
|
specBuilder |
|
|
|
|
.requestsValidator( |
|
|
|
|
new RequestsValidatorCoordinator.Builder() |
|
|
|
|
.addValidator( |
|
|
|
|
RequestType.DEPOSIT, |
|
|
|
|
new DepositRequestValidator((depositContractAddress))) |
|
|
|
|
.build()) |
|
|
|
|
.requestProcessorCoordinator( |
|
|
|
|
new RequestProcessorCoordinator.Builder() |
|
|
|
|
.addProcessor( |
|
|
|
|
RequestType.DEPOSIT, |
|
|
|
|
new DepositRequestProcessor(depositContractAddress)) |
|
|
|
|
.build())); |
|
|
|
|
return createBlockCreator(protocolSpecAdapters); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
record CreateOn(AbstractBlockCreator blockCreator, BlockHeader parentHeader) {} |
|
|
|
|
|
|
|
|
|
private CreateOn createBlockCreator(final ProtocolSpecAdapters protocolSpecAdapters) { |
|
|
|
|
|
|
|
|
|
final var genesisConfigFile = GenesisConfigFile.fromResource("/block-creation-genesis.json"); |
|
|
|
|
final ExecutionContextTestFixture executionContextTestFixture = |
|
|
|
@ -403,11 +418,15 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
.build(); |
|
|
|
|
|
|
|
|
|
final MutableBlockchain blockchain = executionContextTestFixture.getBlockchain(); |
|
|
|
|
BlockHeader parentHeader = blockchain.getChainHeadHeader(); |
|
|
|
|
final TransactionPoolConfiguration poolConf = |
|
|
|
|
ImmutableTransactionPoolConfiguration.builder().txPoolMaxSize(100).build(); |
|
|
|
|
final AbstractPendingTransactionsSorter sorter = |
|
|
|
|
new GasPricePendingTransactionsSorter( |
|
|
|
|
poolConf, Clock.systemUTC(), new NoOpMetricsSystem(), blockchain::getChainHeadHeader); |
|
|
|
|
poolConf, |
|
|
|
|
Clock.systemUTC(), |
|
|
|
|
new NoOpMetricsSystem(), |
|
|
|
|
Suppliers.ofInstance(parentHeader)); |
|
|
|
|
|
|
|
|
|
final EthContext ethContext = mock(EthContext.class, RETURNS_DEEP_STUBS); |
|
|
|
|
when(ethContext.getEthPeers().subscribeConnect(any())).thenReturn(1L); |
|
|
|
@ -435,15 +454,16 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
.build()) |
|
|
|
|
.build(); |
|
|
|
|
|
|
|
|
|
return new TestBlockCreator( |
|
|
|
|
miningParameters, |
|
|
|
|
__ -> Address.ZERO, |
|
|
|
|
__ -> Bytes.fromHexString("deadbeef"), |
|
|
|
|
transactionPool, |
|
|
|
|
executionContextTestFixture.getProtocolContext(), |
|
|
|
|
executionContextTestFixture.getProtocolSchedule(), |
|
|
|
|
blockchain.getChainHeadHeader(), |
|
|
|
|
ethScheduler); |
|
|
|
|
return new CreateOn( |
|
|
|
|
new TestBlockCreator( |
|
|
|
|
miningParameters, |
|
|
|
|
__ -> Address.ZERO, |
|
|
|
|
__ -> Bytes.fromHexString("deadbeef"), |
|
|
|
|
transactionPool, |
|
|
|
|
executionContextTestFixture.getProtocolContext(), |
|
|
|
|
executionContextTestFixture.getProtocolSchedule(), |
|
|
|
|
ethScheduler), |
|
|
|
|
parentHeader); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
static class TestBlockCreator extends AbstractBlockCreator { |
|
|
|
@ -455,7 +475,6 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
final TransactionPool transactionPool, |
|
|
|
|
final ProtocolContext protocolContext, |
|
|
|
|
final ProtocolSchedule protocolSchedule, |
|
|
|
|
final BlockHeader parentHeader, |
|
|
|
|
final EthScheduler ethScheduler) { |
|
|
|
|
super( |
|
|
|
|
miningParameters, |
|
|
|
@ -464,7 +483,6 @@ abstract class AbstractBlockCreatorTest { |
|
|
|
|
transactionPool, |
|
|
|
|
protocolContext, |
|
|
|
|
protocolSchedule, |
|
|
|
|
parentHeader, |
|
|
|
|
ethScheduler); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|