SF 3.4 在服务中注入捆绑配置
SF 3.4 inject bundle config in services
使用 Symfony 3.4,我只是尝试一个新包的简单案例(名称:APiToolBundle
)。
这里是src/ApiToolBundle/Resources/config/config.yml
的内容:
imports:
- { resource: parameters.yml }
api_tool:
api_url: %myapi_url%
api_authorization_name: 'Bearer'
此文件由 ApiToolBundleExtension 加载:
public function load(array $configs, ContainerBuilder $container)
{
$configuration = new Configuration();
$config = $this->processConfiguration($configuration, $configs);
$loader = new Loader\YamlFileLoader($container, new FileLocator(__DIR__.'/../Resources/config'));
$loader->load('services.yml');
}
我也设置了配置文件:
class Configuration implements ConfigurationInterface
{
public function getConfigTreeBuilder()
{
$treeBuilder = new TreeBuilder();
$rootNode = $treeBuilder->root('production_tool');
$rootNode
->children()
->scalarNode('api_url')->defaultValue('')->end()
->scalarNode('api_authorization_name')->defaultValue('')->end()
->end()
;
return $treeBuilder;
}
}
但是我只想将配置参数绑定到我的一项服务:
# src/ApiToolBundle/Resources/config/services.yml
ApiToolBundle\Service\MyApi:
bind:
$apiUrl: '%api_tool.api_url%'
我基于此文档:https://symfony.com/doc/3.4/bundles/configuration.html
但我不确定是否理解所有内容,因为他们以其他方式谈论 mergin ...我是否需要做其他事情来加载我自己的 bundle 配置文件?
这确实有点棘手。捆绑包配置与您在服务配置中使用的参数不同(即使在您的配置中您也可以定义服务,起初看起来有点奇怪)。这也是为什么 Symfony 在版本 4 中不鼓励在应用程序内部使用语义配置,不使用 bundle & 配置,而是直接使用参数和服务的原因之一。
您需要将配置映射到参数或直接将它们注入到您需要它们的服务中,以防您不希望它们对其他服务公开可用或使用 getParameter
。您可以在您有权访问 ContainerBuilder 的扩展中执行此操作。
例如,请参阅 FrameworkExtension,其中您具有更改容器的大型配置:https://github.com/symfony/symfony/blob/v3.4.30/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/FrameworkExtension.php#L194-L196
在您的情况下,它可能看起来像这样:
public function load(array $configs, ContainerBuilder $container)
{
$configuration = new Configuration();
$config = $this->processConfiguration($configuration, $configs);
$loader = new Loader\YamlFileLoader($container, new FileLocator(__DIR__.'/../Resources/config'));
$loader->load('services.yml');
# Below is the new part, the rest is copied from your question
# If you only want to use the configuration values internally in your services:
$container->getDefinition('ApiToolBundle\Service\MyApi')->setArgument(
0 # Offset of the argument where you want to use the api url
$config['api_url']
);
# If you want to make the values publicly available as parameters:
$container->setParameter('api_tool.api_url', $config['api_url']);
}
使用 Symfony 3.4,我只是尝试一个新包的简单案例(名称:APiToolBundle
)。
这里是src/ApiToolBundle/Resources/config/config.yml
的内容:
imports:
- { resource: parameters.yml }
api_tool:
api_url: %myapi_url%
api_authorization_name: 'Bearer'
此文件由 ApiToolBundleExtension 加载:
public function load(array $configs, ContainerBuilder $container)
{
$configuration = new Configuration();
$config = $this->processConfiguration($configuration, $configs);
$loader = new Loader\YamlFileLoader($container, new FileLocator(__DIR__.'/../Resources/config'));
$loader->load('services.yml');
}
我也设置了配置文件:
class Configuration implements ConfigurationInterface
{
public function getConfigTreeBuilder()
{
$treeBuilder = new TreeBuilder();
$rootNode = $treeBuilder->root('production_tool');
$rootNode
->children()
->scalarNode('api_url')->defaultValue('')->end()
->scalarNode('api_authorization_name')->defaultValue('')->end()
->end()
;
return $treeBuilder;
}
}
但是我只想将配置参数绑定到我的一项服务:
# src/ApiToolBundle/Resources/config/services.yml
ApiToolBundle\Service\MyApi:
bind:
$apiUrl: '%api_tool.api_url%'
我基于此文档:https://symfony.com/doc/3.4/bundles/configuration.html
但我不确定是否理解所有内容,因为他们以其他方式谈论 mergin ...我是否需要做其他事情来加载我自己的 bundle 配置文件?
这确实有点棘手。捆绑包配置与您在服务配置中使用的参数不同(即使在您的配置中您也可以定义服务,起初看起来有点奇怪)。这也是为什么 Symfony 在版本 4 中不鼓励在应用程序内部使用语义配置,不使用 bundle & 配置,而是直接使用参数和服务的原因之一。
您需要将配置映射到参数或直接将它们注入到您需要它们的服务中,以防您不希望它们对其他服务公开可用或使用 getParameter
。您可以在您有权访问 ContainerBuilder 的扩展中执行此操作。
例如,请参阅 FrameworkExtension,其中您具有更改容器的大型配置:https://github.com/symfony/symfony/blob/v3.4.30/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/FrameworkExtension.php#L194-L196
在您的情况下,它可能看起来像这样:
public function load(array $configs, ContainerBuilder $container)
{
$configuration = new Configuration();
$config = $this->processConfiguration($configuration, $configs);
$loader = new Loader\YamlFileLoader($container, new FileLocator(__DIR__.'/../Resources/config'));
$loader->load('services.yml');
# Below is the new part, the rest is copied from your question
# If you only want to use the configuration values internally in your services:
$container->getDefinition('ApiToolBundle\Service\MyApi')->setArgument(
0 # Offset of the argument where you want to use the api url
$config['api_url']
);
# If you want to make the values publicly available as parameters:
$container->setParameter('api_tool.api_url', $config['api_url']);
}