2

I have a user collection with tons of properties for each user. One property is an array ('guestlist_submitted') and I am trying to return the most recent 3 items in that array according to the date field.

Using Mongoose, I am able to target that specific property on the user object, but I can't seem to limit or sort them.

I've tried using slice and and a date calculation to return the most recent 3 entires but I am struggling to get it right and not sure whats wrong.

I've tried using Sort/Limit on query builder but I've learned that these dont apply to the array inside the property I am targeting despite me saying " select('guestlist_submitted') as part ofthe query builder.

When I return the result after just targeting the property on the user object, it comes as an array with an object inside and another array inside that object. I am having problems traversing down it to target that inner array to use the slice and date sort.

First try

    Users.
    find({ fbid: req.query.fbid}).
    select('guestlist_submitted -_id').
    sort({"guestlist_submitted.date": 'desc'}).
    limit(3).
    exec((err, result) => {
        if (err) throw (err));
        if (result) {

            res.send(result);

        }

Second try:

    Users.
    find({ fbid: req.query.fbid}).
    select('guestlist_submitted -_id').
    exec((err, result) => {
        if (err) res.send(JSON.stringify(err));
        if (result) {

            const slicedArr = result.guestlist_submitted.slice(0,1);

            const sortedResultArr = slicedArr.sort(function(a,b){return new Date(b.date) - new Date(a.date); });

            const newResultArr = sortedResultArr.slice(0, 2);

            res.send(newResultArr);

        }

The best I can get is 'guestlist_submitted' and the entire array, not sorted and its inside an object inside an array.

I expected the output to be the 3 most recent results from the guestlist_submitted array inside a new array that I can display on the client.

Thank you in advance for your help

EDIT - FIGURED OUT A SOLUTION

I ended up figuring out how to get what I wanted using aggregate()

Users.aggregate([

    {
        $match:  {fbid: req.query.fbid}
    },
    {
        $unwind: "$guestlist_submitted"
    },
    {
        $sort: {'guestlist_submitted.date': -1}
    },
    {
        $limit: 2
    },
    {
        $group: {_id: '$_id', guestlist_submitted: {$push: '$guestlist_submitted'}}

    },
    {
        $project: { guestlist_submitted: 1, _id: 0 }

    }


]).exec((err, result) => {
    if (err) res.send(JSON.stringify(err));
    if (result) {

        console.log(result);
        res.send(result);
    }

}); 

1 Answer 1

2

I ended up figuring out how to get what I wanted using aggregate()

Users.aggregate([

    {
        $match:  {fbid: req.query.fbid}
    },
    {
        $unwind: "$guestlist_submitted"
    },
    {
        $sort: {'guestlist_submitted.date': -1}
    },
    {
        $limit: 2
    },
    {
        $group: {_id: '$_id', guestlist_submitted: {$push: '$guestlist_submitted'}}

    },
    {
        $project: { guestlist_submitted: 1, _id: 0 }

    }


]).exec((err, result) => {
    if (err) res.send(JSON.stringify(err));
    if (result) {

        console.log(result);
        res.send(result);
    }

}); 
Sign up to request clarification or add additional context in comments.

1 Comment

Lifesaver! :D I was wondering if it was even possible or that I needed to sort the array myself. Thank you.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.