summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDavid Storch <david.storch@10gen.com>2015-08-21 11:17:18 -0400
committerDavid Storch <david.storch@10gen.com>2015-08-24 09:31:13 -0400
commitdd15f9c211f5bc40b6fa8a7cd44350d3aeb87d89 (patch)
treec5dd533a814bf498f3aec4a7b52b1c707af5eb11
parent9140a197d93251d262e4f241e9d3b371ea8f5c2b (diff)
downloadmongo-dd15f9c211f5bc40b6fa8a7cd44350d3aeb87d89.tar.gz
SERVER-18849 only send wire version for find/getMore commands if config server mode is CSRS
A mongod will return a maxWireVersion of 4 to indicate support for the find and getMore commands. In constrast, mongos will only return maxWireVersion of 4 if configured with CSRS, as full find/getMore command support is predicated on config server as a replica set.
-rw-r--r--src/mongo/client/scoped_db_conn_test.cpp2
-rw-r--r--src/mongo/db/wire_version.h6
-rw-r--r--src/mongo/rpc/protocol.cpp5
-rw-r--r--src/mongo/rpc/protocol_test.cpp14
-rw-r--r--src/mongo/s/commands/cluster_is_master_cmd.cpp15
-rw-r--r--src/mongo/s/query/cluster_find.cpp8
6 files changed, 36 insertions, 14 deletions
diff --git a/src/mongo/client/scoped_db_conn_test.cpp b/src/mongo/client/scoped_db_conn_test.cpp
index 59f02f20a1a..b032ed2651c 100644
--- a/src/mongo/client/scoped_db_conn_test.cpp
+++ b/src/mongo/client/scoped_db_conn_test.cpp
@@ -115,7 +115,7 @@ public:
// We need to handle the isMaster received during connection.
if (request->getCommandName() == "isMaster") {
- commandResponse.append("maxWireVersion", WireVersion::RELEASE_3_1_5);
+ commandResponse.append("maxWireVersion", WireVersion::FIND_COMMAND);
commandResponse.append("minWireVersion", WireVersion::RELEASE_2_4_AND_BEFORE);
}
diff --git a/src/mongo/db/wire_version.h b/src/mongo/db/wire_version.h
index 8d4ae40d3d9..9d9e7526922 100644
--- a/src/mongo/db/wire_version.h
+++ b/src/mongo/db/wire_version.h
@@ -56,13 +56,13 @@ enum WireVersion {
// support SCRAM-SHA1, listIndexes, listCollections, new explain
RELEASE_2_7_7 = 3,
- // support find/getMore commands, OP_COMMAND in mongod (not mongos)
- RELEASE_3_1_5 = 4
+ // Support find and getMore commands, as well as OP_COMMAND in mongod (but not mongos).
+ FIND_COMMAND = 4,
};
// Latest version that the server accepts. This should always be at the latest entry in
// WireVersion.
-static const int maxWireVersion = RELEASE_3_1_5;
+static const int maxWireVersion = FIND_COMMAND;
// Minimum version that the server accepts. We should bump this whenever we don't want
// to allow communication with too old agents.
diff --git a/src/mongo/rpc/protocol.cpp b/src/mongo/rpc/protocol.cpp
index fb4683ee4ca..5bff4b05e4f 100644
--- a/src/mongo/rpc/protocol.cpp
+++ b/src/mongo/rpc/protocol.cpp
@@ -146,8 +146,9 @@ StatusWith<ProtocolSet> parseProtocolSetFromIsMasterReply(const BSONObj& isMaste
}
bool supportsWireVersionForOpCommandInMongod(int minWireVersion, int maxWireVersion) {
- return (minWireVersion <= WireVersion::RELEASE_3_1_5) &&
- (maxWireVersion >= WireVersion::RELEASE_3_1_5);
+ // FIND_COMMAND versions support OP_COMMAND (in mongod but not mongos).
+ return (minWireVersion <= WireVersion::FIND_COMMAND) &&
+ (maxWireVersion >= WireVersion::FIND_COMMAND);
}
} // namespace rpc
diff --git a/src/mongo/rpc/protocol_test.cpp b/src/mongo/rpc/protocol_test.cpp
index 0f26cc586b2..ad8437ee280 100644
--- a/src/mongo/rpc/protocol_test.cpp
+++ b/src/mongo/rpc/protocol_test.cpp
@@ -71,18 +71,18 @@ TEST(Protocol, FailedNegotiation) {
TEST(Protocol, parseProtocolSetFromIsMasterReply) {
{
// MongoDB 3.2 (mongod)
- auto mongod32 = BSON("maxWireVersion"
- << static_cast<int>(WireVersion::RELEASE_3_1_5) << "minWireVersion"
- << static_cast<int>(WireVersion::RELEASE_2_4_AND_BEFORE));
+ auto mongod32 =
+ BSON("maxWireVersion" << static_cast<int>(WireVersion::FIND_COMMAND) << "minWireVersion"
+ << static_cast<int>(WireVersion::RELEASE_2_4_AND_BEFORE));
ASSERT_EQ(assertGet(parseProtocolSetFromIsMasterReply(mongod32)), supports::kAll);
}
{
// MongoDB 3.2 (mongos)
- auto mongos32 = BSON("maxWireVersion"
- << static_cast<int>(WireVersion::RELEASE_3_1_5) << "minWireVersion"
- << static_cast<int>(WireVersion::RELEASE_2_4_AND_BEFORE) << "msg"
- << "isdbgrid");
+ auto mongos32 =
+ BSON("maxWireVersion" << static_cast<int>(WireVersion::FIND_COMMAND) << "minWireVersion"
+ << static_cast<int>(WireVersion::RELEASE_2_4_AND_BEFORE) << "msg"
+ << "isdbgrid");
ASSERT_EQ(assertGet(parseProtocolSetFromIsMasterReply(mongos32)), supports::kOpQueryOnly);
}
diff --git a/src/mongo/s/commands/cluster_is_master_cmd.cpp b/src/mongo/s/commands/cluster_is_master_cmd.cpp
index 75dde8f15f9..e3e0dfbd84c 100644
--- a/src/mongo/s/commands/cluster_is_master_cmd.cpp
+++ b/src/mongo/s/commands/cluster_is_master_cmd.cpp
@@ -30,6 +30,8 @@
#include "mongo/db/commands.h"
#include "mongo/db/wire_version.h"
+#include "mongo/s/catalog/forwarding_catalog_manager.h"
+#include "mongo/s/grid.h"
#include "mongo/s/write_ops/batched_command_request.h"
namespace mongo {
@@ -70,9 +72,20 @@ public:
result.appendNumber("maxWriteBatchSize", BatchedCommandRequest::kMaxWriteBatchSize);
result.appendDate("localTime", jsTime());
+ // Mongos can only send the wire version indicating find and getMore commands support if the
+ // config server mode has been upgraded to CSRS.
+ //
+ // TODO: This special case will no longer be required for 3.4.
+ auto catalogManager = grid.catalogManager(txn);
+ int maxVersionToSend = maxWireVersion;
+ if (maxVersionToSend == WireVersion::FIND_COMMAND &&
+ catalogManager->getMode() != CatalogManager::ConfigServerMode::CSRS) {
+ maxVersionToSend = WireVersion::RELEASE_2_7_7;
+ }
+
// Mongos tries to keep exactly the same version range of the server for which
// it is compiled.
- result.append("maxWireVersion", maxWireVersion);
+ result.append("maxWireVersion", maxVersionToSend);
result.append("minWireVersion", minWireVersion);
return true;
diff --git a/src/mongo/s/query/cluster_find.cpp b/src/mongo/s/query/cluster_find.cpp
index 5db9e202564..7441a613124 100644
--- a/src/mongo/s/query/cluster_find.cpp
+++ b/src/mongo/s/query/cluster_find.cpp
@@ -141,6 +141,14 @@ StatusWith<CursorId> runQueryWithoutRetrying(OperationContext* txn,
params.remotes.resize(shards.size());
for (size_t i = 0; i < shards.size(); ++i) {
const auto& shard = shards[i];
+
+ // The find command cannot be used to query config server content with legacy 3-host config
+ // servers, because the new targeting logic only works for config server replica sets.
+ if (shard->isConfig() && shard->getConnString().type() == ConnectionString::SYNC) {
+ return Status(ErrorCodes::CommandNotSupported,
+ "find command not supported without config server as a replica set");
+ }
+
auto targeter = shard->getTargeter();
auto hostAndPort = targeter->findHost(readPref);
if (!hostAndPort.isOK()) {