From 58b207fea9bc12ba06fcd5dd487b072bbc06c68b Mon Sep 17 00:00:00 2001 From: Richard Bair Date: Mon, 11 Sep 2023 17:18:47 -0700 Subject: [PATCH] Use the DualState from handleRound instead of from initialization for the DualStateUpdateFacility (#8516) Signed-off-by: Richard Bair --- .../main/java/com/hedera/node/app/Hedera.java | 35 +++------ .../node/app/HederaInjectionComponent.java | 5 +- .../handle/DualStateUpdateFacility.java | 22 ++++-- .../app/workflows/handle/HandleWorkflow.java | 12 ++-- .../app/components/IngestComponentTest.java | 2 - .../handle/DualStateUpdateFacilityTest.java | 14 ++-- .../workflows/handle/HandleWorkflowTest.java | 72 ++++++++++--------- 7 files changed, 80 insertions(+), 82 deletions(-) diff --git a/hedera-node/hedera-app/src/main/java/com/hedera/node/app/Hedera.java b/hedera-node/hedera-app/src/main/java/com/hedera/node/app/Hedera.java index 12cff1febe1f..3fb213cb3d8a 100644 --- a/hedera-node/hedera-app/src/main/java/com/hedera/node/app/Hedera.java +++ b/hedera-node/hedera-app/src/main/java/com/hedera/node/app/Hedera.java @@ -47,7 +47,6 @@ import com.hedera.node.app.service.util.impl.UtilServiceImpl; import com.hedera.node.app.services.ServicesRegistryImpl; import com.hedera.node.app.spi.HapiUtils; -import com.hedera.node.app.spi.Service; import com.hedera.node.app.state.HederaState; import com.hedera.node.app.state.merkle.MerkleHederaState; import com.hedera.node.app.state.merkle.MerkleSchemaRegistry; @@ -55,7 +54,6 @@ import com.hedera.node.app.throttle.ThrottleManager; import com.hedera.node.app.version.HederaSoftwareVersion; import com.hedera.node.app.workflows.dispatcher.ReadableStoreFactory; -import com.hedera.node.app.workflows.handle.DualStateUpdateFacility; import com.hedera.node.app.workflows.handle.SystemFileUpdateFacility; import com.hedera.node.config.ConfigProvider; import com.hedera.node.config.Utils; @@ -123,17 +121,6 @@ public final class Hedera implements SwirldMain { private static final Logger logger = LogManager.getLogger(Hedera.class); // FUTURE: This should come from configuration, not be hardcoded. public static final int MAX_SIGNED_TXN_SIZE = 6144; - - /** - * Defines the registration information for a service. - * - * @param name The name of the service. - * @param service The service implementation itself. - * @param registry The {@link MerkleSchemaRegistry} with which the service registers its schemas. - */ - private record ServiceRegistration( - @NonNull String name, @NonNull Service service, @NonNull MerkleSchemaRegistry registry) {} - /** The registry of all known services */ private final ServicesRegistryImpl servicesRegistry; /** The current version of THIS software */ @@ -342,8 +329,8 @@ private void onStateInitialized( // here. This is intentional so as to avoid forgetting to handle a new trigger. try { switch (trigger) { - case GENESIS -> genesis(state, dualState); - case RESTART -> restart(state, dualState, deserializedVersion); + case GENESIS -> genesis(state); + case RESTART -> restart(state, deserializedVersion); case RECONNECT -> reconnect(); // We exited from this method early if we were recovering from an event stream. case EVENT_STREAM_RECOVERY -> throw new RuntimeException("Should never be reached"); @@ -584,7 +571,7 @@ private void onPreHandle(@NonNull final Event event, @NonNull final HederaState private void onHandleConsensusRound( @NonNull final Round round, @NonNull final SwirldDualState dualState, @NonNull final HederaState state) { daggerApp.workingStateAccessor().setHederaState(state); - daggerApp.handleWorkflow().handleRound(state, round); + daggerApp.handleWorkflow().handleRound(state, dualState, round); } /*================================================================================================================== @@ -612,7 +599,7 @@ public void shutdownGrpcServer() { =================================================================================================================*/ /** Implements the code flow for initializing the state of a new Hedera node with NO SAVED STATE. */ - private void genesis(@NonNull final MerkleHederaState state, @NonNull final SwirldDualState dualState) { + private void genesis(@NonNull final MerkleHederaState state) { logger.debug("Genesis Initialization"); // Initialize the configuration from disk (genesis case). We must do this BEFORE we run migration, because @@ -634,7 +621,7 @@ private void genesis(@NonNull final MerkleHederaState state, @NonNull final Swir onMigrate(state, null); // Now that we have the state created, we are ready to create the dependency graph with Dagger - initializeDagger(state, dualState, GENESIS); + initializeDagger(state, GENESIS); // And now that the entire dependency graph has been initialized, and we have config, and all migration has // been completed, we are prepared to initialize in-memory data structures. These specifically are loaded @@ -652,9 +639,7 @@ private void genesis(@NonNull final MerkleHederaState state, @NonNull final Swir /** Initialize flow for when a node has been restarted. This means it was started from a saved state. */ private void restart( - @NonNull final MerkleHederaState state, - @NonNull final SwirldDualState dualState, - @Nullable final HederaSoftwareVersion deserializedVersion) { + @NonNull final MerkleHederaState state, @Nullable final HederaSoftwareVersion deserializedVersion) { logger.debug("Restart Initialization"); // The deserialized version can ONLY be null if we are in genesis, otherwise something is wrong with the state @@ -681,7 +666,7 @@ private void restart( onMigrate(state, deserializedVersion); // Now that we have the state created, we are ready to create the dependency graph with Dagger - initializeDagger(state, dualState, RESTART); + initializeDagger(state, RESTART); // And now that the entire dependency graph has been initialized, and we have config, and all migration has // been completed, we are prepared to initialize in-memory data structures. These specifically are loaded @@ -708,10 +693,7 @@ private void reconnect() { * =================================================================================================================*/ - private void initializeDagger( - @NonNull final MerkleHederaState state, - @NonNull final SwirldDualState dualState, - @NonNull final InitTrigger trigger) { + private void initializeDagger(@NonNull final MerkleHederaState state, @NonNull final InitTrigger trigger) { logger.debug("Initializing dagger"); final var selfId = platform.getSelfId(); if (daggerApp == null) { @@ -726,7 +708,6 @@ private void initializeDagger( .exchangeRateManager(exchangeRateManager) .systemFileUpdateFacility( new SystemFileUpdateFacility(configProvider, throttleManager, exchangeRateManager)) - .dualStateUpdateFacility(new DualStateUpdateFacility(dualState)) .self(SelfNodeInfoImpl.of(nodeAddress, version)) .initialHash(initialHash) .platform(platform) diff --git a/hedera-node/hedera-app/src/main/java/com/hedera/node/app/HederaInjectionComponent.java b/hedera-node/hedera-app/src/main/java/com/hedera/node/app/HederaInjectionComponent.java index abbaced3693a..4c9b4fd53f04 100644 --- a/hedera-node/hedera-app/src/main/java/com/hedera/node/app/HederaInjectionComponent.java +++ b/hedera-node/hedera-app/src/main/java/com/hedera/node/app/HederaInjectionComponent.java @@ -118,6 +118,8 @@ public interface HederaInjectionComponent { ThrottleManager throttleManager(); + DualStateUpdateFacility dualStateUpdateFacility(); + @Component.Builder interface Builder { @@ -148,9 +150,6 @@ interface Builder { @BindsInstance Builder systemFileUpdateFacility(SystemFileUpdateFacility systemFileUpdateFacility); - @BindsInstance - Builder dualStateUpdateFacility(DualStateUpdateFacility dualStateUpdateFacility); - @BindsInstance Builder exchangeRateManager(ExchangeRateManager exchangeRateManager); diff --git a/hedera-node/hedera-app/src/main/java/com/hedera/node/app/workflows/handle/DualStateUpdateFacility.java b/hedera-node/hedera-app/src/main/java/com/hedera/node/app/workflows/handle/DualStateUpdateFacility.java index e3c93b29e41e..b4560cfbcfae 100644 --- a/hedera-node/hedera-app/src/main/java/com/hedera/node/app/workflows/handle/DualStateUpdateFacility.java +++ b/hedera-node/hedera-app/src/main/java/com/hedera/node/app/workflows/handle/DualStateUpdateFacility.java @@ -32,20 +32,24 @@ import com.swirlds.common.system.DualState; import edu.umd.cs.findbugs.annotations.NonNull; import java.time.Instant; +import javax.inject.Inject; +import javax.inject.Singleton; +import org.apache.logging.log4j.LogManager; +import org.apache.logging.log4j.Logger; /** * Simple facility that notifies interested parties when the freeze state is updated. */ +@Singleton public class DualStateUpdateFacility { - private final DualState dualState; + private static final Logger logger = LogManager.getLogger(DualStateUpdateFacility.class); /** * Creates a new instance of this class. - * - * @param dualState the configuration provider */ - public DualStateUpdateFacility(@NonNull final DualState dualState) { - this.dualState = requireNonNull(dualState, "configProvider must not be null"); + @Inject + public DualStateUpdateFacility() { + // For dagger } /** @@ -55,13 +59,17 @@ public DualStateUpdateFacility(@NonNull final DualState dualState) { * @param state the current state * @param txBody the transaction body */ - public void handleTxBody(@NonNull final HederaState state, @NonNull final TransactionBody txBody) { + public void handleTxBody( + @NonNull final HederaState state, + @NonNull final DualState dualState, + @NonNull final TransactionBody txBody) { requireNonNull(state, "state must not be null"); requireNonNull(txBody, "txBody must not be null"); if (txBody.hasFreeze()) { final FreezeType freezeType = txBody.freezeOrThrow().freezeType(); if (freezeType == FREEZE_UPGRADE || freezeType == FREEZE_ONLY) { + logger.info("Transaction freeze of type {} detected", freezeType); // copy freeze state to dual state final ReadableStates states = state.createReadableStates(FreezeService.NAME); final ReadableSingletonState freezeTime = @@ -69,8 +77,10 @@ public void handleTxBody(@NonNull final HederaState state, @NonNull final Transa requireNonNull(freezeTime.get()); final Instant freezeTimeInstant = Instant.ofEpochSecond( freezeTime.get().seconds(), freezeTime.get().nanos()); + logger.info("Freeze time will be {}", freezeTimeInstant); dualState.setFreezeTime(freezeTimeInstant); } else if (freezeType == FREEZE_ABORT) { + logger.info("Aborting freeze"); // copy freeze state (which is null) to dual state // we just set dual state to null dualState.setFreezeTime(null); diff --git a/hedera-node/hedera-app/src/main/java/com/hedera/node/app/workflows/handle/HandleWorkflow.java b/hedera-node/hedera-app/src/main/java/com/hedera/node/app/workflows/handle/HandleWorkflow.java index 576eed52bea2..b6c93895e13a 100644 --- a/hedera-node/hedera-app/src/main/java/com/hedera/node/app/workflows/handle/HandleWorkflow.java +++ b/hedera-node/hedera-app/src/main/java/com/hedera/node/app/workflows/handle/HandleWorkflow.java @@ -74,6 +74,7 @@ import com.hedera.node.config.data.HederaConfig; import com.hedera.pbj.runtime.io.buffer.Bytes; import com.swirlds.common.system.Round; +import com.swirlds.common.system.SwirldDualState; import com.swirlds.common.system.events.ConsensusEvent; import com.swirlds.common.system.transaction.ConsensusTransaction; import com.swirlds.config.api.Configuration; @@ -162,7 +163,8 @@ public HandleWorkflow( * @param state the writable {@link HederaState} that this round will work on * @param round the next {@link Round} that needs to be processed */ - public void handleRound(@NonNull final HederaState state, @NonNull final Round round) { + public void handleRound( + @NonNull final HederaState state, @NonNull final SwirldDualState dualState, @NonNull final Round round) { // Keep track of whether any user transactions were handled. If so, then we will need to close the round // with the block record manager. final var userTransactionsHandled = new AtomicBoolean(false); @@ -187,7 +189,7 @@ public void handleRound(@NonNull final HederaState state, @NonNull final Round r // skip system transactions if (!platformTxn.isSystem()) { userTransactionsHandled.set(true); - handlePlatformTransaction(state, event, creator, platformTxn); + handlePlatformTransaction(state, dualState, event, creator, platformTxn); } } catch (final Exception e) { logger.fatal( @@ -209,6 +211,7 @@ public void handleRound(@NonNull final HederaState state, @NonNull final Round r private void handlePlatformTransaction( @NonNull final HederaState state, + @NonNull final SwirldDualState dualState, @NonNull final ConsensusEvent platformEvent, @NonNull final NodeInfo creator, @NonNull final ConsensusTransaction platformTxn) { @@ -217,7 +220,7 @@ private void handlePlatformTransaction( final Instant consensusNow = platformTxn.getConsensusTimestamp(); // handle user transaction - handleUserTransaction(consensusNow, state, platformEvent, creator, platformTxn); + handleUserTransaction(consensusNow, state, dualState, platformEvent, creator, platformTxn); // TODO: handle long scheduled transactions @@ -228,6 +231,7 @@ private void handlePlatformTransaction( private void handleUserTransaction( @NonNull final Instant consensusNow, @NonNull final HederaState state, + @NonNull final SwirldDualState dualState, @NonNull final ConsensusEvent platformEvent, @NonNull final NodeInfo creator, @NonNull final ConsensusTransaction platformTxn) { @@ -346,7 +350,7 @@ private void handleUserTransaction( systemFileUpdateFacility.handleTxBody(stack, txBody); // Notify if dual state was updated - dualStateUpdateFacility.handleTxBody(stack, txBody); + dualStateUpdateFacility.handleTxBody(stack, dualState, txBody); } catch (final HandleException e) { rollback(e.getStatus(), stack, recordListBuilder); diff --git a/hedera-node/hedera-app/src/test/java/com/hedera/node/app/components/IngestComponentTest.java b/hedera-node/hedera-app/src/test/java/com/hedera/node/app/components/IngestComponentTest.java index dbaabbc6af7e..7d91c184e355 100644 --- a/hedera-node/hedera-app/src/test/java/com/hedera/node/app/components/IngestComponentTest.java +++ b/hedera-node/hedera-app/src/test/java/com/hedera/node/app/components/IngestComponentTest.java @@ -34,7 +34,6 @@ import com.hedera.node.app.state.recordcache.RecordCacheService; import com.hedera.node.app.throttle.ThrottleManager; import com.hedera.node.app.version.HederaSoftwareVersion; -import com.hedera.node.app.workflows.handle.DualStateUpdateFacility; import com.hedera.node.app.workflows.handle.SystemFileUpdateFacility; import com.hedera.node.config.testfixtures.HederaTestConfigBuilder; import com.swirlds.common.context.PlatformContext; @@ -101,7 +100,6 @@ void setUp() { .configuration(configProvider) .systemFileUpdateFacility( new SystemFileUpdateFacility(configProvider, throttleManager, exchangeRateManager)) - .dualStateUpdateFacility(new DualStateUpdateFacility(dualState)) .throttleManager(throttleManager) .self(selfNodeInfo) .initialHash(new Hash()) diff --git a/hedera-node/hedera-app/src/test/java/com/hedera/node/app/workflows/handle/DualStateUpdateFacilityTest.java b/hedera-node/hedera-app/src/test/java/com/hedera/node/app/workflows/handle/DualStateUpdateFacilityTest.java index b7169342c1eb..0048300030c0 100644 --- a/hedera-node/hedera-app/src/test/java/com/hedera/node/app/workflows/handle/DualStateUpdateFacilityTest.java +++ b/hedera-node/hedera-app/src/test/java/com/hedera/node/app/workflows/handle/DualStateUpdateFacilityTest.java @@ -72,7 +72,7 @@ void setUp() { .when(dualState) .setFreezeTime(any(Instant.class)); - subject = new DualStateUpdateFacility(dualState); + subject = new DualStateUpdateFacility(); } @SuppressWarnings("ConstantConditions") @@ -82,9 +82,10 @@ void testMethodsWithInvalidArguments() { final var txBody = simpleCryptoTransfer().body(); // then - assertThatThrownBy(() -> new DualStateUpdateFacility(null)).isInstanceOf(NullPointerException.class); - assertThatThrownBy(() -> subject.handleTxBody(null, txBody)).isInstanceOf(NullPointerException.class); - assertThatThrownBy(() -> subject.handleTxBody(state, null)).isInstanceOf(NullPointerException.class); + assertThatThrownBy(() -> subject.handleTxBody(null, dualState, txBody)) + .isInstanceOf(NullPointerException.class); + assertThatThrownBy(() -> subject.handleTxBody(state, null, txBody)).isInstanceOf(NullPointerException.class); + assertThatThrownBy(() -> subject.handleTxBody(state, dualState, null)).isInstanceOf(NullPointerException.class); } @Test @@ -95,7 +96,8 @@ void testCryptoTransferShouldBeNoOp() { .build(); // then - Assertions.assertThatCode(() -> subject.handleTxBody(state, txBody)).doesNotThrowAnyException(); + Assertions.assertThatCode(() -> subject.handleTxBody(state, dualState, txBody)) + .doesNotThrowAnyException(); } @Test @@ -107,7 +109,7 @@ void testFreezeUpgrade() { .freeze(FreezeTransactionBody.newBuilder().freezeType(FREEZE_UPGRADE)); // when - subject.handleTxBody(state, txBody.build()); + subject.handleTxBody(state, dualState, txBody.build()); // then assertEquals(freezeTime.seconds(), dualState.getFreezeTime().getEpochSecond()); diff --git a/hedera-node/hedera-app/src/test/java/com/hedera/node/app/workflows/handle/HandleWorkflowTest.java b/hedera-node/hedera-app/src/test/java/com/hedera/node/app/workflows/handle/HandleWorkflowTest.java index 8dc78abea7db..2bf7bf3dd54a 100644 --- a/hedera-node/hedera-app/src/test/java/com/hedera/node/app/workflows/handle/HandleWorkflowTest.java +++ b/hedera-node/hedera-app/src/test/java/com/hedera/node/app/workflows/handle/HandleWorkflowTest.java @@ -73,6 +73,7 @@ import com.hedera.node.config.testfixtures.HederaTestConfigBuilder; import com.hedera.pbj.runtime.io.buffer.Bytes; import com.swirlds.common.system.Round; +import com.swirlds.common.system.SwirldDualState; import com.swirlds.common.system.events.ConsensusEvent; import com.swirlds.common.system.transaction.ConsensusTransaction; import com.swirlds.common.system.transaction.internal.SwirldTransaction; @@ -192,6 +193,9 @@ private static PreHandleResult createPreHandleResult(@NonNull Status status, @No @Mock(strictness = LENIENT) private Authorizer authorizer; + @Mock + private SwirldDualState dualState; + private HandleWorkflow workflow; @BeforeEach @@ -635,7 +639,7 @@ void testPlatformTxnIsSkipped() { when(platformTxn.isSystem()).thenReturn(true); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then assertThat(accountsState.isModified()).isFalse(); @@ -648,14 +652,14 @@ void testPlatformTxnIsSkipped() { @DisplayName("Successful execution of simple case") void testHappyPath() { // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var alice = aliasesState.get(new ProtoBytes(Bytes.wrap(ALICE_ALIAS))); assertThat(alice).isEqualTo(ALICE.account().accountId()); // TODO: Check that record was created verify(systemFileUpdateFacility).handleTxBody(any(), any()); - verify(dualStateUpdateFacility).handleTxBody(any(), any()); + verify(dualStateUpdateFacility).handleTxBody(any(), any(), any()); } @Nested @@ -675,7 +679,7 @@ void testPreHandleNotExecuted() { when(platformTxn.getMetadata()).thenReturn(null); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then verify(preHandleWorkflow).preHandleTransaction(any(), any(), any(), eq(platformTxn)); @@ -688,7 +692,7 @@ void testPreHandleFailure() { when(platformTxn.getMetadata()).thenReturn(PRE_HANDLE_FAILURE_RESULT); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then verify(preHandleWorkflow).preHandleTransaction(any(), any(), any(), eq(platformTxn)); @@ -701,7 +705,7 @@ void testUnknownFailure() { when(platformTxn.getMetadata()).thenReturn(PreHandleResult.unknownFailure()); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then verify(preHandleWorkflow).preHandleTransaction(any(), any(), any(), eq(platformTxn)); @@ -726,7 +730,7 @@ void testConfigurationChanged() { when(platformTxn.getMetadata()).thenReturn(preHandleResult); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then verify(preHandleWorkflow).preHandleTransaction(any(), any(), any(), eq(platformTxn)); @@ -739,7 +743,7 @@ void testPreHandleSuccess() { when(platformTxn.getMetadata()).thenReturn(null); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var alice = aliasesState.get(new ProtoBytes(Bytes.wrap(ALICE_ALIAS))); @@ -756,7 +760,7 @@ void testPreHandleCausesDueDilligenceError() { .thenReturn(DUE_DILIGENCE_RESULT); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then assertThat(aliasesState.isModified()).isFalse(); @@ -772,7 +776,7 @@ void testPreHandleCausesPreHandleFailure() { .thenReturn(DUE_DILIGENCE_RESULT); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then assertThat(aliasesState.isModified()).isFalse(); @@ -787,7 +791,7 @@ void testPreHandleCausesUnknownFailure() { .thenReturn(PreHandleResult.unknownFailure()); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then assertThat(accountsState.isModified()).isFalse(); @@ -802,7 +806,7 @@ void testPreHandleWithDueDiligenceFailure() { // given when(platformTxn.getMetadata()).thenReturn(DUE_DILIGENCE_RESULT); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then assertThat(aliasesState.isModified()).isFalse(); @@ -850,7 +854,7 @@ void testRequiredExistingKeyWithPassingSignature() throws PreCheckException, Tim .expand(eq(Set.of(bobsKey)), any(), any()); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var argCapture = ArgumentCaptor.forClass(HandleContext.class); @@ -904,7 +908,7 @@ void testRequiredExistingKeyWithFailingSignature() throws PreCheckException { .expand(eq(Set.of(bobsKey)), any(), any()); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then verify(dispatcher, never()).dispatchHandle(any()); @@ -939,7 +943,7 @@ void testRequiredNewKeyWithPassingSignature() throws PreCheckException, TimeoutE .thenReturn(verificationResults); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var argCapture = ArgumentCaptor.forClass(HandleContext.class); @@ -984,7 +988,7 @@ void testRequiredNewKeyWithFailingSignature() throws PreCheckException { .thenReturn(verificationResults); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then verify(dispatcher, never()).dispatchHandle(any()); @@ -1027,7 +1031,7 @@ void testOptionalExistingKeyWithPassingSignature() throws PreCheckException, Tim .expand(eq(Set.of(bobsKey)), any(), any()); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var argCapture = ArgumentCaptor.forClass(HandleContext.class); @@ -1081,7 +1085,7 @@ void testOptionalExistingKeyWithFailingSignature() throws PreCheckException, Tim .expand(eq(Set.of(bobsKey)), any(), any()); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var argCapture = ArgumentCaptor.forClass(HandleContext.class); @@ -1127,7 +1131,7 @@ void testOptionalNewKeyWithPassingSignature() throws PreCheckException, TimeoutE .thenReturn(verificationResults); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var argCapture = ArgumentCaptor.forClass(HandleContext.class); @@ -1173,7 +1177,7 @@ void testOptionalNewKeyWithFailingSignature() throws PreCheckException, TimeoutE .thenReturn(verificationResults); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var argCapture = ArgumentCaptor.forClass(HandleContext.class); @@ -1244,7 +1248,7 @@ void testComplexCase() throws PreCheckException, TimeoutException { .thenReturn(verificationResults); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var argCapture = ArgumentCaptor.forClass(HandleContext.class); @@ -1284,7 +1288,7 @@ void testDuplicateFromOtherNode() { .thenReturn(DuplicateCheckResult.OTHER_NODE); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then assertThat(accountsState.get(ALICE.accountID()).tinybarBalance()).isLessThan(DEFAULT_FEES.totalFee()); @@ -1299,7 +1303,7 @@ void testDuplicateFromSameNode() { .thenReturn(DuplicateCheckResult.SAME_NODE); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then assertThat(accountsState.get(ALICE.accountID()).tinybarBalance()).isEqualTo(DEFAULT_FEES.totalFee()); @@ -1316,7 +1320,7 @@ void testExpiredTransactionFails(final ResponseCodeEnum responseCode) throws Pre .checkTimeBox(OK_RESULT.txInfo().txBody(), CONSENSUS_NOW); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var block = getRecordFromStream(); @@ -1335,7 +1339,7 @@ void testInvalidPayerAccountFails(final ResponseCodeEnum responseCode) throws Pr .getPayerAccount(any(), eq(ALICE.accountID())); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var block = getRecordFromStream(); @@ -1360,7 +1364,7 @@ void testInsolventPayerAccountFails(final ResponseCodeEnum responseCode) throws .checkSolvency(eq(OK_RESULT.txInfo()), any(), eq(DEFAULT_FEES.totalWithoutServiceFee())); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var block = getRecordFromStream(); @@ -1377,7 +1381,7 @@ void testNonAuthorizedAccountFails() { .thenReturn(false); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var block = getRecordFromStream(); @@ -1397,7 +1401,7 @@ void testNonAuthorizedAccountFailsForPrivilegedTxn() { .thenReturn(SystemPrivilege.UNAUTHORIZED); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var block = getRecordFromStream(); @@ -1417,7 +1421,7 @@ void testImpermissibleTransactionFails() { .thenReturn(SystemPrivilege.IMPERMISSIBLE); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var block = getRecordFromStream(); @@ -1438,7 +1442,7 @@ void testAuthorizedAccountFailsForPrivilegedTxn(final SystemPrivilege privilege) .thenReturn(privilege); // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then final var block = getRecordFromStream(); @@ -1456,7 +1460,7 @@ void testHandleException() { doThrow(new HandleException(ResponseCodeEnum.INVALID_SIGNATURE)) .when(dispatcher) .dispatchHandle(any()); - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then assertThat(aliasesState.isModified()).isFalse(); @@ -1468,7 +1472,7 @@ void testHandleException() { void testUnknownFailure() { // when doThrow(new ArrayIndexOutOfBoundsException()).when(dispatcher).dispatchHandle(any()); - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then assertThat(accountsState.isModified()).isFalse(); @@ -1487,7 +1491,7 @@ final class RecordManagerInteractionTest { @Test void testSimpleRun() { // when - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); // then verify(blockRecordManager).startUserTransaction(CONSENSUS_NOW, state); @@ -1498,7 +1502,7 @@ void testSimpleRun() { @Test void testConsensusTimeHookCalled() { - workflow.handleRound(state, round); + workflow.handleRound(state, dualState, round); verify(stakingPeriodTimeHook).process(any()); }