For extended documentation, check out http://docs.mongodb.org/manual/reference/operator/query/
- Supported operators: $in, $nin, $exists, $gte, $gt, $lte, $lt, $eq, $ne, $mod, $all, $and, $or, $nor, $not, $size, $type, $regex, $where, $elemMatch
- Regexp searches
- Function filtering
- sub object searching
- dot notation searching
- Supports node.js, and web
- Custom Expressions
- filtering of immutable datastructures
import sift from 'sift';
//intersecting arrays
var result = ['hello', 'sifted', 'array!'].filter(sift({$in: ['hello', 'world']})); //['hello']
//regexp filter
var result = ['craig', 'john', 'jake'].filter(sift(/^j/)); //['john','jake']
// function filter
var testFilter = sift({
//you can also filter against functions
name: function(value) {
return value.length == 5;
},
});
var result = [
{
name: 'craig',
},
{
name: 'john',
},
{
name: 'jake',
},
].filter(testFilter); // filtered: [{ name: 'craig' }]
//you can test *single values* against your custom sifter
testQuery({name: 'sarah'}); //true
testQuery({name: 'tim'}); //false\
query
- the filter to use against the target arrayoptions
-select
- value selector -expressions
- custom expressions
With an array:
['craig', null].filter(sift({$exists: true})); //['craig']
Without an array, a sifter is returned:
var existsFilter = sift({$exists: true});
existsFilter('craig'); //true
existsFilter(null); //false
['craig', null].filter(existsFilter); //['craig']
With a selector:
var omitNameFilter = sift({$exists: true}, function(user) {
return !!user.name;
});
[
{
name: 'Craig',
},
{
name: null,
},
].filter(omitNameFilter);
With your sifter, you can also test values:
siftExists(null); //false
siftExists('craig'); //true
See MongoDB's advanced queries for more info.
array value must be $in the given query:
Intersecting two arrays:
//filtered: ['Brazil']
['Brazil', 'Haiti', 'Peru', 'Chile'].filter(sift({$in: ['Costa Rica', 'Brazil']}));
Here's another example. This acts more like the $or operator:
[{name: 'Craig', location: 'Brazil'}].filter(sift({location: {$in: ['Costa Rica', 'Brazil']}}));
Opposite of $in:
//filtered: ['Haiti','Peru','Chile']
['Brazil', 'Haiti', 'Peru', 'Chile'].filter(sift({$nin: ['Costa Rica', 'Brazil']}));
Checks if whether a value exists:
//filtered: ['Craig','Tim']
sift({$exists: true}, ['Craig', null, 'Tim']);
You can also filter out values that don't exist
//filtered: [{ name: 'Craig', city: 'Minneapolis' }]
[{name: 'Craig', city: 'Minneapolis'}, {name: 'Tim'}].filter(sift({city: {$exists: false}}));
Checks if a number is >= value:
//filtered: [2, 3]
[0, 1, 2, 3].filter(sift({$gte: 2}));
Checks if a number is > value:
//filtered: [3]
[0, 1, 2, 3].filter(sift({$gt: 2}));
Checks if a number is <= value.
//filtered: [0, 1, 2]
[0, 1, 2, 3].filter(sift({$lte: 2}));
Checks if number is < value.
//filtered: [0, 1]
[0, 1, 2, 3].filter(sift({$lt: 2}));
Checks if query === value
. Note that $eq can be omitted. For $eq, and $ne
//filtered: [{ state: 'MN' }]
[{state: 'MN'}, {state: 'CA'}, {state: 'WI'}].filter(sift({state: {$eq: 'MN'}}));
Or:
//filtered: [{ state: 'MN' }]
[{state: 'MN'}, {state: 'CA'}, {state: 'WI'}].filter(sift({state: 'MN'}));
Checks if query !== value
.
//filtered: [{ state: 'CA' }, { state: 'WI'}]
[{state: 'MN'}, {state: 'CA'}, {state: 'WI'}].filter(sift({state: {$ne: 'MN'}}));
Modulus:
//filtered: [300, 600]
[100, 200, 300, 400, 500, 600].filter(sift({$mod: [3, 0]}));
values must match everything in array:
//filtered: [ { tags: ['books','programming','travel' ]} ]
[{tags: ['books', 'programming', 'travel']}, {tags: ['travel', 'cooking']}].filter(
sift({tags: {$all: ['books', 'programming']}})
);
ability to use an array of expressions. All expressions must test true.
//filtered: [ { name: 'Craig', state: 'MN' }]
[{name: 'Craig', state: 'MN'}, {name: 'Tim', state: 'MN'}, {name: 'Joe', state: 'CA'}].filter(
sift({$and: [{name: 'Craig'}, {state: 'MN'}]})
);
OR array of expressions.
//filtered: [ { name: 'Craig', state: 'MN' }, { name: 'Tim', state: 'MN' }]
[{name: 'Craig', state: 'MN'}, {name: 'Tim', state: 'MN'}, {name: 'Joe', state: 'CA'}].filter(
sift({$or: [{name: 'Craig'}, {state: 'MN'}]})
);
opposite of or:
//filtered: [ { name: 'Tim', state: 'MN' }, { name: 'Joe', state: 'CA' }]
[{name: 'Craig', state: 'MN'}, {name: 'Tim', state: 'MN'}, {name: 'Joe', state: 'CA'}].filter(
sift({$nor: [{name: 'Craig'}, {state: 'MN'}]})
);
Matches an array (or, for backwards-compatibility purposes, any value that reports a length
property that matches the given parameter) with the given size:
//filtered: ['food','cooking']
[{tags: ['food', 'cooking']}, {tags: ['traveling']}].filter(sift({tags: {$size: 2}}));
Matches a values based on the type
[new Date(), 4342, 'hello world'].filter(sift({$type: Date})); //returns single date
[new Date(), 4342, 'hello world'].filter(sift({$type: String})); //returns ['hello world']
Matches values based on the given regular expression
['frank', 'fred', 'sam', 'frost'].filter(sift({$regex: /^f/i, $nin: ['frank']})); // ["fred", "frost"]
['frank', 'fred', 'sam', 'frost'].filter(sift({$regex: '^f', $options: 'i', $nin: ['frank']})); // ["fred", "frost"]
Matches based on some javascript comparison
[{name: 'frank'}, {name: 'joe'}].filter(
sift({
$where: function() {
return this.name === 'frank';
},
})
); // ["frank"]
NOT supported, due to risk of RCE vulnerabilities:
[{name: 'frank'}, {name: 'joe'}].filter(sift({$where: "this.name === 'frank'"})); // ["frank"]
Matches elements of array
var bills = [
{
month: 'july',
casts: [
{
id: 1,
value: 200,
},
{
id: 2,
value: 1000,
},
],
},
{
month: 'august',
casts: [
{
id: 3,
value: 1000,
},
{
id: 4,
value: 4000,
},
],
},
];
var result = bills.filter(
sift({
casts: {
$elemMatch: {
value: {$gt: 1000},
},
},
})
); // {month:'august', casts:[{id:3, value: 1000},{id: 4, value: 4000}]}
Not expression:
['craig', 'tim', 'jake'].filter(sift({$not: {$in: ['craig', 'tim']}})); //['jake']
['craig', 'tim', 'jake'].filter(sift({$not: {$size: 5}})); //['tim','jake']
var filter = sift(
{
$customMod: 2,
},
{
expressions: {
$customMod: function(query, value) {
return query % value;
},
},
}
);
[1, 2, 3, 4, 5].filter(filter); // 1, 3, 5