Потихоньку осваивая symfony 4 возникли недопонимания. Имеется абстрактный репозиторий в который inject-ица некий DriverManager объект-коннекшн к базе данных. От него отнаследованы конкретные репозитории, но в примере будет фигурировать один ConcreteRepository.
abstract class AbstractRepository {
public function __construct(DriverManager $dm) {
$this->driverManager = $dm;
}
}
class ConcreteRepository extends AbstractRepository {
public function save($object) {
// use DriverManage and save $object
}
}
Это использовалось примерно вот так(в console-команде как пример)
class ConcreteCommand extends Command {
public function __construct(ConcreteRepository $cr) {
$this->cr = $cr;
}
public function execute(InputInterface $input, OutputInterface $output) {
...
$result = $this->cr->save($object);
}
}
Далее возникла необходимость создать некую фабрику репозиториев и тут сталкиваюсь с проблемой. Мне нужно через все слои прокинуть DriverManager к конкретному репозиторию:
/**
*
*/
class RepositoryFactory {
public function __construct(DriverManager $dm) {
$this->dm = $dm;
}
public function create($type) {
if($type === 'concrete-repository') {
return new ConcreteRepository($this->dm);
}
}
}
/**
*
*/
class ConcreteCommand extends Command {
public function __construct(DriverManager $dm) {
$this->dm = $dm;
}
public function execute(InputInterface $input, OutputInterface $output) {
$repo = (new RepositoryFactory($this->dm))->create('concrete-repo');
}
}
Выглядит как-то странно, как можно избежать данной проблемы с прокидыванием DriverManager через все слои?
PS: По ряду причин доктрину использовать нет возможности.
А что мешает сделать прямо так:
public function execute(InputInterface $input, OutputInterface $output, RepositoryFactory $factory) {
$repo = $factory->create('concrete-repo');
}
я попробовал у себя только не на консольный команде а в контроллере:
/**
* Ваш первый вариант с прямым вызовов репозитория
* @Route("/concrete", name="concrete")
*/
public function concrete(ConcreteRepository $repo) {
$repo->save(['test']);
return new Response(
'<html><body>concrete</body></html>'
);
}
/**
* Через фабрику
* @Route("/factory", name="factory")
*/
public function factory(RepositoryFactory $factory) {
$repo = $factory->create('concrete-repository');
if ($repo) {
$repo->save(['test']);
}
return new Response(
'<html><body>factory</body></html>'
);
}
Собсно фабрика и классы репозиториев ваши:
namespace App\Repository;
use App\Service\DriverManager;
class RepositoryFactory {
/**
* @var DriverManager
*/
protected $dm;
public function __construct(DriverManager $dm) {
$this->dm = $dm;
}
public function create($type) {
if($type === 'concrete-repository') {
return new ConcreteRepository($this->dm);
}
throw new \Exception('Unknown type of Repo');
}
}
Репы
use App\Service\DriverManager;
class AbstractRepository {
/**
* @var DriverManager
*/
protected $driverManager;
public function __construct(DriverManager $driverManager) {
$this->driverManager = $driverManager;
}
}
namespace App\Repository;
class ConcreteRepository extends AbstractRepository {
public function save ($object) {
$this->driverManager->anythingDo($object);
}
}
и некий DriveManager
namespace App\Service;
class DriverManager {
public function __construct() {
}
public function anythingDo($object) {
echo self::class . ' anythingDo with: ' . print_r($object, true) . '<br>';
}
}
я сам только изучаю и стало любопытно
Виртуальный выделенный сервер (VDS) становится отличным выбором
Задача следующая - есть мапа, которая хранит в себе Id и связанный с ним список значений
Написал программуПрограмма выполняет все поставленные задачи, кроме одной, она должна выполнятся за 1 секунду, но выполняется за 4, подскажите,...
У меня такой вопрос, как разобрать json с неизвестным ключом? https://acxio//api/v2/tickers