// $ifNull returns the result of the first expression if not null or undefined, otherwise of the // second expression. load('jstests/aggregation/extras/utils.js'); t = db.jstests_aggregation_ifnull; t.drop(); t.save({}); function assertError(expectedErrorCode, ifNullSpec) { assertErrorCode(t, {$project: {a: {$ifNull: ifNullSpec}}}, expectedErrorCode); } function assertResult(expectedResult, arg0, arg1) { var res = t.aggregate({$project: {a: {$ifNull: [arg0, arg1]}}}).toArray()[0]; assert.eq(expectedResult, res.a); } // Wrong number of args. assertError(16020, []); assertError(16020, [1]); assertError(16020, [null]); assertError(16020, [1, 1, 1]); assertError(16020, [1, 1, null]); assertError(16020, [1, 1, undefined]); // First arg non null. assertResult(1, 1, 2); assertResult(2, 2, 1); assertResult(false, false, 1); assertResult('', '', 1); assertResult([], [], 1); assertResult({}, {}, 1); assertResult(1, 1, null); assertResult(2, 2, undefined); // First arg null. assertResult(2, null, 2); assertResult(1, null, 1); assertResult(null, null, null); assertResult(undefined, null, undefined); // First arg undefined. assertResult(2, undefined, 2); assertResult(1, undefined, 1); assertResult(null, undefined, null); assertResult(undefined, undefined, undefined); // Computed expression. assertResult(3, {$add: [1, 2]}, 5); assertResult(20, '$missingField', {$multiply: [4, 5]}); // Divide/mod by 0. assertError(16608, [{$divide: [1, 0]}, 0]); assertError(16610, [{$mod: [1, 0]}, 0]); // Nested. t.drop(); t.save({d: 'foo'}); assertResult('foo', '$a', {$ifNull: ['$b', {$ifNull: ['$c', '$d']}]}); t.update({}, {$set: {b: 'bar'}}); assertResult('bar', '$a', {$ifNull: ['$b', {$ifNull: ['$c', '$d']}]});