Reputation: 207
im new to Doctrine and ORM in general.
I got 4 user types (Admin, Caretaker, Child, Personal). They all got some of the same columns (id, name, mail, password, created, type & group) and they got a few columns special to each of them (Caretaker has a child id etc.)
I'm not quite sure how i should map this. Like should i make my user types extend the User, giving the Child table the user columns, or what would be best practice here?
I assume the the option to use extend would force some more work when doing a login?
User.php
/**
* @MappedSuperclass
* @Entity @Table(name="users")
*/
class User
{
/**
* @Id @GeneratedValue @Column(type="integer")
* @var int
**/
protected $id;
/**
* @Column(type="string")
* @var string
**/
protected $name;
/**
* @Column(type="string")
* @var string
**/
protected $mail;
/**
* @Column(type="string")
* @var string
**/
protected $password;
/**
* @Column(type="datetime")
**/
protected $created;
/**
* @Column(type="datetime")
**/
protected $lastlogin;
/**
* @ManyToOne(targetEntity="Group")
* @JoinColumn(name="group_id", referencedColumnName="id")
*/
protected $group;
/**
* @ManyToOne(targetEntity="Type")
* @JoinColumn(name="type_id", referencedColumnName="id")
*/
protected $type;
public function __construct() {}
public function getId() { return $this->id; }
public function getName() { return $this->name; }
public function getMail() { return $this->mail; }
public function getCreated() { return $this->mail; }
public function getLastLogin() { return $this->lastlogin; }
public function getGroup() { return $this->group; }
public function getType() { return $this->type; }
public function setName($name) { $this->name = $name; }
public function setMail($mail) { $this->mail = $mail; }
public function setCreated() { $this->created = new DateTime("now"); }
public function setLastLogin() { $this->lastlogin = new DateTime("now"); }
public function setGroup($group) { $this->group = $group; }
public function setType($type) { $this->type = $type; }
}
Child.php
// src/Child.php
use Doctrine\Common\Collections\ArrayCollection;
/**
* @Entity @Table(name="child")
*/
class Child extends User
{
/**
* @Id @OneToOne(targetEntity="User")
* @JoinColumn(name="id", referencedColumnName="id")
**/
protected $id;
/**
* @Column(type="string")
*/
protected $image;
/**
* @ManyToMany(targetEntity="User")
* @JoinTable(name="child_Contacts",
* joinColumns={@JoinColumn(name="child_id", referencedColumnName="id")},
* inverseJoinColumns={@JoinColumn(name="contact_id", referencedColumnName="id")}
* )
*/
protected $currentContacts;
/**
* @OneToMany(targetEntity="Alarm", mappedBy="child")
*/
protected $alarms;
public function __construct()
{
$this->alarms = new ArrayCollection();
}
}
Upvotes: 2
Views: 915
Reputation: 185
You can easily solve this problem with doctrine and InheritanceType
mapping.
Basically, you can do something like this :
/**
* @MappedSuperclass
* @Entity @Table(name="users")
* @InheritanceType("JOINED")
* @DiscriminatorColumn(name="discr", type="string")
* @DiscriminatorMap({"Admin" = "Admin", "Caretaker" = "Caretaker", "Child" = "Child", "Personal" = "Personal"})
*/
class User
{
/**
* @Id @GeneratedValue @Column(type="integer")
* @var int
**/
protected $id;
/**
* @Column(type="string")
* @var string
**/
protected $name;
/**
* @Column(type="string")
* @var string
**/
protected $mail;
/**
* @Column(type="string")
* @var string
**/
protected $password;
/**
* @Column(type="datetime")
**/
protected $created;
/**
* @Column(type="datetime")
**/
protected $lastlogin;
/**
* @ManyToOne(targetEntity="Group")
* @JoinColumn(name="group_id", referencedColumnName="id")
*/
protected $group;
}
And then, in each 4 different classes,
// src/Child.php
use Doctrine\Common\Collections\ArrayCollection;
/**
* @Entity @Table(name="child")
*/
class Child extends User
{
/**
* @Id @OneToOne(targetEntity="User")
* @JoinColumn(name="id", referencedColumnName="id")
**/
protected $id;
/**
* @Column(type="string")
*/
protected $image;
/**
* @ManyToMany(targetEntity="User")
* @JoinTable(name="child_Contacts",
* joinColumns={@JoinColumn(name="child_id", referencedColumnName="id")},
* inverseJoinColumns={@JoinColumn(name="contact_id", referencedColumnName="id")}
* )
*/
protected $currentContacts;
/**
* @OneToMany(targetEntity="Alarm", mappedBy="child")
*/
protected $alarms;
public function __construct()
{
$this->alarms = new ArrayCollection();
}
}
The doctrine docs is really good for this problem : http://doctrine-orm.readthedocs.io/projects/doctrine-orm/en/latest/reference/inheritance-mapping.html
And you don't need an extra check at login because doctrine create automatically the right class for you.
Upvotes: 2