Angry B
Angry B

Reputation: 305

Is it possible to find random documents in collection, without same fields? (monogdb\node.js)

For example, I have a collection users with the following structure:

{
   _id: 1, 
   name: "John",
   from: "Amsterdam"
},
{
    _id: 2,
    name: "John",
    from: "Boston"
},
{
    _id: 3,
    name: "Mia",
    from: "Paris"
},
{
    _id: 4,
    name: "Kate",
    from: "London"
},
{
    _id: 5,
    name: "Kate",
    from: "Moscow"
}

How can I get 3 random documents in which names will not be repeated?

Using the function getFourNumbers(1, 5), I get array with 3 non-repeating numbers and search by _id

var random_nums = getThreeNumbersnumbers(1, 5); // [2,3,1]
users.find({_id: {$in: random_nums}, function (err, data) {...} //[John, Mia, John]

But it can consist two Johns or two Kates, what is unwanted behavior. How can I get three random documents ( [John, Mia, Kate]. Not [John, Kate, Kate] or [John, Mia, John]) with 1 or maximum 2 queries? Kate or John (duplicated names) should be random, but should not be repeated.

Upvotes: 0

Views: 57

Answers (2)

dnickless
dnickless

Reputation: 10918

There you go - see the comments in the code for further explanation of what the stages do:

users.aggregate(
[
    { // eliminate duplicates based on "name" field and keep track of first document of each group
       $group: {
            "_id": "$name",
            "doc": { $first: "$$ROOT" }
        }
    },
    {
        // restore the original document structure
        $replaceRoot: {
            newRoot: "$doc"
        }
    },
    {
        // select 3 random documents from the result
        $sample: {
            size:3
        }
    }
])

As always with the aggrgation framework you can run the query with more or less stages added in order to see the transformations step by step.

Upvotes: 1

Raghav Garg
Raghav Garg

Reputation: 3707

I think what you are looking for is the $group aggregator, which will give you the distinct value of the collection. It can be used as:

db.users.aggregate( [ { $group : { name : "$name" } } ] );

MongoDB docs: Retrieve Distinct Values

Upvotes: 1

Related Questions