#ReflectionClassを使ってオブジェクトを注入
サンプルとして、UserServiceにReflectionClassを使ってUserRepositoryを注入します。
##サンプルクラス
UserService.php
class UserService
{
/**
* @var UserRepository
*/
private $repo;
/**
* UserService constructor.
* @param UserRepository $repo
*/
public function __construct(UserRepository $repo)
{
$this->repo = $repo;
}
/**
* @return User
*/
public function getUser()
{
return $this->repo->getUser();
}
}
UserRepository.php
class UserRepository
{
/**
* @return User
*/
public function getUser()
{
// サンプルなので直接生成して返す
return new User('User Name');
}
}
User.php
class User
{
/**
* @var string
*/
private $name;
/**
* User constructor.
* @param $name
*/
public function __construct($name)
{
$this->name = $name;
}
/**
* @return string
*/
public function getName()
{
return $this->name;
}
}
実際にやってみる
main.php
#ReflectionClass生成
$reflection = new \ReflectionClass(UserService::class);
$args = [];
# コンストラクタが定義されているか
if ($reflection->hasMethod('__construct')) {
/**
* コンストラクタの引数取得
*
* @var \ReflectionParameter[] $parameters
*/
$parameters = $reflection->getConstructor()->getParameters();
# 引数に指定されているオブジェクトの生成
$args = array_reduce($parameters, function ($args, $parameter) {
/**
* 引数に指定されているClassの取得して生成する
*
* @var \ReflectionClass $parameterClass
*/
if ($reflectionClass = $parameter->getClass()) {
$className = $reflectionClass->getName();
$args[$parameter->getName()] = new $className;
}
return $args;
}, []);
}
/**
* ReflectionClassを使用してUserServiceを生成
*
* @var UserService $userService
*/
$userService = $reflection->newInstanceArgs($args);
$user = $userService->getUser();
var_dump($user->getName());
// string(9) "User Name"
今回は簡単なサンプルですがもうちょっとちゃんとしたのをGitHubに置いてみました!