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
102
103
104
105
106
107
108
109
110
111
112
113
114
|
/**
* Test that operations that get blocked by catalog cache refreshes get logged to
* shardingStatistics.
*/
(function() {
'use strict';
load('jstests/sharding/libs/sharded_transactions_helpers.js');
load("jstests/sharding/libs/chunk_bounds_util.js");
load("jstests/sharding/libs/find_chunks_util.js");
let st = new ShardingTest({mongos: 2, shards: 2});
const configDB = st.s.getDB('config');
const dbName = "test";
const collName = "foo";
const ns = dbName + "." + collName;
const mongos0DB = st.s0.getDB(dbName);
const mongos1DB = st.s1.getDB(dbName);
const mongos0Coll = mongos0DB[collName];
const mongos1Coll = mongos1DB[collName];
let setUp = () => {
/**
* Sets up a test by moving chunks to such that one chunk is on each
* shard, with the following distribution:
* shard0: [-inf, 0)
* shard1: [0, inf)
*/
assert.commandWorked(st.s0.adminCommand({enableSharding: dbName}));
assert.commandWorked(st.s0.adminCommand({movePrimary: dbName, to: st.shard0.shardName}));
assert.commandWorked(st.s0.adminCommand({shardCollection: ns, key: {x: 1}}));
assert.commandWorked(st.s0.adminCommand({split: ns, middle: {x: 0}}));
flushRoutersAndRefreshShardMetadata(st, {ns});
};
let getOpsBlockedByRefresh = () => {
return assert.commandWorked(st.s1.adminCommand({serverStatus: 1}))
.shardingStatistics.catalogCache.operationsBlockedByRefresh;
};
let verifyBlockedOperationsChange = (oldOperationsCount, increasedOps) => {
let newOperationsCount = getOpsBlockedByRefresh();
increasedOps.forEach(op => {
assert.eq(newOperationsCount[op.opType], oldOperationsCount[op.opType] + op.increase);
});
};
let getShardToTargetForMoveChunk = () => {
const chunkDocs = findChunksUtil.findChunksByNs(configDB, ns).toArray();
const shardChunkBounds = chunkBoundsUtil.findShardChunkBounds(chunkDocs);
const shardThatOwnsChunk = chunkBoundsUtil.findShardForShardKey(st, shardChunkBounds, {x: 100});
return st.getOther(shardThatOwnsChunk).shardName;
};
let runTest = (operationToRunFn, expectedOpIncreases) => {
let opsBlockedByRefresh = getOpsBlockedByRefresh();
// Move chunk to ensure stale shard version for the next operation.
assert.commandWorked(
st.s0.adminCommand({moveChunk: ns, find: {x: 100}, to: getShardToTargetForMoveChunk()}));
operationToRunFn();
verifyBlockedOperationsChange(opsBlockedByRefresh, expectedOpIncreases);
};
setUp();
/**
* Verify that insert operations get logged when blocked by a refresh.
*/
runTest(() => assert.commandWorked(mongos1Coll.insert({x: 250})), [
{opType: 'countAllOperations', increase: 2},
{opType: 'countInserts', increase: 1},
{opType: 'countCommands', increase: 1}
]);
/**
* Verify that queries get logged when blocked by a refresh.
*/
runTest(() => mongos1Coll.findOne({x: 250}),
[{opType: 'countAllOperations', increase: 1}, {opType: 'countQueries', increase: 1}]);
/**
* Verify that updates get logged when blocked by a refresh.
*/
runTest(() => assert.commandWorked(mongos1Coll.update({x: 250}, {$set: {a: 1}})), [
{opType: 'countAllOperations', increase: 2},
{opType: 'countUpdates', increase: 1},
{opType: 'countCommands', increase: 1}
]);
/**
* Verify that deletes get logged when blocked by a refresh.
*/
runTest(() => assert.commandWorked(mongos1Coll.remove({x: 250})), [
{opType: 'countAllOperations', increase: 2},
{opType: 'countDeletes', increase: 1},
{opType: 'countCommands', increase: 1}
]);
/**
* Verify that non-CRUD commands get logged when blocked by a refresh.
*/
runTest(() => assert.commandWorked(mongos1DB.runCommand(
{createIndexes: collName, indexes: [{key: {a: 1}, name: 'index'}]})),
[
{opType: 'countAllOperations', increase: 1},
{opType: 'countCommands', increase: 1},
]);
st.stop();
})();
|