summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRyan Timmons <ryan.timmons@10gen.com>2020-01-28 17:13:42 -0500
committerEvergreen Agent <no-reply@evergreen.mongodb.com>2020-04-02 01:34:46 +0000
commitb804b718aa7479f46ce7aa2536f558ab9526281b (patch)
tree43559039591482a2cd1e7e57e35ffcc0aa3a19b5
parentc51dbb8eb4d81e6b70c542065eb66b9e36082d38 (diff)
downloadmongo-b804b718aa7479f46ce7aa2536f558ab9526281b.tar.gz
SERVER-32903 Ambiguous field name error should be ignored during initial sync
create mode 100644 jstests/replsets/initial_sync_ambiguous_index.js (cherry picked from commit 3423ca586b88566857f3fcdfeca1c6fdee7a0911)
-rw-r--r--jstests/replsets/initial_sync_ambiguous_index.js71
-rw-r--r--src/mongo/db/index/index_access_method.cpp2
2 files changed, 73 insertions, 0 deletions
diff --git a/jstests/replsets/initial_sync_ambiguous_index.js b/jstests/replsets/initial_sync_ambiguous_index.js
new file mode 100644
index 00000000000..85c1b673536
--- /dev/null
+++ b/jstests/replsets/initial_sync_ambiguous_index.js
@@ -0,0 +1,71 @@
+/**
+ * Asserts that inserting a document like `{a:[{"0":1}]}` on the
+ * primary doesn't cause initial-sync to fail if there was index
+ * on `a.0` at the beginning of initial-sync but the `dropIndex`
+ * hasn't yet been applied on the secondary prior to cloning the
+ * insert oplog entry.
+ */
+
+(function() {
+ "use strict";
+
+ load("jstests/libs/check_log.js");
+
+ const dbName = 'test';
+ const collectionName = 'coll';
+
+ // How many documents to insert on the primary prior to
+ // starting initial-sync.
+ const initialDocs = 10;
+ // Batch-size used for cloning.
+ // Used as a fail-point parameter as detailed below.
+ const clonerBatchSize = 1;
+
+ // Setting initialDocs larger than clonerBatchSize causes
+ // the fail-point to be hit because we fetch
+ // multiple batches in the InitialSyncer.
+
+ // Start one-node repl-set.
+ const rst = new ReplSetTest({name: "apply_ops_ambiguous_index", nodes: 1});
+ rst.startSet();
+ rst.initiate();
+ const primaryColl = rst.getPrimary().getDB(dbName).getCollection(collectionName);
+
+ // Insert the initial document set.
+ for (let i = 0; i < initialDocs; ++i) {
+ primaryColl.insertOne({_id: i, a: i});
+ }
+
+ // Add a secondary.
+ const secondary = rst.add({
+ setParameter: {"numInitialSyncAttempts": 1, 'collectionClonerBatchSize': clonerBatchSize}
+ });
+ secondary.setSlaveOk();
+ const secondaryColl = secondary.getDB(dbName).getCollection(collectionName);
+
+ // We set the collectionClonerBatchSize low above, so we will definitely hit
+ // this fail-point and hang after the first batch is applied. While the
+ // secondary is hung we clone the problematic document.
+ secondary.adminCommand({
+ configureFailPoint: "initialSyncHangBeforeCopyingDatabases",
+ mode: "alwaysOn",
+ data: {nss: secondaryColl.getFullName()}
+ });
+ rst.reInitiate();
+ checkLog.contains(secondary, "initialSyncHangBeforeCopyingDatabases fail point enabled");
+
+ // Insert and delete the problematic document and then create the problematic index.
+ // The collection-cloner will resume when the failpoint is turned off.
+ primaryColl.insertOne({_id: 200, a: [{"0": 1}]});
+ primaryColl.deleteOne({_id: 200});
+ primaryColl.ensureIndex({"a.0": 1});
+
+ // Resume initial sync. The "bad" document will be applied; the dropIndex will
+ // be applied later.
+ secondary.adminCommand(
+ {configureFailPoint: "initialSyncHangBeforeCopyingDatabases", mode: "off"});
+
+ // Wait for initial sync to finish.
+ rst.awaitSecondaryNodes();
+ rst.stopSet();
+})();
diff --git a/src/mongo/db/index/index_access_method.cpp b/src/mongo/db/index/index_access_method.cpp
index 583a2cd3bf0..8fdc91d2048 100644
--- a/src/mongo/db/index/index_access_method.cpp
+++ b/src/mongo/db/index/index_access_method.cpp
@@ -589,6 +589,8 @@ void IndexAccessMethod::getKeys(const BSONObj& obj,
17262,
// Hash
16766,
+ // Ambiguous array field name
+ 16746,
// Haystack
16775,
16776,