diff options
author | Sergi Mateo Bellido <sergi.mateo-bellido@mongodb.com> | 2020-12-02 12:59:01 +0000 |
---|---|---|
committer | Evergreen Agent <no-reply@evergreen.mongodb.com> | 2020-12-10 10:14:41 +0000 |
commit | 4e5de13940486910b57c1feb57e58687f778b855 (patch) | |
tree | 6597549ba1d16a10b6e4f849d1ddcfdcfe006e23 /src/mongo/db | |
parent | f2f7e1d867dca21c66bd2ff699812f63b5f82b87 (diff) | |
download | mongo-4e5de13940486910b57c1feb57e58687f778b855.tar.gz |
SERVER-53093 Add timestamp to ChunkVersion
PART 1: Adding the timestamp to the ChunkVersion class and to the places
where we construct a ChunkVersion
Diffstat (limited to 'src/mongo/db')
-rw-r--r-- | src/mongo/db/s/config/configsvr_reshard_collection_cmd.cpp | 12 | ||||
-rw-r--r-- | src/mongo/db/s/config/initial_split_policy.cpp | 29 | ||||
-rw-r--r-- | src/mongo/db/s/config/sharding_catalog_manager_chunk_operations.cpp | 31 | ||||
-rw-r--r-- | src/mongo/db/s/set_shard_version_command.cpp | 2 | ||||
-rw-r--r-- | src/mongo/db/s/shard_metadata_util.cpp | 7 | ||||
-rw-r--r-- | src/mongo/db/s/shard_metadata_util.h | 3 | ||||
-rw-r--r-- | src/mongo/db/s/shard_server_catalog_cache_loader.cpp | 20 | ||||
-rw-r--r-- | src/mongo/db/s/type_shard_collection.cpp | 4 |
8 files changed, 79 insertions, 29 deletions
diff --git a/src/mongo/db/s/config/configsvr_reshard_collection_cmd.cpp b/src/mongo/db/s/config/configsvr_reshard_collection_cmd.cpp index 3373da60a87..d22f559b15b 100644 --- a/src/mongo/db/s/config/configsvr_reshard_collection_cmd.cpp +++ b/src/mongo/db/s/config/configsvr_reshard_collection_cmd.cpp @@ -39,10 +39,12 @@ #include "mongo/db/s/resharding/resharding_coordinator_service.h" #include "mongo/db/s/resharding/resharding_server_parameters_gen.h" #include "mongo/db/s/resharding_util.h" +#include "mongo/db/vector_clock.h" #include "mongo/logv2/log.h" #include "mongo/s/catalog/type_tags.h" #include "mongo/s/grid.h" #include "mongo/s/request_types/reshard_collection_gen.h" +#include "mongo/s/sharded_collections_ddl_parameters_gen.h" namespace mongo { namespace { @@ -127,7 +129,15 @@ public: int numInitialChunks; std::set<ShardId> recipientShardIds; std::vector<ChunkType> initialChunks; - ChunkVersion version(1, 0, OID::gen()); + + boost::optional<Timestamp> timestamp; + if (feature_flags::gShardingFullDDLSupport.isEnabled( + serverGlobalParams.featureCompatibility)) { + const auto now = VectorClock::get(opCtx)->getTime(); + timestamp = now.clusterTime().asTimestamp(); + } + + ChunkVersion version(1, 0, OID::gen(), timestamp); auto tempReshardingNss = constructTemporaryReshardingNss( nss.db(), getCollectionUUIDFromChunkManger(nss, cm)); diff --git a/src/mongo/db/s/config/initial_split_policy.cpp b/src/mongo/db/s/config/initial_split_policy.cpp index c7efc2019f7..56cf3f008ba 100644 --- a/src/mongo/db/s/config/initial_split_policy.cpp +++ b/src/mongo/db/s/config/initial_split_policy.cpp @@ -40,6 +40,7 @@ #include "mongo/s/catalog/type_shard.h" #include "mongo/s/grid.h" #include "mongo/s/shard_util.h" +#include "mongo/s/sharded_collections_ddl_parameters_gen.h" namespace mongo { namespace { @@ -110,7 +111,12 @@ InitialSplitPolicy::ShardCollectionConfig createChunks(const ShardKeyPattern& sh const std::vector<ShardId>& allShardIds, std::vector<BSONObj>& finalSplitPoints, const Timestamp& validAfter) { - ChunkVersion version(1, 0, OID::gen()); + boost::optional<Timestamp> timestamp; + if (feature_flags::gShardingFullDDLSupport.isEnabled(serverGlobalParams.featureCompatibility)) { + timestamp = validAfter; + } + + ChunkVersion version(1, 0, OID::gen(), timestamp); const auto& keyPattern(shardKeyPattern.getKeyPattern()); std::vector<ChunkType> chunks; @@ -277,9 +283,17 @@ std::unique_ptr<InitialSplitPolicy> InitialSplitPolicy::calculateOptimizationStr InitialSplitPolicy::ShardCollectionConfig SingleChunkOnPrimarySplitPolicy::createFirstChunks( OperationContext* opCtx, const ShardKeyPattern& shardKeyPattern, SplitPolicyParams params) { ShardCollectionConfig initialChunks; - ChunkVersion version(1, 0, OID::gen()); - const auto& keyPattern = shardKeyPattern.getKeyPattern(); + const auto currentTime = VectorClock::get(opCtx)->getTime(); + const auto clusterTime = currentTime.clusterTime().asTimestamp(); + + boost::optional<Timestamp> timestamp; + if (feature_flags::gShardingFullDDLSupport.isEnabled(serverGlobalParams.featureCompatibility)) { + timestamp = clusterTime; + } + + ChunkVersion version(1, 0, OID::gen(), timestamp); + const auto& keyPattern = shardKeyPattern.getKeyPattern(); appendChunk(params.nss, params.collectionUUID, keyPattern.globalMin(), @@ -288,7 +302,7 @@ InitialSplitPolicy::ShardCollectionConfig SingleChunkOnPrimarySplitPolicy::creat currentTime.clusterTime().asTimestamp(), params.primaryShardId, &initialChunks.chunks); - initialChunks.creationTime = currentTime.clusterTime().asTimestamp(); + initialChunks.creationTime = clusterTime; return initialChunks; } @@ -373,7 +387,12 @@ InitialSplitPolicy::ShardCollectionConfig AbstractTagsBasedSplitPolicy::createFi return shardIds[indx++ % shardIds.size()]; }; - ChunkVersion version(1, 0, OID::gen()); + boost::optional<Timestamp> timestamp; + if (feature_flags::gShardingFullDDLSupport.isEnabled(serverGlobalParams.featureCompatibility)) { + timestamp = validAfter; + } + + ChunkVersion version(1, 0, OID::gen(), timestamp); auto lastChunkMax = keyPattern.globalMin(); std::vector<ChunkType> chunks; for (const auto& tag : _tags) { diff --git a/src/mongo/db/s/config/sharding_catalog_manager_chunk_operations.cpp b/src/mongo/db/s/config/sharding_catalog_manager_chunk_operations.cpp index caaf535a1e6..0011b1478e3 100644 --- a/src/mongo/db/s/config/sharding_catalog_manager_chunk_operations.cpp +++ b/src/mongo/db/s/config/sharding_catalog_manager_chunk_operations.cpp @@ -378,7 +378,8 @@ BSONObj getShardAndCollectionVersion(OperationContext* opCtx, if (swDonorShardVersion.getStatus().code() == 50577) { // The query to find 'nss' chunks belonging to the donor shard didn't return any chunks, // meaning the last chunk for fromShard was donated. Gracefully handle the error. - shardVersion = ChunkVersion(0, 0, collectionVersion.epoch()); + shardVersion = + ChunkVersion(0, 0, collectionVersion.epoch(), collectionVersion.getTimestamp()); } else { // Bubble up any other error uassertStatusOK(swDonorShardVersion); @@ -404,8 +405,10 @@ void bumpMajorVersionOneChunkPerShard(OperationContext* opCtx, TxnNumber txnNumber, const std::vector<ShardId>& shardIds) { auto curCollectionVersion = uassertStatusOK(getCollectionVersion(opCtx, nss)); - ChunkVersion targetChunkVersion( - curCollectionVersion.majorVersion() + 1, 0, curCollectionVersion.epoch()); + ChunkVersion targetChunkVersion(curCollectionVersion.majorVersion() + 1, + 0, + curCollectionVersion.epoch(), + curCollectionVersion.getTimestamp()); for (const auto& shardId : shardIds) { BSONObjBuilder updateBuilder; @@ -930,8 +933,10 @@ StatusWith<BSONObj> ShardingCatalogManager::commitChunkMigration( newMigratedChunk.setCollectionUUID(collectionUUID); } newMigratedChunk.setShard(toShard); - newMigratedChunk.setVersion(ChunkVersion( - currentCollectionVersion.majorVersion() + 1, 0, currentCollectionVersion.epoch())); + newMigratedChunk.setVersion(ChunkVersion(currentCollectionVersion.majorVersion() + 1, + 0, + currentCollectionVersion.epoch(), + currentCollectionVersion.getTimestamp())); // Copy the complete history. auto newHistory = origChunk.getValue().getHistory(); @@ -983,8 +988,10 @@ StatusWith<BSONObj> ShardingCatalogManager::commitChunkMigration( newControlChunk = origControlChunk.getValue(); newControlChunk->setName(origControlChunk.getValue().getName()); - newControlChunk->setVersion(ChunkVersion( - currentCollectionVersion.majorVersion() + 1, 1, currentCollectionVersion.epoch())); + newControlChunk->setVersion(ChunkVersion(currentCollectionVersion.majorVersion() + 1, + 1, + currentCollectionVersion.epoch(), + currentCollectionVersion.getTimestamp())); } auto command = makeCommitChunkTransactionCommand( @@ -1111,8 +1118,10 @@ void ShardingCatalogManager::clearJumboFlag(OperationContext* opCtx, << chunk.toString() << ").", currentCollectionVersion.epoch() == collectionEpoch); - ChunkVersion newVersion( - currentCollectionVersion.majorVersion() + 1, 0, currentCollectionVersion.epoch()); + ChunkVersion newVersion(currentCollectionVersion.majorVersion() + 1, + 0, + currentCollectionVersion.epoch(), + currentCollectionVersion.getTimestamp()); BSONObj chunkQuery(BSON(ChunkType::ns(nss.ns()) << ChunkType::epoch(collectionEpoch) << ChunkType::min(chunk.getMin()) @@ -1228,8 +1237,8 @@ void ShardingCatalogManager::ensureChunkVersionIsGreaterThan(OperationContext* o // Generate a new version for the chunk by incrementing the collectionVersion's major version. auto newChunk = currentChunk; - newChunk.setVersion( - ChunkVersion(highestChunk.getVersion().majorVersion() + 1, 0, version.epoch())); + newChunk.setVersion(ChunkVersion( + highestChunk.getVersion().majorVersion() + 1, 0, version.epoch(), version.getTimestamp())); // Update the chunk, if it still exists, to have the bumped version. earlyReturnBeforeDoingWriteGuard.dismiss(); diff --git a/src/mongo/db/s/set_shard_version_command.cpp b/src/mongo/db/s/set_shard_version_command.cpp index c1ab9fbc146..997df91264b 100644 --- a/src/mongo/db/s/set_shard_version_command.cpp +++ b/src/mongo/db/s/set_shard_version_command.cpp @@ -323,7 +323,7 @@ public: result.appendBool("reloadConfig", true); // Zero-version also needed to trigger full mongos reload, sadly // TODO: Make this saner, and less impactful (full reload on last chunk is bad) - ChunkVersion(0, 0, OID()).appendLegacyWithField(&result, "version"); + ChunkVersion::UNSHARDED().appendLegacyWithField(&result, "version"); // For debugging requestedVersion.appendLegacyWithField(&result, "origVersion"); } else { diff --git a/src/mongo/db/s/shard_metadata_util.cpp b/src/mongo/db/s/shard_metadata_util.cpp index baf9582d42f..5aca5172c98 100644 --- a/src/mongo/db/s/shard_metadata_util.cpp +++ b/src/mongo/db/s/shard_metadata_util.cpp @@ -134,7 +134,7 @@ StatusWith<RefreshState> getPersistedRefreshFlags(OperationContext* opCtx, entry.getRefreshing() ? *entry.getRefreshing() : true, entry.getLastRefreshedCollectionVersion() ? *entry.getLastRefreshedCollectionVersion() - : ChunkVersion(0, 0, entry.getEpoch())}; + : ChunkVersion(0, 0, entry.getEpoch(), entry.getTimestamp())}; } StatusWith<ShardCollectionType> readShardCollectionsEntry(OperationContext* opCtx, @@ -292,7 +292,8 @@ StatusWith<std::vector<ChunkType>> readShardChunks(OperationContext* opCtx, const BSONObj& query, const BSONObj& sort, boost::optional<long long> limit, - const OID& epoch) { + const OID& epoch, + const boost::optional<Timestamp>& timestamp) { try { Query fullQuery(query); fullQuery.sort(sort); @@ -311,7 +312,7 @@ StatusWith<std::vector<ChunkType>> readShardChunks(OperationContext* opCtx, std::vector<ChunkType> chunks; while (cursor->more()) { BSONObj document = cursor->nextSafe().getOwned(); - auto statusWithChunk = ChunkType::fromShardBSON(document, epoch); + auto statusWithChunk = ChunkType::fromShardBSON(document, epoch, timestamp); if (!statusWithChunk.isOK()) { return statusWithChunk.getStatus().withContext( str::stream() << "Failed to parse chunk '" << document.toString() << "'"); diff --git a/src/mongo/db/s/shard_metadata_util.h b/src/mongo/db/s/shard_metadata_util.h index 376b29eca56..45bee780dd0 100644 --- a/src/mongo/db/s/shard_metadata_util.h +++ b/src/mongo/db/s/shard_metadata_util.h @@ -175,7 +175,8 @@ StatusWith<std::vector<ChunkType>> readShardChunks(OperationContext* opCtx, const BSONObj& query, const BSONObj& sort, boost::optional<long long> limit, - const OID& epoch); + const OID& epoch, + const boost::optional<Timestamp>& timestamp); /** * Takes a vector of 'chunks' and updates the shard's chunks collection for 'nss'. Any chunk diff --git a/src/mongo/db/s/shard_server_catalog_cache_loader.cpp b/src/mongo/db/s/shard_server_catalog_cache_loader.cpp index d5a81a24128..05945aecc74 100644 --- a/src/mongo/db/s/shard_server_catalog_cache_loader.cpp +++ b/src/mongo/db/s/shard_server_catalog_cache_loader.cpp @@ -194,8 +194,13 @@ ChunkVersion getPersistedMaxChunkVersion(OperationContext* opCtx, const Namespac return ChunkVersion::UNSHARDED(); } - auto statusWithChunk = shardmetadatautil::readShardChunks( - opCtx, nss, BSONObj(), BSON(ChunkType::lastmod() << -1), 1LL, cachedCollection.getEpoch()); + auto statusWithChunk = shardmetadatautil::readShardChunks(opCtx, + nss, + BSONObj(), + BSON(ChunkType::lastmod() << -1), + 1LL, + cachedCollection.getEpoch(), + cachedCollection.getTimestamp()); uassertStatusOKWithContext( statusWithChunk, str::stream() << "Failed to read highest version persisted chunk for collection '" @@ -224,12 +229,17 @@ CollectionAndChangedChunks getPersistedMetadataSinceVersion(OperationContext* op // If the persisted epoch doesn't match what the CatalogCache requested, read everything. ChunkVersion startingVersion = (shardCollectionEntry.getEpoch() == version.epoch()) ? version - : ChunkVersion(0, 0, shardCollectionEntry.getEpoch()); + : ChunkVersion(0, 0, shardCollectionEntry.getEpoch(), shardCollectionEntry.getTimestamp()); QueryAndSort diff = createShardChunkDiffQuery(startingVersion); - auto changedChunks = uassertStatusOK( - readShardChunks(opCtx, nss, diff.query, diff.sort, boost::none, startingVersion.epoch())); + auto changedChunks = uassertStatusOK(readShardChunks(opCtx, + nss, + diff.query, + diff.sort, + boost::none, + startingVersion.epoch(), + startingVersion.getTimestamp())); return CollectionAndChangedChunks{shardCollectionEntry.getEpoch(), shardCollectionEntry.getTimestamp(), diff --git a/src/mongo/db/s/type_shard_collection.cpp b/src/mongo/db/s/type_shard_collection.cpp index 74d40fcc940..fa6e8d68ea0 100644 --- a/src/mongo/db/s/type_shard_collection.cpp +++ b/src/mongo/db/s/type_shard_collection.cpp @@ -61,8 +61,8 @@ ShardCollectionType::ShardCollectionType(const BSONObj& obj) { // it exists, into a chunk version. if (getLastRefreshedCollectionVersion()) { ChunkVersion version = *getLastRefreshedCollectionVersion(); - setLastRefreshedCollectionVersion( - ChunkVersion(version.majorVersion(), version.minorVersion(), getEpoch())); + setLastRefreshedCollectionVersion(ChunkVersion( + version.majorVersion(), version.minorVersion(), getEpoch(), getTimestamp())); } } |