4

How can I tell the difference between an empty array and a null/undefined value when reading from a MongoDB with Mongoose? Mongoose reads both as an empty array, but in the database I have to work with the meanings of those is a different one.

Example:

var Mongoose = require('mongoose');
var MongoClient = require('mongodb').MongoClient;

Mongoose.connect('mongodb://localhost/test'); // mongoose
var Demo = Mongoose.model('demo', { names: [String] }, 'demo');

MongoClient.connect('mongodb://localhost/test', function (err, db) {
  if (err) return console.error(err);
  var collection = db.collection('demo');

  // insert undefined array with MongoDB:
  collection.insert({}, function(err, status) {
    if(err) return console.error(err);
    console.log('direct DB:', status.ops[0]);

    // retrieve with Mongoose:
    Demo.findOne({_id: status.insertedIds[0]}, function(err, doc) {
      if(err) return console.error(err);
      console.log('Mongoose:', doc);
    });
  });
});

When I run this code, it results in this output:

direct DB: { _id: 56b07f632390b15c15b4185d }
Mongoose: { names: [], _id: 56b07f632390b15c15b4185d }

So Mongoose sets an empty array where there shouldn't be one when reading from the database. I already tried setting name to undefined in post init hook, but it did not show any effect.

Any ideas how I could read this undef as an undef?

1
  • 2
    Probably not the answer you want to hear, but the right answer here is to add a separate boolean field to your schema to indicate whatever your null array field is meant to indicate. Commented Feb 2, 2016 at 14:27

1 Answer 1

1

Mongoose always initializes array attributes to an empty array.

You can check if the names attribute exists and if its length property is not 0:

if (doc.names && doc.names.length) {
  // Do something if there is at least one item in the names array.
}

The check works by short-circuiting:

  1. If doc.names does not exist, the result is undefined which is falsy. This causes the if block to be skipped.
  2. If doc.names exists and is truthy, then the if block evaluates thh length property of doc.names. If this length is 0 or doesn't exist, the boolean expression in the if block is false and the if block is skipped.
Sign up to request clarification or add additional context in comments.

2 Comments

How could that tell the difference to a non-existing property in the database?
But doc.names exists and ist truthy, despite the fact there is no names property in the database. This is exactly my problem :-)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.