Does _.pluck preserves the original index of the "plucked" array?

212 Views Asked by At

I have a mongoDB document with an array of objects field looking like this:

"leaving_users" : [
        {
            "user_id" : "FZ78Pr82JPz66Gc3p",
            "leaving_date" : ISODate("2015-06-12T14:14:14.501Z")
        }
    ]

Can I use _.pluck to obtain the leaving_date related to a specific user_id?

My code seems to work fine but I wanted to check this is the right way to do it, and be sure that I won't end up sometimes with a different index if I use a _.pluck function.

Here is my code:

if (doc.leaving_users //guarding
    //if the user belongs to the leaving_users object array
    &&  _.pluck(doc.leaving_users, "user_id").indexOf(userId) != -1 
    //if his leaving_date field is after yesterday
    && doc.leaving_users[_.pluck(doc.leaving_users, "user_id").indexOf(userId)].leaving_date > yesterday)
                {
                    leftRecently  = true;
                }   else{
                    leftRecently  = false;
                }

Bonus question: how would you make that more elegant?

1

There are 1 best solutions below

3
T.J. Crowder On BEST ANSWER

Yes, the indexes will be the same. This is clear if you look at the implementation of _.pluck:

_.pluck = function(obj, key) {
  return _.map(obj, _.property(key));
};

...and the implementation of _.map:

_.map = _.collect = function(obj, iteratee, context) {
  iteratee = cb(iteratee, context);
  var keys = !isArrayLike(obj) && _.keys(obj),
      length = (keys || obj).length,
      results = Array(length);
  for (var index = 0; index < length; index++) {
    var currentKey = keys ? keys[index] : index;
    results[index] = iteratee(obj[currentKey], currentKey, obj);
  }
  return results;
};

That said, I wouldn't call _.pluck twice like that, and I don't think I'd use _.pluck for this at all, I'd use _.findIndex and save the result:

var index;
if (doc.leaving_users //guarding
    //if the user belongs to the leaving_users object array
    && (index = _.findIndex(doc.leaving_users, function(e) { e.user_id === userId; }) !== -1)
    //if his leaving_date field is after yesterday
    && doc.leaving_users[index].leaving_date > yesterday)
                {
                    leftRecently  = true;
                }   else{
                    leftRecently  = false;
                }