php - Symfony - Get a container inside an Interface
one text
Solution:
As mentioned in my comment, you should utilize dependency injection to add only the services you need instead of the entire container.
Be sure to clear and warmup your Symfony cache after making the changes below.
autowire services
In Symfony 3.4+ you can utilize autowire
, which will automatically inject known FQCN services into the __construct
for example using the logger service.
vendor/symfony/monolog-bundle/Resources/config/monolog.xml
<?xml version="1.0" ?>
<container xmlns="http://symfony.com/schema/dic/services"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://symfony.com/schema/dic/services http://symfony.com/schema/dic/services/services-1.0.xsd">
<services>
<service id="monolog.logger" parent="monolog.logger_prototype" public="false">
<argument index="0">app</argument>
<call method="useMicrosecondTimestamps">
<argument>%monolog.use_microseconds%</argument>
</call>
</service>
<service id="logger" alias="monolog.logger" />
<service id="Psr\Log\LoggerInterface" alias="logger" public="false" />
<!-- ... -->
</service>
</services>
</container>
config/services.xml
<?xml version="1.0" ?>
<container xmlns="http://symfony.com/schema/dic/services"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://symfony.com/schema/dic/services http://symfony.com/schema/dic/services/services-1.0.xsd">
<services>
<!-- attempts to inject and tag services automatically -->
<defaults autowire="true" autoconfigure="true" public="false"/>
<service id="RegistrationExtension\Storefront\Controller\RegistrationExtensionController" public="true"> </service>
<service id="RegistrationExtension\Subscriber\RegisterExtensionSubscriber">
<tag name="kernel.event_subscriber"/>
</service>
</services>
</container>
src/RegistrationExtension/Subscriber/RegisterExtensionSubscriber.php
use Psr\Log\LoggerInterface;
class RegisterExtensionSubscriber implements EventSubscriberInterface
{
private $logger;
public function __construct(LoggerInterface $logger)
{
$this->logger = $logger;
}
}
Dependency Injection
If the service can not use autowire
to be injected because it uses a string service name instead of FQCN you can manually declare the service in your config.
config/services.xml
<?xml version="1.0" ?>
<container xmlns="http://symfony.com/schema/dic/services"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://symfony.com/schema/dic/services http://symfony.com/schema/dic/services/services-1.0.xsd">
<services>
<service id="RegistrationExtension\Storefront\Controller\RegistrationExtensionController" public="true"> </service>
<service id="RegistrationExtension\Subscriber\RegisterExtensionSubscriber">
<argument type="service" id="mail_template_type.repository" />
<argument type="service" id="mail_template.repository" />
<tag name="kernel.event_subscriber"/>
</service>
</services>
</container>
src/RegistrationExtension/Subscriber/RegisterExtensionSubscriber.php
use Shopware\Core\Framework\DataAbstractionLayer\EntityRepositoryInterface;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
//...
class RegisterExtensionSubscriber implements EventSubscriberInterface
{
/**
* @var EntityRepositoryInterface
*/
private $mailTypeRepository;
/**
* @var EntityRepositoryInterface
*/
private $mailRepository;
public function __construct(
EntityRepositoryInterface $mailTypeRepository,
EntityRepositoryInterface $mailRepository
) {
$this->mailTypeRepository = $mailTypeRepository;
$this->mailRepository = $mailRepository;
}
public function onCustomRegister(AccountLoginPageLoadedEvent $event)
{
$mailEntity = $this->mailTypeRepository->search(
(new Criteria())->addFilter(new EqualsFilter('mail_template_type.technicalName', "customer_register")),
$event->getContext()
);
if ($mailType = $mailEntity->getEntities()->first()) {
$mailEntity = $this->mailRepository->search(
(new Criteria())->addFilter(new EqualsFilter('mail_template.mailTemplateTypeId', $mailType->getId())),
$event->getContext()
);
$mail = $mailEntity->getEntities();
//...
}
}
}
Source