diff options
author | Louis Williams <louis.williams@mongodb.com> | 2020-04-10 10:02:34 -0400 |
---|---|---|
committer | Evergreen Agent <no-reply@evergreen.mongodb.com> | 2020-04-10 14:16:22 +0000 |
commit | 3d929ed533a72446353b18b5d60770aed33b58f1 (patch) | |
tree | 09bd3562511aef88eb6aa1ef3b6c45b8d73c16e9 /src/mongo/db/commands/drop_indexes.cpp | |
parent | 76d4548a751a56c8faf1887114685b540203a650 (diff) | |
download | mongo-3d929ed533a72446353b18b5d60770aed33b58f1.tar.gz |
SERVER-46560 Make abort index build deterministic
This redesigns user index build abort to have the following behavior:
- Take a collection X lock to stop the index build from making progress
- If we are no longer primary, return an error
- Check whether we can abort the index build (i.e. it is not already committing
or aborting)
- Delete the index catalog entry and write the abortIndexBuild oplog entry in a WUOW
- Interrupt the index builder thread
- Wait for the thread to exit
- Release locks
Diffstat (limited to 'src/mongo/db/commands/drop_indexes.cpp')
-rw-r--r-- | src/mongo/db/commands/drop_indexes.cpp | 45 |
1 files changed, 21 insertions, 24 deletions
diff --git a/src/mongo/db/commands/drop_indexes.cpp b/src/mongo/db/commands/drop_indexes.cpp index e924becf9f4..38266a3cf48 100644 --- a/src/mongo/db/commands/drop_indexes.cpp +++ b/src/mongo/db/commands/drop_indexes.cpp @@ -213,22 +213,20 @@ public: StatusWith<std::vector<BSONObj>> swIndexesToRebuild(ErrorCodes::UnknownError, "Uninitialized"); - // The 'indexer' can throw, so ensure build cleanup occurs. - ON_BLOCK_EXIT([&] { - indexer->cleanUpAfterBuild(opCtx, collection, MultiIndexBlock::kNoopOnCleanUpFn); + writeConflictRetry(opCtx, "dropAllIndexes", toReIndexNss.ns(), [&] { + WriteUnitOfWork wunit(opCtx); + collection->getIndexCatalog()->dropAllIndexes(opCtx, true); + + swIndexesToRebuild = + indexer->init(opCtx, collection, all, MultiIndexBlock::kNoopOnInitFn); + uassertStatusOK(swIndexesToRebuild.getStatus()); + wunit.commit(); }); - { - writeConflictRetry(opCtx, "dropAllIndexes", toReIndexNss.ns(), [&] { - WriteUnitOfWork wunit(opCtx); - collection->getIndexCatalog()->dropAllIndexes(opCtx, true); - - swIndexesToRebuild = - indexer->init(opCtx, collection, all, MultiIndexBlock::kNoopOnInitFn); - uassertStatusOK(swIndexesToRebuild.getStatus()); - wunit.commit(); - }); - } + // The 'indexer' can throw, so ensure build cleanup occurs. + auto abortOnExit = makeGuard([&] { + indexer->abortIndexBuild(opCtx, collection, MultiIndexBlock::kNoopOnCleanUpFn); + }); if (MONGO_unlikely(reIndexCrashAfterDrop.shouldFail())) { LOGV2(20458, "exiting because 'reIndexCrashAfterDrop' fail point was set"); @@ -241,16 +239,15 @@ public: uassertStatusOK(indexer->checkConstraints(opCtx)); - { - writeConflictRetry(opCtx, "commitReIndex", toReIndexNss.ns(), [&] { - WriteUnitOfWork wunit(opCtx); - uassertStatusOK(indexer->commit(opCtx, - collection, - MultiIndexBlock::kNoopOnCreateEachFn, - MultiIndexBlock::kNoopOnCommitFn)); - wunit.commit(); - }); - } + writeConflictRetry(opCtx, "commitReIndex", toReIndexNss.ns(), [&] { + WriteUnitOfWork wunit(opCtx); + uassertStatusOK(indexer->commit(opCtx, + collection, + MultiIndexBlock::kNoopOnCreateEachFn, + MultiIndexBlock::kNoopOnCommitFn)); + wunit.commit(); + }); + abortOnExit.dismiss(); // Do not allow majority reads from this collection until all original indexes are visible. // This was also done when dropAllIndexes() committed, but we need to ensure that no one |