diff options
author | Lingzhi Deng <lingzhi.deng@mongodb.com> | 2020-04-06 17:58:35 -0400 |
---|---|---|
committer | Evergreen Agent <no-reply@evergreen.mongodb.com> | 2020-04-07 17:54:52 +0000 |
commit | a488e5a035a4824067a1b61005177f87539d614a (patch) | |
tree | 5899cbbcf7eebd45f7cf5e58eda8e828726d74e3 | |
parent | f8d1d969e6b3fe28503dc5c250bb6eba38cbd7a3 (diff) | |
download | mongo-a488e5a035a4824067a1b61005177f87539d614a.tar.gz |
SERVER-47179: Fix crash when requesting serverStatus oplog before the oplog collection is created
(cherry picked from commit d34b92cb31a147cf29fe676081978f3ff7acd79f)
-rw-r--r-- | jstests/replsets/optime.js | 6 | ||||
-rw-r--r-- | src/mongo/db/repl/replication_info.cpp | 32 |
2 files changed, 24 insertions, 14 deletions
diff --git a/jstests/replsets/optime.js b/jstests/replsets/optime.js index 3fd9aff2139..6d44c198216 100644 --- a/jstests/replsets/optime.js +++ b/jstests/replsets/optime.js @@ -59,7 +59,11 @@ function optimesAndWallTimesAreEqual(replTest, isPersistent) { var replTest = new ReplSetTest( {name: "replStatus", nodes: 3, oplogSize: 1, waitForKeys: true, nodeOptions: {syncdelay: 1}}); -replTest.startSet(); +const nodes = replTest.startSet(); + +// Tests that serverStatus oplog returns an error if the oplog collection doesn't exist. +assert.commandFailedWithCode(nodes[0].getDB('admin').serverStatus({oplog: true}), 17347); + replTest.initiate(); var master = replTest.getPrimary(); replTest.awaitReplication(); diff --git a/src/mongo/db/repl/replication_info.cpp b/src/mongo/db/repl/replication_info.cpp index bf33e4334d7..eddaf899f6f 100644 --- a/src/mongo/db/repl/replication_info.cpp +++ b/src/mongo/db/repl/replication_info.cpp @@ -269,21 +269,27 @@ public: // TODO(siyuan) Output term of OpTime result.append("latestOptime", replCoord->getMyLastAppliedOpTime().getTimestamp()); - AutoGetCollection oplog(opCtx, NamespaceString::kRsOplogNamespace, MODE_IS); - auto earliestOplogTimestampFetch = - oplog.getCollection()->getRecordStore()->getEarliestOplogTimestamp(opCtx); - Timestamp earliestOplogTimestamp; - if (earliestOplogTimestampFetch.isOK()) { - earliestOplogTimestamp = earliestOplogTimestampFetch.getValue(); - } else { + auto earliestOplogTimestampFetch = [&] { + AutoGetCollection oplog(opCtx, NamespaceString::kRsOplogNamespace, MODE_IS); + if (!oplog.getCollection()) { + return StatusWith<Timestamp>(ErrorCodes::NamespaceNotFound, "oplog doesn't exist"); + } + return oplog.getCollection()->getRecordStore()->getEarliestOplogTimestamp(opCtx); + }(); + + if (earliestOplogTimestampFetch.getStatus() == ErrorCodes::OplogOperationUnsupported) { + // Falling back to use getSingleton if the storage engine does not support + // getEarliestOplogTimestamp. BSONObj o; - uassert( - 17347, - "Problem reading earliest entry from oplog", - Helpers::getSingleton(opCtx, NamespaceString::kRsOplogNamespace.ns().c_str(), o)); - earliestOplogTimestamp = o["ts"].timestamp(); + if (Helpers::getSingleton(opCtx, NamespaceString::kRsOplogNamespace.ns().c_str(), o)) { + earliestOplogTimestampFetch = o["ts"].timestamp(); + } } - result.append("earliestOptime", earliestOplogTimestamp); + + uassert( + 17347, "Problem reading earliest entry from oplog", earliestOplogTimestampFetch.isOK()); + result.append("earliestOptime", earliestOplogTimestampFetch.getValue()); + return result.obj(); } } oplogInfoServerStatus; |