I have read Doctrine 2 Inheritance Mapping with Association but say if you needed Animal
to be an entity in its own right, say for creating option lists.
In this case the Discriminator Column for a Pet
is in the species column in the animal table
.
So the classes would be something like this.
class Animal
{
$id;
$species;
}
/**
* @Table(name="animal")
* @InheritanceType("JOINED")
* @DiscriminatorColumn(name="species", type="string")
* @DiscriminatorMap({"dog" = "Dog", "cat" = "Cat"})
*/
abstract class Pet
{
$id
$species;
}
class Dog extends Pet { }
class Cat extends Pet { }
class Owner
{
/**
* @OneToMany(targetEntity="Pet")
*/
$pets
}
I see a couple of problems.
the
animal
table doesn't have a foreign key toowner
. So the the$pets
association isn't going to work.Animal
andPet
are more or less that same thing. If some one changes something inAnimal
those changes wouldn't be reflected in anyPet
subclasses.
A possible solution to the first problem would be to have an extra table called pet
, but there is still an issue with the association, because the discriminator column is still in the animal
table and duplicating the column in pet
would break normalisation.
I'm not sure to fully understand your problem, but I'll give it a try:
Pet
being anAnimal
, it makes sense to make it explicit in your class hierarchy. Note that the abstract classPet
can subclass the concrete classAnimal
. This way, you can still instantiate anAnimal
, aDog
or aCat
, but you can't instantiate aPet
;Animal
root class can have its own discriminator value, which makes possible to persist it with Doctrine. You can then create and persist aDog
or aCat
, and even a genericAnimal
;Animal
needs a reference to its owner;Owner
now has a one-to-many relationship toAnimal
;species
column is a discriminator, and adds no value to your domain model (the class name will tell you whichAnimal
you're dealing with), so I would advise to remove this property.Final note, do you really need a
Pet
class? If a Pet has nothing specific over anAnimal
(i.e. the class is empty), then you should probably remove it from your class hierarchy.About your database structure, I propose the following changes:
owner_id
fromDog
&Cat
to theAnimal
table;animal_id
from theDog
&Cat
tables; they'll share theid
value with theAnimal
table (one-to-one).