/** * This test tests that initial sync succeeds when the sync source's oplog rolls over before the * destination node reaches the oplog apply phase. It adds a new secondary to a replicaset and then * pauses the initial sync before it copies the databases but after it starts to fetch and buffer * oplog entries. The primary then fills up its oplog until it rolls over. At that point * initial sync is resumed and we assert that it succeeds and that all of the inserted documents * are there. */ (function() { "use strict"; load("jstests/libs/fail_point_util.js"); load("jstests/replsets/rslib.js"); var name = 'initial_sync_oplog_rollover'; var replSet = new ReplSetTest({ name: name, // This test requires a third node (added later) to be syncing when the oplog rolls // over. Rolling over the oplog requires a majority of nodes to have confirmed and // persisted those writes. Set the syncdelay to one to speed up checkpointing. nodeOptions: {syncdelay: 1}, nodes: [ {rsConfig: {priority: 1}}, {rsConfig: {priority: 0}}, ], }); var oplogSizeOnPrimary = 1; // size in MB replSet.startSet({oplogSize: oplogSizeOnPrimary}); replSet.initiate(); var primary = replSet.getPrimary(); var coll = primary.getDB('test').foo; assert.commandWorked(coll.insert({a: 1})); var firstOplogEntry = getFirstOplogEntry(primary); // Add a secondary node but make it hang before copying databases. var secondary = replSet.add(); secondary.setSlaveOk(); var failPoint = configureFailPoint(secondary, 'initialSyncHangBeforeCopyingDatabases'); replSet.reInitiate(); failPoint.wait(); // Keep inserting large documents until they roll over the oplog. const largeStr = new Array(4 * 1024 * oplogSizeOnPrimary).join('aaaaaaaa'); var i = 0; while (bsonWoCompare(getFirstOplogEntry(primary), firstOplogEntry) === 0) { assert.commandWorked(coll.insert({a: 2, x: i++, long_str: largeStr})); sleep(100); } failPoint.off(); replSet.awaitSecondaryNodes(200 * 1000); assert.eq( i, secondary.getDB('test').foo.count({a: 2}), 'collection successfully synced to secondary'); assert.eq(0, secondary.getDB('local')['temp_oplog_buffer'].find().itcount(), "Oplog buffer was not dropped after initial sync"); replSet.stopSet(); })();