Использование параметров в классе внедрения зависимостей

Использование параметров в классе внедрения зависимостей

Вы уже видели, как использовать параметры конфигурации в сервис-контейнерах Symfony. Существуют специальные случаи, когда, например, вы хотите использовать параметр %kernel.debug%, чтобы заставить ваш пакет войти в режим отладки. Для такого случая нужно сделать больше работы, чтобы заставить систему понять значение параметра. По умолчаню, ваш параметр %kernel.debug% будет воспринят, как обычная строка. Рассмотрите следующий пример:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
// inside Configuration class
$rootNode
    ->children()
        ->booleanNode('logging')->defaultValue('%kernel.debug%')->end()
        // ...
    ->end()
;

// внутри класса Расширения
$config = $this->processConfiguration($configuration, $configs);
var_dump($config['logging']);

Теперь, рассмотрите результаты внимательнее, чтобы увидеть это:

  • YAML
     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    my_bundle:
        logging: true
        # true, as expected
    
    my_bundle:
        logging: '%kernel.debug%'
        # true/false (зависит от 2го параметра AppKernel),
        # как ожидается, так как %kernel.debug% внутри конфигурации
        # оценивается перед тем, как передаётся расширению
    
    my_bundle: ~
    # передаёт строку "%kernel.debug%".
    # Которая всегда считается true.
    # Конфигуратор не знает ничего о том, что
    # "%kernel.debug%" - это параметр.
    
  • XML
     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    <?xml version="1.0" encoding="UTF-8" ?>
    <container xmlns="http://symfony.com/schema/dic/services"
        xmlns:my-bundle="http://example.org/schema/dic/my_bundle">
    
        <my-bundle:config logging="true" />
        <!-- true, как ожидается -->
    
        <my-bundle:config logging="%kernel.debug%" />
        <!-- true/false (зависит от 2го параметра AppKernel),
             как ожидается, так как %kernel.debug% внутри конфигурации
             оценивается перед тем, как передаётся расширению -->
    
        <my-bundle:config />
        <!-- передаёт строку "%kernel.debug%".
             Которая всегда считается true.
             Конфигуратор не знает ничего о том, что
             "%kernel.debug%" - это параметр. -->
    </container>
    
  • PHP
     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    $container->loadFromExtension('my_bundle', array(
            'logging' => true,
            // true, как ожидается
        )
    );
    
    $container->loadFromExtension('my_bundle', array(
            'logging' => "%kernel.debug%",
            // true/false (зависит от 2го параметра AppKernel),
            // как ожидается, так как %kernel.debug% внутри конфигурации
            // оценивается перед тем, как передаётся расширению
        )
    );
    
    $container->loadFromExtension('my_bundle');
    // передаёт строку "%kernel.debug%".
    // Которая всегда считается true.
    // Конфигуратор не знает ничего о том, что
    // "%kernel.debug%" - это параметр.
    passes the string "%kernel.debug%".
    

Чтобы поддержать такой пример использования, класс Configuration должен быть внедрён с этим параметро через расширение, как показано далее:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
namespace AppBundle\DependencyInjection;

use Symfony\Component\Config\Definition\Builder\TreeBuilder;
use Symfony\Component\Config\Definition\ConfigurationInterface;

class Configuration implements ConfigurationInterface
{
    private $debug;

    public function  __construct($debug)
    {
        $this->debug = (bool) $debug;
    }

    public function getConfigTreeBuilder()
    {
        $treeBuilder = new TreeBuilder();
        $rootNode = $treeBuilder->root('my_bundle');

        $rootNode
            ->children()
                // ...
                ->booleanNode('logging')->defaultValue($this->debug)->end()
                // ...
            ->end()
        ;

        return $treeBuilder;
    }
}

И установите его в конструкторе Configuration через класс Extension:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
namespace AppBundle\DependencyInjection;

use Symfony\Component\DependencyInjection\ContainerBuilder;
use Symfony\Component\HttpKernel\DependencyInjection\Extension;

class AppExtension extends Extension
{
    // ...

    public function getConfiguration(array $config, ContainerBuilder $container)
    {
        return new Configuration($container->getParameter('kernel.debug'));
    }
}

Существуют пример использования %kernel.debug% в классе Configurator в TwigBundle и AsseticBundle. Однако это так потому, что значение параметра по умолчанию установлено классом Расширения (Extension). Например, в AsseticBundle, вы можете найти:

1
$container->setParameter('assetic.debug', $config['debug']);

Строка %kernel.debug% передаётся тут, так как аргумент выполняет работу переводчика для контейнера, который, в свою очередь, производит оценку. Оба способа достигают похожих целей. AsseticBundle не будет использовать %kernel.debug%, а скорее выберет новый параметр %assetic.debug%.

Эта документация является переводом официальной документации Symfony и предоставляется по свободной лицензии CC BY-SA 3.0.