Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Doctrine MongoDb Embedded Document - How to specify fields

I'm using Symfony 2 with Doctrine MongoDb bundle.

There are two classes with mappings:

/**
 * @MongoDB\Document
 */
class Consultant
{
    /**
     * @MongoDB\Id(strategy="NONE")
     */
    protected $id;

    /**
     * @MongoDB\EmbedMany(targetDocument="Specialization", strategy="set")
     */
    protected $specs;
}

/**
 * @MongoDB\Document
 */
class Specialization
{
    /**
     * @MongoDB\Id
     */
    protected $id;

    /**
     * @MongoDB\String
     */
    protected $name;

    /**
     * @MongoDB\Boolean
     */
    protected $visible = true;
}

After saving a consultant, the Mongo record looks like this:

{
   "_id": "1",
   "name": "Manager",
   "specs": {
     "0": {
       "_id": ObjectId("50d071ac6146a1f342000001"),
       "name": "Support",
       "visible": false 
    },
     "1": {
       "_id": ObjectId("50d069336146a10244000000"),
       "name": "Orders",
       "visible": false 
    } 
  } 
}

Everything is fine except the redundant field 'visible'.

Is there a way to specify what fields should be embedded by Doctrine using @EmbedMany annotation?

like image 376
marden Avatar asked Dec 19 '12 06:12

marden


1 Answers

The Specialization class uses a Document mapping, which is not intended for use with embedding. You should be using EmbeddedDocument for that.

Given that you want to use the same class on its own and in embedded form, it would be best to create an abstract class annotated with MappedSuperclass. There, you can define any field mappings that should exist on both the document and embedded document. In your case, you could leave visible to be defined on the inheriting document class.

Also, be aware that by using the set strategy, you're storing the embedded collection as an object instead of the usual array. This can have implications if you mean to index fields within the denormalized, embedded documents, as you won't be able to make use of multikey indexing. It's also possible to create gaps among the numeric keys.

like image 174
jmikola Avatar answered Sep 30 '22 03:09

jmikola