summaryrefslogtreecommitdiff
path: root/src/mongo/db/repl/election_winner_declarer_test.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/mongo/db/repl/election_winner_declarer_test.cpp')
-rw-r--r--src/mongo/db/repl/election_winner_declarer_test.cpp324
1 files changed, 156 insertions, 168 deletions
diff --git a/src/mongo/db/repl/election_winner_declarer_test.cpp b/src/mongo/db/repl/election_winner_declarer_test.cpp
index dfb278f69a1..04177148453 100644
--- a/src/mongo/db/repl/election_winner_declarer_test.cpp
+++ b/src/mongo/db/repl/election_winner_declarer_test.cpp
@@ -44,190 +44,178 @@ namespace mongo {
namespace repl {
namespace {
- using executor::NetworkInterfaceMock;
- using unittest::assertGet;
+using executor::NetworkInterfaceMock;
+using unittest::assertGet;
- bool stringContains(const std::string &haystack, const std::string& needle) {
- return haystack.find(needle) != std::string::npos;
+bool stringContains(const std::string& haystack, const std::string& needle) {
+ return haystack.find(needle) != std::string::npos;
+}
+
+
+class ElectionWinnerDeclarerTest : public mongo::unittest::Test {
+public:
+ virtual void setUp() {
+ std::string setName = "rs0";
+ long long winnerId = 0;
+ long long term = 1;
+ std::vector<HostAndPort> hosts = {
+ HostAndPort("host0"), HostAndPort("host1"), HostAndPort("host2")};
+
+ _declarer.reset(new ElectionWinnerDeclarer::Algorithm(setName, winnerId, term, hosts));
+ }
+
+ virtual void tearDown() {
+ _declarer.reset(NULL);
+ }
+
+protected:
+ int64_t countLogLinesContaining(const std::string& needle) {
+ return std::count_if(getCapturedLogMessages().begin(),
+ getCapturedLogMessages().end(),
+ stdx::bind(stringContains, stdx::placeholders::_1, needle));
}
+ bool hasReceivedSufficientResponses() {
+ return _declarer->hasReceivedSufficientResponses();
+ }
- class ElectionWinnerDeclarerTest : public mongo::unittest::Test {
- public:
- virtual void setUp() {
- std::string setName = "rs0";
- long long winnerId = 0;
- long long term = 1;
- std::vector<HostAndPort> hosts = {HostAndPort("host0"),
- HostAndPort("host1"),
- HostAndPort("host2")};
-
- _declarer.reset(new ElectionWinnerDeclarer::Algorithm(setName,
- winnerId,
- term,
- hosts));
- }
-
- virtual void tearDown() {
- _declarer.reset(NULL);
- }
-
- protected:
- int64_t countLogLinesContaining(const std::string& needle) {
- return std::count_if(getCapturedLogMessages().begin(),
- getCapturedLogMessages().end(),
- stdx::bind(stringContains,
- stdx::placeholders::_1,
- needle));
- }
-
- bool hasReceivedSufficientResponses() {
- return _declarer->hasReceivedSufficientResponses();
- }
-
- Status getStatus() {
- return _declarer->getStatus();
- }
-
- void processResponse(const RemoteCommandRequest& request, const ResponseStatus& response) {
- _declarer->processResponse(request, response);
- }
-
- RemoteCommandRequest requestFrom(std::string hostname) {
- return RemoteCommandRequest(HostAndPort(hostname),
- "", // fields do not matter in ElectionWinnerDeclarer
- BSONObj(),
- Milliseconds(0));
- }
-
- ResponseStatus badResponseStatus() {
- return ResponseStatus(ErrorCodes::NodeNotFound, "not on my watch");
- }
-
- ResponseStatus staleTermResponse() {
- return ResponseStatus(NetworkInterfaceMock::Response(BSON("ok" << 0
- << "code" << ErrorCodes::BadValue
- << "errmsg"
- << "term has already passed"
- << "term" << 3),
- Milliseconds(10)));
- }
-
- ResponseStatus alreadyAnotherPrimaryResponse() {
- return ResponseStatus(NetworkInterfaceMock::Response(BSON("ok" << 0
- << "code" << ErrorCodes::BadValue
- << "errmsg"
- << "term already has a primary"
- << "term" << 1),
- Milliseconds(10)));
- }
-
- ResponseStatus differentConfigVersionResponse() {
- return ResponseStatus(NetworkInterfaceMock::Response(BSON("ok" << 0
- << "code" << ErrorCodes::BadValue
- << "errmsg"
- << "config version does not match"
- << "term" << 1),
- Milliseconds(10)));
- }
-
- ResponseStatus differentSetNameResponse() {
- return ResponseStatus(NetworkInterfaceMock::Response(BSON("ok" << 0
- << "code" << ErrorCodes::BadValue
- << "errmsg"
- << "replSet name does not match"
- << "term" << 1),
- Milliseconds(10)));
- }
-
- ResponseStatus goodResponse() {
- return ResponseStatus(NetworkInterfaceMock::Response(BSON("ok" << 1
- << "term" << 1),
- Milliseconds(10)));
- }
-
- private:
- unique_ptr<ElectionWinnerDeclarer::Algorithm> _declarer;
-
- };
-
- TEST_F(ElectionWinnerDeclarerTest, FinishWithOnlyGoodResponses) {
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host0"), goodResponse());
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host1"), goodResponse());
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host2"), goodResponse());
- ASSERT_TRUE(hasReceivedSufficientResponses());
- ASSERT_OK(getStatus());
+ Status getStatus() {
+ return _declarer->getStatus();
}
- TEST_F(ElectionWinnerDeclarerTest, FailedDueToStaleTerm) {
- startCapturingLogMessages();
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host0"), goodResponse());
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host1"), staleTermResponse());
- ASSERT_TRUE(hasReceivedSufficientResponses());
- ASSERT_EQUALS(1, countLogLinesContaining("Got error response from host1"));
- stopCapturingLogMessages();
- ASSERT_EQUALS(getStatus().reason(), "term has already passed");
+ void processResponse(const RemoteCommandRequest& request, const ResponseStatus& response) {
+ _declarer->processResponse(request, response);
}
- TEST_F(ElectionWinnerDeclarerTest, FailedDueToAnotherPrimary) {
- startCapturingLogMessages();
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host0"), goodResponse());
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host1"), alreadyAnotherPrimaryResponse());
- ASSERT_TRUE(hasReceivedSufficientResponses());
- ASSERT_EQUALS(1, countLogLinesContaining("Got error response from host1"));
- stopCapturingLogMessages();
- ASSERT_EQUALS(getStatus().reason(), "term already has a primary");
+ RemoteCommandRequest requestFrom(std::string hostname) {
+ return RemoteCommandRequest(HostAndPort(hostname),
+ "", // fields do not matter in ElectionWinnerDeclarer
+ BSONObj(),
+ Milliseconds(0));
}
- TEST_F(ElectionWinnerDeclarerTest, FailedDueToDifferentSetName) {
- startCapturingLogMessages();
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host0"), goodResponse());
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host1"), differentSetNameResponse());
- ASSERT_TRUE(hasReceivedSufficientResponses());
- ASSERT_EQUALS(1, countLogLinesContaining("Got error response from host1"));
- stopCapturingLogMessages();
- ASSERT_EQUALS(getStatus().reason(), "replSet name does not match");
+ ResponseStatus badResponseStatus() {
+ return ResponseStatus(ErrorCodes::NodeNotFound, "not on my watch");
}
- TEST_F(ElectionWinnerDeclarerTest, FinishWithOnlyGoodResponsesAndMissingNode) {
- startCapturingLogMessages();
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host0"), goodResponse());
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host1"), badResponseStatus());
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host2"), goodResponse());
- ASSERT_TRUE(hasReceivedSufficientResponses());
- ASSERT_EQUALS(1, countLogLinesContaining("Got failed response from host1"));
- stopCapturingLogMessages();
- ASSERT_OK(getStatus());
+ ResponseStatus staleTermResponse() {
+ return ResponseStatus(NetworkInterfaceMock::Response(
+ BSON("ok" << 0 << "code" << ErrorCodes::BadValue << "errmsg"
+ << "term has already passed"
+ << "term" << 3),
+ Milliseconds(10)));
}
- TEST_F(ElectionWinnerDeclarerTest, FinishWithOnlyMissingResponses) {
- startCapturingLogMessages();
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host0"), badResponseStatus());
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host1"), badResponseStatus());
- ASSERT_FALSE(hasReceivedSufficientResponses());
- processResponse(requestFrom("host2"), badResponseStatus());
- ASSERT_TRUE(hasReceivedSufficientResponses());
- ASSERT_EQUALS(1, countLogLinesContaining("Got failed response from host0"));
- ASSERT_EQUALS(1, countLogLinesContaining("Got failed response from host1"));
- ASSERT_EQUALS(1, countLogLinesContaining("Got failed response from host2"));
- stopCapturingLogMessages();
- ASSERT_OK(getStatus());
+ ResponseStatus alreadyAnotherPrimaryResponse() {
+ return ResponseStatus(NetworkInterfaceMock::Response(
+ BSON("ok" << 0 << "code" << ErrorCodes::BadValue << "errmsg"
+ << "term already has a primary"
+ << "term" << 1),
+ Milliseconds(10)));
}
+ ResponseStatus differentConfigVersionResponse() {
+ return ResponseStatus(NetworkInterfaceMock::Response(
+ BSON("ok" << 0 << "code" << ErrorCodes::BadValue << "errmsg"
+ << "config version does not match"
+ << "term" << 1),
+ Milliseconds(10)));
+ }
+
+ ResponseStatus differentSetNameResponse() {
+ return ResponseStatus(NetworkInterfaceMock::Response(
+ BSON("ok" << 0 << "code" << ErrorCodes::BadValue << "errmsg"
+ << "replSet name does not match"
+ << "term" << 1),
+ Milliseconds(10)));
+ }
+
+ ResponseStatus goodResponse() {
+ return ResponseStatus(
+ NetworkInterfaceMock::Response(BSON("ok" << 1 << "term" << 1), Milliseconds(10)));
+ }
+
+private:
+ unique_ptr<ElectionWinnerDeclarer::Algorithm> _declarer;
+};
+
+TEST_F(ElectionWinnerDeclarerTest, FinishWithOnlyGoodResponses) {
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host0"), goodResponse());
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host1"), goodResponse());
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host2"), goodResponse());
+ ASSERT_TRUE(hasReceivedSufficientResponses());
+ ASSERT_OK(getStatus());
+}
+
+TEST_F(ElectionWinnerDeclarerTest, FailedDueToStaleTerm) {
+ startCapturingLogMessages();
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host0"), goodResponse());
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host1"), staleTermResponse());
+ ASSERT_TRUE(hasReceivedSufficientResponses());
+ ASSERT_EQUALS(1, countLogLinesContaining("Got error response from host1"));
+ stopCapturingLogMessages();
+ ASSERT_EQUALS(getStatus().reason(), "term has already passed");
+}
+
+TEST_F(ElectionWinnerDeclarerTest, FailedDueToAnotherPrimary) {
+ startCapturingLogMessages();
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host0"), goodResponse());
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host1"), alreadyAnotherPrimaryResponse());
+ ASSERT_TRUE(hasReceivedSufficientResponses());
+ ASSERT_EQUALS(1, countLogLinesContaining("Got error response from host1"));
+ stopCapturingLogMessages();
+ ASSERT_EQUALS(getStatus().reason(), "term already has a primary");
+}
+
+TEST_F(ElectionWinnerDeclarerTest, FailedDueToDifferentSetName) {
+ startCapturingLogMessages();
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host0"), goodResponse());
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host1"), differentSetNameResponse());
+ ASSERT_TRUE(hasReceivedSufficientResponses());
+ ASSERT_EQUALS(1, countLogLinesContaining("Got error response from host1"));
+ stopCapturingLogMessages();
+ ASSERT_EQUALS(getStatus().reason(), "replSet name does not match");
+}
+
+TEST_F(ElectionWinnerDeclarerTest, FinishWithOnlyGoodResponsesAndMissingNode) {
+ startCapturingLogMessages();
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host0"), goodResponse());
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host1"), badResponseStatus());
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host2"), goodResponse());
+ ASSERT_TRUE(hasReceivedSufficientResponses());
+ ASSERT_EQUALS(1, countLogLinesContaining("Got failed response from host1"));
+ stopCapturingLogMessages();
+ ASSERT_OK(getStatus());
+}
+
+TEST_F(ElectionWinnerDeclarerTest, FinishWithOnlyMissingResponses) {
+ startCapturingLogMessages();
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host0"), badResponseStatus());
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host1"), badResponseStatus());
+ ASSERT_FALSE(hasReceivedSufficientResponses());
+ processResponse(requestFrom("host2"), badResponseStatus());
+ ASSERT_TRUE(hasReceivedSufficientResponses());
+ ASSERT_EQUALS(1, countLogLinesContaining("Got failed response from host0"));
+ ASSERT_EQUALS(1, countLogLinesContaining("Got failed response from host1"));
+ ASSERT_EQUALS(1, countLogLinesContaining("Got failed response from host2"));
+ stopCapturingLogMessages();
+ ASSERT_OK(getStatus());
+}
+
} // namespace
} // namespace repl
} // namespace mongo