summaryrefslogtreecommitdiff
path: root/jstests/concurrency/fsm_workloads/create_index_background_unique.js
blob: 4b4c50fd18e3654de7839835027e02683f1b1adf (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
'use strict';

/**
 * create_index_background_unique.js
 *
 * Creates multiple unique background indexes in parallel.
 *
 * @tags: [creates_background_indexes]
 */
load("jstests/concurrency/fsm_workload_helpers/assert_handle_fail_in_transaction.js");
var $config = (function() {
    var data = {
        prefix: "create_index_background_unique_",
        numDocsToLoad: 5000,
        iterationCount: 0,
        getCollectionNameForThread: function(threadId) {
            return this.prefix + threadId.toString();
        },
        // Allows tests that inherit from this one to specify options other than the default.
        getCollectionOptions: function() {
            return {};
        },
        buildvariableSizedDoc: function(uniquePrefix) {
            const indexedVal = uniquePrefix + Array(Random.randInt(1000)).toString();
            const doc = {x: indexedVal};
            return doc;
        },
    };

    var states = (function() {
        function buildIndex(db, collName) {
            this.iterationCount++;

            const res = db.runCommand({
                createIndexes: this.getCollectionNameForThread(this.tid),
                indexes: [{key: {x: 1}, name: "x_1", unique: true, background: true}]
            });
            // Multi-statement Transactions can fail with SnapshotUnavailable if there are
            // pending catalog changes as of the transaction start (see SERVER-43018).
            assertWorkedOrFailedHandleTxnErrors(res,
                                                [
                                                    ErrorCodes.IndexBuildAlreadyInProgress,
                                                    ErrorCodes.SnapshotUnavailable,
                                                    ErrorCodes.SnapshotTooOld,
                                                    ErrorCodes.NotMaster
                                                ],
                                                [ErrorCodes.NotMaster]);
        }

        function dropIndex(db, collName) {
            this.iterationCount++;

            // In the case that we have an even # of iterations, we skip the final drop so that
            // validation can be performed on the indexes created.
            if (this.iterationCount === this.iterations) {
                return;
            }

            assertAlways.commandWorked(db.runCommand(
                {dropIndexes: this.getCollectionNameForThread(this.tid), index: "x_1"}));
        }

        return {
            buildIndex: buildIndex,
            dropIndex: dropIndex,
        };
    })();

    var transitions = {
        buildIndex: {dropIndex: 1.0},
        dropIndex: {buildIndex: 1.0},
    };

    function setup(db, collName, cluster) {
        for (let j = 0; j < this.threadCount; ++j) {
            const collectionName = this.getCollectionNameForThread(j);
            assertAlways.commandWorked(
                db.createCollection(collectionName, this.getCollectionOptions()));
            var bulk = db[collectionName].initializeUnorderedBulkOp();

            // Preload documents for each thread's collection. This ensures that the index build and
            // drop have meaningful work to do.
            for (let i = 0; i < this.numDocsToLoad; ++i) {
                const uniqueValuePrefix = i.toString() + "_";
                bulk.insert(this.buildvariableSizedDoc(uniqueValuePrefix));
            }
            assertAlways.commandWorked(bulk.execute());
            assertAlways.eq(this.numDocsToLoad, db[collectionName].find({}).itcount());
        }
    }

    return {
        threadCount: 10,
        iterations: 11,
        data: data,
        states: states,
        startState: 'buildIndex',
        transitions: transitions,
        setup: setup,
    };
})();