114 lines
3.1 KiB
JavaScript
114 lines
3.1 KiB
JavaScript
/**
|
|
* Test the rank based window functions.
|
|
*/
|
|
(function() {
|
|
"use strict";
|
|
|
|
load("jstests/aggregation/extras/utils.js"); // documentEq
|
|
|
|
const coll = db[jsTestName()];
|
|
for (let i = 0; i < 12; i++) {
|
|
coll.insert({_id: i, double: Math.floor(i / 2)});
|
|
}
|
|
|
|
let origDocs = coll.find().sort({_id: 1});
|
|
function verifyResults(results, valueFunction) {
|
|
for (let i = 0; i < results.length; i++) {
|
|
const correctDoc = valueFunction(i, Object.assign({}, origDocs[i]));
|
|
assert(documentEq(correctDoc, results[i]),
|
|
"Got: " + tojson(results[i]) + "\nExpected: " + tojson(correctDoc) +
|
|
"\n at position " + i + "\n");
|
|
}
|
|
}
|
|
|
|
function runRankBasedAccumulator(sortByField, exprField) {
|
|
return coll
|
|
.aggregate([{
|
|
$setWindowFields: {sortBy: sortByField, output: {rank: exprField}},
|
|
}])
|
|
.toArray();
|
|
}
|
|
|
|
// Rank based accumulators don't take windows.
|
|
assert.commandFailedWithCode(coll.runCommand({
|
|
aggregate: coll.getName(),
|
|
pipeline: [{
|
|
$setWindowFields: {
|
|
sortBy: {_id: 1},
|
|
output: {rank: {$rank: {}, window: []}},
|
|
}
|
|
}],
|
|
cursor: {}
|
|
}),
|
|
5371601);
|
|
|
|
// Rank based accumulators don't take arguments.
|
|
assert.commandFailedWithCode(coll.runCommand({
|
|
aggregate: coll.getName(),
|
|
pipeline: [{
|
|
$setWindowFields: {
|
|
sortBy: {_id: 1},
|
|
output: {rank: {$rank: "$_id"}},
|
|
}
|
|
}],
|
|
cursor: {}
|
|
}),
|
|
5371603);
|
|
|
|
// Rank based accumulators must have a sortBy.
|
|
assert.commandFailedWithCode(coll.runCommand({
|
|
aggregate: coll.getName(),
|
|
pipeline: [{
|
|
$setWindowFields: {
|
|
output: {rank: {$rank: {}}},
|
|
}
|
|
}],
|
|
cursor: {}
|
|
}),
|
|
5371602);
|
|
|
|
// Rank based accumulators don't take windows.
|
|
assert.commandFailedWithCode(coll.runCommand({
|
|
aggregate: coll.getName(),
|
|
pipeline: [{
|
|
$setWindowFields: {
|
|
sortBy: {_id: 1},
|
|
output: {rank: {$rank: {}, window: {documents: [-1, 1]}}},
|
|
}
|
|
}],
|
|
cursor: {}
|
|
}),
|
|
5371601);
|
|
|
|
// Check results with no ties
|
|
let result = runRankBasedAccumulator({_id: 1}, {$rank: {}});
|
|
function noTieFunc(num, baseObj) {
|
|
baseObj.rank = num + 1;
|
|
return baseObj;
|
|
}
|
|
verifyResults(result, noTieFunc);
|
|
result = runRankBasedAccumulator({_id: 1}, {$denseRank: {}});
|
|
verifyResults(result, noTieFunc);
|
|
result = runRankBasedAccumulator({_id: 1}, {$documentNumber: {}});
|
|
verifyResults(result, noTieFunc);
|
|
|
|
// Check results with ties
|
|
origDocs = coll.find().sort({double: 1});
|
|
result = runRankBasedAccumulator({double: 1}, {$rank: {}});
|
|
verifyResults(result, function(num, baseObj) {
|
|
if (num % 2 == 0) {
|
|
baseObj.rank = num + 1;
|
|
} else {
|
|
baseObj.rank = num;
|
|
}
|
|
return baseObj;
|
|
});
|
|
result = runRankBasedAccumulator({double: 1}, {$denseRank: {}});
|
|
verifyResults(result, function(num, baseObj) {
|
|
baseObj.rank = Math.floor(num / 2) + 1;
|
|
return baseObj;
|
|
});
|
|
result = runRankBasedAccumulator({double: 1}, {$documentNumber: {}});
|
|
verifyResults(result, noTieFunc);
|
|
})();
|