如何指定服务的参数。在Symfony文档之后,我通过将其添加到我的包中的config.yml文件中来创建自己的服务。
system_info_memory:
class: "%system_info.memory.class%"
arguments: ['enviroment']
这在我的控制器中完美地通过调用:
$service = $this->get('system_info_memory');
但是我没有看到如何动态地将参数设置为我的服务,上面只是静态地将字符串'environment'传递给类构造函数。但是,我希望传递的值为:
$this->container->get( 'kernel' )->getEnvironment()
从容器中获取类的实例之前。
有人可以帮忙吗?
答案 0 :(得分:1)
主要有两种类型的依赖注入。在Symfony中,我们还有一个额外的方法,我在这里解释了所有这些。
1-构造函数注入
此方法要求客户端在构造函数中提供参数 Symfony将通过在配置文件中定义服务参数来为您完成的服务。
saman.search:
class: Saman\SearchBundle\Services\SearchService
arguments:
- @translator
- @doctrine.orm.default_entity_manager
- %search_service_parameters%
在您的服务类中,您有:
<?php
namespace Library\Services;
use Doctrine\ORM\EntityManager;
use Symfony\Bundle\FrameworkBundle\Translation\Translator;
class SearchService
{
/**
* Translator services
*
* @var TranslatorService $translatorService
*/
protected $translatorService;
/**
*
* @var EntityManager $em
*/
protected $em;
/**
* Client side parameters
*
* @var array
*/
protected $parameters;
public function __construct(
TranslatorService $translatorService,
EntityManager $em,
array $parameters = array()
)
{
$this->translatorService = $translatorService;
$this->em = $em;
$this->parameters = $parameters;
}
public function doSomething()
{
return $this->translatorService->trans('app.text.hello');
}
}
?>
2-塞特尔注射
此方法要求您的服务为每个依赖项提供setter方法。 当您想要使用该服务时,您可以动态设置依赖关系。 这使您可以随时自由设置依赖。
saman.search:
class: Saman\SearchBundle\Services\SearchService
arguments:
- @translator
- @doctrine.orm.default_entity_manager
- %search_service_parameters%
saman.a:
class: Saman\SearchBundle\Services\A
arguments: ~
在您的服务中,您有:
<?php
namespace Library\Services;
use Doctrine\ORM\EntityManager;
use Symfony\Bundle\FrameworkBundle\Translation\Translator;
use Library\Services\A;
class SearchService
{
/**
* Translator services
*
* @var TranslatorService $translatorService
*/
protected $translatorService;
/**
*
* @var EntityManager $em
*/
protected $em;
/**
* Service A
* @var A $a
*/
protected $a;
/**
* Client side parameters
*
* @var array
*/
protected $parameters;
public function __construct(
TranslatorService $translatorService,
EntityManager $em,
array $parameters = array()
)
{
$this->translatorService = $translatorService;
$this->em = $em;
$this->parameters = $parameters;
}
public function setServiceA(A $a)
{
$this->a = $a;
return $this;
}
public function doSomethingNeedServiceA()
{
return $this->getServiceA()->doSomethingInA();
}
private function getServiceA()
{
if (null === $this->a) {
throw new \LogicException("You should set service A first");
}
return $this->a;
}
}
?>
使用接口
也可以改善这一点<?php
namespace Library\Services;
use Doctrine\ORM\EntityManager;
use Symfony\Bundle\FrameworkBundle\Translation\Translator;
use Library\Interfaces\A;
class SearchService
{
/**
* Translator services
*
* @var TranslatorService $translatorService
*/
protected $translatorService;
/**
*
* @var EntityManager $em
*/
protected $em;
/**
* Interfaces A
* @var A $a
*/
protected $a;
/**
* Client side parameters
*
* @var array
*/
protected $parameters;
public function __construct(
TranslatorService $translatorService,
EntityManager $em,
array $parameters = array()
)
{
$this->translatorService = $translatorService;
$this->em = $em;
$this->parameters = $parameters;
}
public function setServiceA(A $a)
{
$this->a = $a;
return $this;
}
public function doSomethingNeedServiceA()
{
return $this->getServiceA()->doSomethingInA();
}
private function getServiceA()
{
if (null === $this->a) {
throw new \LogicException("You should set a service that implement A interfaces");
}
return $this->a;
}
}
?>
和您的界面
<?php
namespace Library\Interfaces;
interface A
{
public function doSomethingInA();
}
?>
然后,当您想要使用此服务时,您应该
$aService = $this->get('saman.a');
$searchService = $this->get('saman.search');
$searchService->setServiceA($aService)
->doSomethingNeedServiceA();
3标记服务
在Symfony中,有一种方法可以在另一个服务中注册服务,使用配置标记Working with Tagged Services
我已经实现了这种方法,它非常好,但它很大。如果有人需要实施,我很乐意听到。
答案 1 :(得分:0)
您可以注入kernel.environment
参数:
services:
system_info_memory:
class: %system_info.memory.class%
arguments: [ %kernel.environment% ]