Reputation: 120
Which is the best way to implement factory method.
1) A factory method that contain all members of the model to define
class UserFactory {
/**
* @return UserModel
*/
function create($firstName, $lastName, $age) {
$user = new UserModel();
$user->setFirstName($firstName);
$user->setLastName($firstName);
$user->setAge($age);
return $user;
}
}
// Usage example
$user = $userFactory->createUser('Yanik', 'Lupien', 99);
$userRepo->persist($user);
2) A factory method that simply create the model and return it. After we can fill the model by using the model setters.
class UserFactory {
/**
* @return UserModel
*/
function create() {
$user = new UserModel();
return $user;
}
}
// Usage example
$user = $userFactory->create();
$user->setFirstName('Yanik');
$user->setLastName('Lupien');
$user->setAge(99);
$userRepo->persist($user);
3) A Factory that return a different class implementation base on a param
class MyUserFactory {
const ADMIN = 'admin';
const SUPER_ADMIN = 'superadmin';
public function create($type = self::ADMIN)
{
switch ($type) {
case self::SUPER_ADMIN:
return new UserSuperAdmin($options);
break;
case self::ADMIN:
default:
return new UserAdmin($options);
break;
}
}
// Usage
$user = $myUserFactory->create(MyUserFactory::SUPER_ADMIN);
if ($user instanceof UserSuperAdmin) {
$user->setSuperAdminProperties();
}
if ($user instanceof UserAdmin) {
$user->setAdminProperties();
}
Upvotes: 1
Views: 228
Reputation: 9876
The way I've always seen the factory pattern applied is when there are multiple types of, say, users. For example, admin and superadmin. You could have a factory method like so:
// within a class named "User" for example
const ADMIN = 'admin';
const SUPER_ADMIN = 'superadmin';
// ...
public static function factory($type = 'admin')
{
switch ($type) {
case self::SUPER_ADMIN:
return new UserSuperAdmin();
break;
case self::ADMIN:
default:
return new UserAdmin();
break;
}
}
Both - or ANY for that matter - of the User classes would implement
some sort of interface that defines those getters and setters you were using like setFirstName()
and setAge()
for example.
You could also define an $options
array or something to pass along to each of their constructors to instantiate all of those fields right away for you.
public static function factory($type = 'admin', $options = array())
{
switch ($type) {
case self::SUPER_ADMIN:
return new UserSuperAdmin($options);
break;
case self::ADMIN:
default:
return new UserAdmin($options);
break;
}
}
Then, here is an example of one of the contructors:
class UserAdmin implements IUserInterface // for example
{
public function __construct($options)
{
// do something with the options array
}
}
Then when you instantiate it, it's as simple as something like this:
$user = User::factory('admin');
Upvotes: 3
Reputation: 883
You are the only person who can decide this. You should consider the following options:
Upvotes: 1