Question

What I'm trying to do sounds logical to me however I'm not sure.

I am trying to improve part of a MongoDB collection by using Multikeys.

For example: I have multiple documents with the following format:

Document:

{
   "_id": ObjectId("528a4177dbcfd00000000013"),
   "name": "Shopping",
   "tags": [
     "retail",
     "shop",
     "shopping",
     "store",
     "grocery" 
  ] 
}


Query:
Up until now, I have been using the following query to match the tags field.

var tags = Array("store", "shopping", "etc");
db.collection.findOne({ 'tags': { $in: tags } }, { name: true });

This has been working well, however I think Multikeys should be used in this instance to improve speed & performance. Please, correct me if I am wrong!


Indexing:
I issued the following command in an attempt to index the tags.

db.collection.ensureIndex( { tags: 1 }, { safe: true }, function(err, doc) {} );

ensureIndex was successful.


Result:
However when using RockMongo's explain feature on the above query, the result is:

{
   "indexOnly": false,
   "indexBounds": {
     "tags": [
       [
         "etc",
         "etc" 
      ],
       [
         "shopping",
         "shopping" 
      ],
       [
         "store",
         "store" 
      ] 
    ] 
  }
}


Questions:

  1. Why is indexing not working, is there something else I have to do?
  2. Is Multikey indexing in this case beneficial? (I'm assuming yes.)
  3. Is there another form of indexing that would be more beneficial?



Edit:
I've just noticed that in the RockMongo explain data there is a field: "isMultiKey": true,
could it be that Multikeys are being used and I've completely misunderstood that it IS being indexed?

Was it helpful?

Solution

As you say in your edit, and coming from the part of explain you did not post is that isMulyiKey: true along with other information on the cursor are showing that the index is being used. The indexBounds are another indicator.

What is being described by indexOnly is the fact that your query contains another field, name, which is not part of the index. When the query optimizer sees that all elements of the query can be met by using the fields from within the index this is referred to as a covered query and the indexOnly property here is set to true.

So in an Ideal situation your query and results are using the information from the index only and MongoDB does not also have to look up the entry from the index in the collection in order to return more data.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top