Discriminator in a Joined Table with Doctrine2

2.5k views Asked by At

I have an abstract parent class called Divers which is extended by few other classes.
So, I use inheritance mapping with D2 using Single Table Inheritance strategy.

namespace MyBundle\Entity;

use Doctrine\ORM\Mapping as ORM;

/**
 * ParentClass
 * 
 * @ORM\Table(name="PARENTCLASS")
 * @ORM\Entity
 * @ORM\InheritanceType("SINGLE_TABLE")
 * @ORM\DiscriminatorColumn(name="idtable", type="string")
 * @ORM\DiscriminatorMap({
 *      "CHILD-CLASS1" = "ChildClassOne",
 *      "CHILD-CLASS2" = "ChildClassTwo",
 *      "CHILD-CLASS3" = "ChildClassThree",
 *      "CHILD-CLASS4" = "ChildClassFour"
 * })
 */
abstract class ParentClass
{
    ...
}

What I want to achieve is to display the discriminator in the browser with a little description that explains what is it to the user.
I googled for a solution like putting the discriminator in a joined table but found nothing.

Do you have any advice to achieve my goal ?

Thanks by advance for your help.

2

There are 2 answers

1
Cerad On BEST ANSWER

The discriminator column has special meaning for Doctrine 2 and thus cannot be part of a relation.

But there is an easy work around. Just add another column and give it the same value that your discriminator column has. The value will never change so it's easy enough to do. You can then of course use your new column in the same way as any other column.

I know having two columns with the same value is not ideal from a database perspective. But from an object perspective, it's no big deal since the discriminator column is never exposed as a property. And it's just the way doctrine works. It wants that column all to itself.

0
yvoyer On

You can achieve it using PHP, whitout adding another field in the db as long as you don't need the field in a SQL query.

Since the discriminator is an abstract class, just adding a public abstract method returning your hard-coded discriminator value would do the trick. Then you can use your entity in twig or a json serializer.

abstract class ParentClass {
    public abstract function getDiscriminator(): string; // The discriminator type
}

class ChildClassOne extends ParentClass
{
    public function getDiscriminator(): string 
    {
        return 'CHILD-CLASS1'; 
    }
}

If you need to fetch in SQL, use $qb->andWhere($qb->isInstanceOf(ChildClassOne::class)) since the method or discriminator attribute is not available in sql.