diff options
author | Jack Mulrow <jack.mulrow@mongodb.com> | 2019-12-17 22:55:38 +0000 |
---|---|---|
committer | evergreen <evergreen@mongodb.com> | 2019-12-17 22:55:38 +0000 |
commit | ceeb1a0402e2d0f6f0f55808c16a90e8b30f106c (patch) | |
tree | 85ed681451e9abd58212bc22f640415feaa74701 /src/mongo/db/commands/rwc_defaults_commands.cpp | |
parent | 61241bedf571481a89525ac26d311d3fed4108d6 (diff) | |
download | mongo-ceeb1a0402e2d0f6f0f55808c16a90e8b30f106c.tar.gz |
SERVER-43720 Make RWCDefaults commands persist the defaults
Diffstat (limited to 'src/mongo/db/commands/rwc_defaults_commands.cpp')
-rw-r--r-- | src/mongo/db/commands/rwc_defaults_commands.cpp | 52 |
1 files changed, 47 insertions, 5 deletions
diff --git a/src/mongo/db/commands/rwc_defaults_commands.cpp b/src/mongo/db/commands/rwc_defaults_commands.cpp index b6fb559c9a8..df4a0217d9c 100644 --- a/src/mongo/db/commands/rwc_defaults_commands.cpp +++ b/src/mongo/db/commands/rwc_defaults_commands.cpp @@ -33,14 +33,42 @@ #include "mongo/db/commands.h" #include "mongo/db/commands/rwc_defaults_commands_gen.h" +#include "mongo/db/dbdirectclient.h" +#include "mongo/db/namespace_string.h" +#include "mongo/db/ops/write_ops.h" #include "mongo/db/read_write_concern_defaults.h" #include "mongo/db/repl/read_concern_args.h" #include "mongo/db/repl/replication_coordinator.h" +#include "mongo/db/rw_concern_default_gen.h" +#include "mongo/rpc/get_status_from_command_result.h" #include "mongo/util/log.h" namespace mongo { namespace { +/** + * Replaces the persisted default read/write concern document with a new one representing the given + * defaults. Waits for the write concern on the given operation context to be satisfied before + * returning. + */ +void updatePersistedDefaultRWConcernDocument(OperationContext* opCtx, const RWConcernDefault& rw) { + DBDirectClient client(opCtx); + const auto commandResponse = client.runCommand([&] { + write_ops::Update updateOp(NamespaceString::kConfigSettingsNamespace); + updateOp.setUpdates({[&] { + write_ops::UpdateOpEntry entry; + entry.setQ(BSON("_id" << ReadWriteConcernDefaults::kPersistedDocumentId)); + // Note the _id is propagated from the query into the upserted document. + entry.setU(rw.toBSON()); + entry.setUpsert(true); + return entry; + }()}); + return updateOp.serialize( + BSON(WriteConcernOptions::kWriteConcernField << opCtx->getWriteConcern().toBSON())); + }()); + uassertStatusOK(getStatusFromWriteCommandReply(commandResponse->getCommandReply())); +} + void assertNotStandaloneOrShardServer(OperationContext* opCtx, StringData cmdName) { const auto replCoord = repl::ReplicationCoordinator::get(opCtx); uassert(51300, @@ -78,10 +106,20 @@ public: assertNotStandaloneOrShardServer(opCtx, SetDefaultRWConcern::kCommandName); auto& rwcDefaults = ReadWriteConcernDefaults::get(opCtx->getServiceContext()); - auto newDefaults = rwcDefaults.setConcerns( + auto newDefaults = rwcDefaults.generateNewConcerns( opCtx, request().getDefaultReadConcern(), request().getDefaultWriteConcern()); - log() << "successfully set RWC defaults to " << newDefaults.toBSON(); - return newDefaults; + + // TODO SERVER-44890 Remove this check once this command can only run on a primary node. + if (repl::ReplicationCoordinator::get(opCtx)->getMemberState() == + repl::MemberState::RS_PRIMARY) { + // TODO SERVER-44890: Make this update invalidate the RWC cache through an + // OpObserver so setting the new values below is safe to be best effort. + updatePersistedDefaultRWConcernDocument(opCtx, newDefaults); + } + + // Force a refresh to find the newly set defaults, then return them. + rwcDefaults.refreshIfNecessary(opCtx); + return rwcDefaults.getDefault(opCtx); } private: @@ -121,9 +159,13 @@ public: auto typedRun(OperationContext* opCtx) { assertNotStandaloneOrShardServer(opCtx, GetDefaultRWConcern::kCommandName); - // TODO SERVER-43720 Implement inMemory option. - auto& rwcDefaults = ReadWriteConcernDefaults::get(opCtx->getServiceContext()); + if (request().getInMemory()) { + return rwcDefaults.getDefault(opCtx); + } + + // Force a refresh to find the most recent defaults, then return them. + rwcDefaults.refreshIfNecessary(opCtx); return rwcDefaults.getDefault(opCtx); } |