vendredi 27 mars 2020

Repository + factory pattern implementation for classes with multiple inheritance in PHP?

Here is the case: let's say I have a User abstract class. This class is extended into Employee and Customer subclasses.

The User class has basic attributes like name and address. Employee has an additional attribute sallary. Customer has an additional attribute membership_code.

These entities are stored in multiple tables: users, employees, and customers. The users table contains basic information about any user. The employees and customers table refer to the users table, and in each contains the additional attributes.

users table:

id | name       | address           | type
---+------------+-------------------+---------
1  | Employee 1 | First Address St. | Employee
2  | Customer 1 | First Address St. | Customer

employees table:

user_id | salary
--------+---------
1       | 5000

customers table:

user_id | membership_code
--------+---------
2       | 1325_5523_2351

Here is what I have in mind as to how these should be implemented in PHP:

abstract class User
{
    protected $id;
    protected $name;

    public static function load(int $id): User
    {
        /** @var array $data */
        $data = get_a_row_from_users_table_by($id); // this part does a query to DB

        return new $data['type']($data['id'], $data['name']);
    }

    final public function __construct($id, $name)
    {
        $this->id = $id;
        $this->name = $name;
        $this->init();
    }

    abstract protected function init();
}

class Employee extends User
{
    protected $salary;

    protected function init()
    {
        /** @var array $data */
        $data = get_a_row_from_employees_table_by($this->id); // this part does a query to DB
        $this->salary = $data['salary'];
    }
}

class Customer extends User
{
    protected $membership_code;

    protected function init()
    {
        /** @var array $data */
        $data = get_a_row_from_customers_table_by($this->id); // this part does a query to DB
        $this->salary = $data['membership_code'];
    }
}

However, I feel like the code above still seems a bit hacky to maintain. Recently I read a book discussing about domain-driven design and how the persistence mechanism should be separated into a Repository. On the other hand, I also discovered that the type-switching mechanism, for example between Employee and Customer, should be done in a Factory.

I have a bit of a grasp to the concepts of Repository and Factory, but I still failed to understand how to combine and implement those concepts into a working code.

In this case, how should the above be implemented to use Repository and Factory pattern in PHP?

Aucun commentaire:

Enregistrer un commentaire