summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/mongo/client/remote_command_targeter.h7
-rw-r--r--src/mongo/client/remote_command_targeter_factory_mock.cpp4
-rw-r--r--src/mongo/client/remote_command_targeter_mock.cpp2
-rw-r--r--src/mongo/client/remote_command_targeter_mock.h5
-rw-r--r--src/mongo/client/remote_command_targeter_rs.cpp6
-rw-r--r--src/mongo/client/remote_command_targeter_rs.h2
-rw-r--r--src/mongo/client/remote_command_targeter_standalone.cpp4
-rw-r--r--src/mongo/client/remote_command_targeter_standalone.h2
-rw-r--r--src/mongo/s/client/shard_registry.cpp4
9 files changed, 35 insertions, 1 deletions
diff --git a/src/mongo/client/remote_command_targeter.h b/src/mongo/client/remote_command_targeter.h
index c345f8b2c9f..8cf912ba98b 100644
--- a/src/mongo/client/remote_command_targeter.h
+++ b/src/mongo/client/remote_command_targeter.h
@@ -66,6 +66,13 @@ public:
*/
virtual StatusWith<HostAndPort> findHost(const ReadPreferenceSetting& readPref) = 0;
+ /**
+ * Reports to the targeter that a NotMaster response was received when communicating with
+ * "host', and so it should update its bookkeeping to avoid giving out the host again on a
+ * subsequent request for the primary.
+ */
+ virtual void markHostNotMaster(const HostAndPort& host) = 0;
+
protected:
RemoteCommandTargeter() = default;
};
diff --git a/src/mongo/client/remote_command_targeter_factory_mock.cpp b/src/mongo/client/remote_command_targeter_factory_mock.cpp
index 1ed1c11cbc6..8029b5b4c6c 100644
--- a/src/mongo/client/remote_command_targeter_factory_mock.cpp
+++ b/src/mongo/client/remote_command_targeter_factory_mock.cpp
@@ -51,6 +51,10 @@ public:
return _mock->findHost(readPref);
}
+ void markHostNotMaster(const HostAndPort& host) override {
+ _mock->markHostNotMaster(host);
+ }
+
private:
const std::shared_ptr<RemoteCommandTargeter> _mock;
};
diff --git a/src/mongo/client/remote_command_targeter_mock.cpp b/src/mongo/client/remote_command_targeter_mock.cpp
index d09bdc36e8f..38ade7dd09b 100644
--- a/src/mongo/client/remote_command_targeter_mock.cpp
+++ b/src/mongo/client/remote_command_targeter_mock.cpp
@@ -55,6 +55,8 @@ StatusWith<HostAndPort> RemoteCommandTargeterMock::findHost(const ReadPreference
return _findHostReturnValue;
}
+void RemoteCommandTargeterMock::markHostNotMaster(const HostAndPort& host) {}
+
void RemoteCommandTargeterMock::setConnectionStringReturnValue(const ConnectionString returnValue) {
_connectionStringReturnValue = std::move(returnValue);
}
diff --git a/src/mongo/client/remote_command_targeter_mock.h b/src/mongo/client/remote_command_targeter_mock.h
index 443d7cb68f8..3293300ce5d 100644
--- a/src/mongo/client/remote_command_targeter_mock.h
+++ b/src/mongo/client/remote_command_targeter_mock.h
@@ -56,6 +56,11 @@ public:
StatusWith<HostAndPort> findHost(const ReadPreferenceSetting& readPref) override;
/**
+ * No-op for the mock.
+ */
+ void markHostNotMaster(const HostAndPort& host) override;
+
+ /**
* Sets the return value for the next call to connectionString.
*/
void setConnectionStringReturnValue(const ConnectionString returnValue);
diff --git a/src/mongo/client/remote_command_targeter_rs.cpp b/src/mongo/client/remote_command_targeter_rs.cpp
index 2870215dfc2..cbaaee553ef 100644
--- a/src/mongo/client/remote_command_targeter_rs.cpp
+++ b/src/mongo/client/remote_command_targeter_rs.cpp
@@ -78,4 +78,10 @@ StatusWith<HostAndPort> RemoteCommandTargeterRS::findHost(const ReadPreferenceSe
return hostAndPort;
}
+void RemoteCommandTargeterRS::markHostNotMaster(const HostAndPort& host) {
+ invariant(_rsMonitor);
+
+ _rsMonitor->failedHost(host);
+}
+
} // namespace mongo
diff --git a/src/mongo/client/remote_command_targeter_rs.h b/src/mongo/client/remote_command_targeter_rs.h
index 8e849fbf9aa..00ece641ef8 100644
--- a/src/mongo/client/remote_command_targeter_rs.h
+++ b/src/mongo/client/remote_command_targeter_rs.h
@@ -54,6 +54,8 @@ public:
StatusWith<HostAndPort> findHost(const ReadPreferenceSetting& readPref) override;
+ void markHostNotMaster(const HostAndPort& host) override;
+
private:
// Name of the replica set which this targeter maintains
const std::string _rsName;
diff --git a/src/mongo/client/remote_command_targeter_standalone.cpp b/src/mongo/client/remote_command_targeter_standalone.cpp
index e1f7eac46ef..cfb06e38a18 100644
--- a/src/mongo/client/remote_command_targeter_standalone.cpp
+++ b/src/mongo/client/remote_command_targeter_standalone.cpp
@@ -47,4 +47,8 @@ StatusWith<HostAndPort> RemoteCommandTargeterStandalone::findHost(
return _hostAndPort;
}
+void RemoteCommandTargeterStandalone::markHostNotMaster(const HostAndPort& host) {
+ dassert(host == _hostAndPort);
+}
+
} // namespace mongo
diff --git a/src/mongo/client/remote_command_targeter_standalone.h b/src/mongo/client/remote_command_targeter_standalone.h
index a7bbad1429e..79b29a93556 100644
--- a/src/mongo/client/remote_command_targeter_standalone.h
+++ b/src/mongo/client/remote_command_targeter_standalone.h
@@ -45,6 +45,8 @@ public:
StatusWith<HostAndPort> findHost(const ReadPreferenceSetting& readPref) override;
+ void markHostNotMaster(const HostAndPort& host) override;
+
private:
const HostAndPort _hostAndPort;
};
diff --git a/src/mongo/s/client/shard_registry.cpp b/src/mongo/s/client/shard_registry.cpp
index bf7a9e74b15..5b6b497a8e7 100644
--- a/src/mongo/s/client/shard_registry.cpp
+++ b/src/mongo/s/client/shard_registry.cpp
@@ -366,7 +366,9 @@ StatusWith<BSONObj> ShardRegistry::runCommandWithNotMasterRetries(const ShardId&
}
Status commandStatus = getStatusFromCommandResult(response.getValue());
- if (ErrorCodes::NotMaster == commandStatus) {
+ if (ErrorCodes::NotMaster == commandStatus ||
+ ErrorCodes::NotMasterNoSlaveOkCode == commandStatus) {
+ targeter->markHostNotMaster(target.getValue());
if (i == kNotMasterNumRetries - 1) {
// If we're out of retries don't bother sleeping, just return.
return commandStatus;