diff --git a/src/mongo/db/s/resharding/resharding_recipient_service.cpp b/src/mongo/db/s/resharding/resharding_recipient_service.cpp index 2c009ff229b..dfe9272c183 100644 --- a/src/mongo/db/s/resharding/resharding_recipient_service.cpp +++ b/src/mongo/db/s/resharding/resharding_recipient_service.cpp @@ -95,9 +95,11 @@ ExecutorFuture RecipientStateMachine::_awaitAllDonorsPreparedToDonateThenT return ExecutorFuture(**executor, Status::OK()); } - return _allDonorsPreparedToDonate.getFuture().thenRunOn(**executor).then([this]() { - _transitionState(RecipientStateEnum::kCloning); - }); + return _allDonorsPreparedToDonate.getFuture() + .thenRunOn(**executor) + .then([this](Timestamp fetchTimestamp) { + _transitionState(RecipientStateEnum::kCloning, fetchTimestamp); + }); } void RecipientStateMachine::_cloneThenTransitionToApplying() { @@ -147,9 +149,24 @@ void RecipientStateMachine::_renameTemporaryReshardingCollectionThenDeleteLocalS _transitionState(RecipientStateEnum::kDone); } -void RecipientStateMachine::_transitionState(RecipientStateEnum endState) { +void RecipientStateMachine::_fulfillAllDonorsPreparedToDonate(Timestamp fetchTimestamp) { + _allDonorsPreparedToDonate.emplaceValue(fetchTimestamp); +} + +void RecipientStateMachine::_transitionState(RecipientStateEnum endState, + boost::optional fetchTimestamp) { ReshardingRecipientDocument replacementDoc(_recipientDoc); replacementDoc.setState(endState); + if (fetchTimestamp) { + auto& fetchTimestampStruct = replacementDoc.getFetchTimestampStruct(); + + // If the recipient is recovering and already knows the fetchTimestamp, it cannot change + if (fetchTimestampStruct.getFetchTimestamp()) + invariant(fetchTimestampStruct.getFetchTimestamp().get() == fetchTimestamp.get()); + + fetchTimestampStruct.setFetchTimestamp(std::move(fetchTimestamp)); + } + _updateRecipientDocument(std::move(replacementDoc)); } diff --git a/src/mongo/db/s/resharding/resharding_recipient_service.h b/src/mongo/db/s/resharding/resharding_recipient_service.h index 5fd739a1c0e..b3259719183 100644 --- a/src/mongo/db/s/resharding/resharding_recipient_service.h +++ b/src/mongo/db/s/resharding/resharding_recipient_service.h @@ -103,8 +103,11 @@ private: void _renameTemporaryReshardingCollectionThenDeleteLocalState(); + void _fulfillAllDonorsPreparedToDonate(Timestamp); + // Transitions the state on-disk and in-memory to 'endState'. - void _transitionState(RecipientStateEnum endState); + void _transitionState(RecipientStateEnum endState, + boost::optional fetchTimestamp = boost::none); // Transitions the state on-disk and in-memory to kError. void _transitionStateToError(const Status& status); @@ -118,7 +121,7 @@ private: // Each promise below corresponds to a state on the recipient state machine. They are listed in // ascending order, such that the first promise below will be the first promise fulfilled. - SharedPromise _allDonorsPreparedToDonate; + SharedPromise _allDonorsPreparedToDonate; SharedPromise _allDonorsMirroring;