summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMax Hirschhorn <max.hirschhorn@mongodb.com>2016-01-27 16:48:44 -0500
committerMax Hirschhorn <max.hirschhorn@mongodb.com>2016-01-27 16:48:44 -0500
commit70d53cfcb4751603f6509ea2c734eccafe565e2e (patch)
tree6b0e170fa671340232cd32f50c46a146b3f0aa8d
parentdd6350f7dea586a73d5dbba002deb51f6a5dbce3 (diff)
downloadmongo-70d53cfcb4751603f6509ea2c734eccafe565e2e.tar.gz
SERVER-21499 Update FSM workloads to handle more frequent yielding.
When running different FSM workloads simultaneously, it is possible for failpoints or configured server parameters to cause a workload to experience conditions that would normally only occur under high load. (cherry picked from commit c36c82ed483ffcd1087260e4a125c625a2026ed1)
-rw-r--r--jstests/concurrency/fsm_workloads/update_array.js25
-rw-r--r--jstests/concurrency/fsm_workloads/update_inc.js15
-rw-r--r--jstests/concurrency/fsm_workloads/update_ordered_bulk_inc.js5
-rw-r--r--jstests/concurrency/fsm_workloads/update_replace.js17
4 files changed, 50 insertions, 12 deletions
diff --git a/jstests/concurrency/fsm_workloads/update_array.js b/jstests/concurrency/fsm_workloads/update_array.js
index fe741090dd6..b2681fb792a 100644
--- a/jstests/concurrency/fsm_workloads/update_array.js
+++ b/jstests/concurrency/fsm_workloads/update_array.js
@@ -49,9 +49,15 @@ var $config = (function() {
assertWhenOwnColl.neq(null, doc);
assertWhenOwnColl(doc.hasOwnProperty('arr'),
'doc should have contained a field named "arr": ' + tojson(doc));
- assertWhenOwnColl.contains(value, doc.arr,
- "doc.arr doesn't contain value (" + value +
- ') after $push: ' + tojson(doc.arr));
+
+ // If the document was invalidated during a yield, then we may not have updated
+ // anything. The $push operator always modifies the matched document, so if we
+ // matched something, then we must have updated it.
+ if (res.nMatched > 0) {
+ assertWhenOwnColl.contains(value, doc.arr,
+ "doc.arr doesn't contain value (" + value +
+ ') after $push: ' + tojson(doc.arr));
+ }
});
}
@@ -65,9 +71,16 @@ var $config = (function() {
var doc = db[collName].findOne({ _id: docIndex });
assertWhenOwnColl(function() {
assertWhenOwnColl.neq(null, doc);
- assertWhenOwnColl.eq(-1, doc.arr.indexOf(value),
- 'doc.arr contains removed value (' + value +
- ') after $pull: ' + tojson(doc.arr));
+
+ // If the document was invalidated during a yield, then we may not have updated
+ // anything. If the update matched a document, then the $pull operator would have
+ // removed all occurrences of 'value' from the array (meaning that there should be
+ // none left).
+ if (res.nMatched > 0) {
+ assertWhenOwnColl.eq(-1, doc.arr.indexOf(value),
+ 'doc.arr contains removed value (' + value +
+ ') after $pull: ' + tojson(doc.arr));
+ }
});
}
diff --git a/jstests/concurrency/fsm_workloads/update_inc.js b/jstests/concurrency/fsm_workloads/update_inc.js
index 32dca107456..adc1c536fdd 100644
--- a/jstests/concurrency/fsm_workloads/update_inc.js
+++ b/jstests/concurrency/fsm_workloads/update_inc.js
@@ -49,16 +49,23 @@ var $config = (function() {
}
}
- ++this.count;
+ // The $inc operator always modifies the matched document, so if we matched something,
+ // then we must have updated it.
+ this.count += (res.nMatched >= 1);
},
find: function find(db, collName) {
var docs = db[collName].find().toArray();
assertWhenOwnColl.eq(1, docs.length);
- assertWhenOwnColl((function() {
+ assertWhenOwnColl(() => {
+ // If the document hasn't been updated at all, then the field won't exist.
var doc = docs[0];
- assertWhenOwnColl.eq(this.count, doc[this.fieldName]);
- }).bind(this));
+ if (doc.hasOwnProperty(this.fieldName)) {
+ assertWhenOwnColl.eq(this.count, doc[this.fieldName]);
+ } else {
+ assertWhenOwnColl.eq(this.count, 0);
+ }
+ });
}
};
diff --git a/jstests/concurrency/fsm_workloads/update_ordered_bulk_inc.js b/jstests/concurrency/fsm_workloads/update_ordered_bulk_inc.js
index 9bd36519229..93911a4a44f 100644
--- a/jstests/concurrency/fsm_workloads/update_ordered_bulk_inc.js
+++ b/jstests/concurrency/fsm_workloads/update_ordered_bulk_inc.js
@@ -54,7 +54,10 @@ var $config = (function() {
}
docs.forEach(function(doc) {
- assertWhenOwnColl.lte(doc[this.fieldName], this.count);
+ // If the document hasn't been updated at all, then the field won't exist.
+ if (doc.hasOwnProperty(this.fieldName)) {
+ assertWhenOwnColl.lte(doc[this.fieldName], this.count);
+ }
assertWhenOwnColl.lt(doc._id, this.docCount);
}, this);
}
diff --git a/jstests/concurrency/fsm_workloads/update_replace.js b/jstests/concurrency/fsm_workloads/update_replace.js
index 9776d6f31da..bc183d01fbb 100644
--- a/jstests/concurrency/fsm_workloads/update_replace.js
+++ b/jstests/concurrency/fsm_workloads/update_replace.js
@@ -6,14 +6,29 @@
* Does updates that replace an entire document.
* The collection has indexes on some but not all fields.
*/
+load('jstests/concurrency/fsm_workload_helpers/server_types.js'); // for isMongod and isMMAPv1
+
var $config = (function() {
// explicitly pass db to avoid accidentally using the global `db`
function assertResult(db, res) {
assertAlways.eq(0, res.nUpserted, tojson(res));
- assertWhenOwnColl.eq(1, res.nMatched, tojson(res));
+
+ if (isMongod(db) && !isMMAPv1(db)) {
+ // For non-MMAPv1 storage engines we can make a stong assertion that exactly one
+ // document was matched.
+ assertWhenOwnColl.eq(res.nMatched, 1, tojson(res));
+ } else {
+ // It's possible to match zero documents with MMAPv1 because the update can skip a
+ // document that was invalidated during a yield.
+ assertWhenOwnColl.contains(res.nMatched, [0, 1], tojson(res));
+ }
+
if (db.getMongo().writeMode() === 'commands') {
+ // It's possible that we replaced the document with its current contents, making the
+ // update a no-op.
assertWhenOwnColl.contains(res.nModified, [0, 1], tojson(res));
+ assertAlways.lte(res.nModified, res.nMatched, tojson(res));
}
}