Jak odczytać ustawienia konfiguracyjne z konfiguracji Symfony2.yml?

Dodałem ustawienie do mojego config.plik yml jako taki:

app.config:
    contact_email: [email protected]
    ...
Nie wiem, jak to odczytać w zmiennej. Próbowałem czegoś takiego w jednym z moich kontrolerów:
$recipient =
$this->container->getParameter('contact_email');

Ale dostaję błąd mówiąc:

Parametr "contact_email" musi być zdefiniowany.

Wyczyściłem swoją pamięć podręczną, Szukałem też wszędzie dokumentacji Symfony2 reloaded site, ale nie mogę się dowiedzieć, jak to zrobić.

Prawdopodobnie zbyt jestem zmęczony, żeby to rozgryźć. Czy ktoś może w tym pomóc?

Author: nbro, 2011-01-27

6 answers

Zamiast definiować contact_email wewnątrz app.config, zdefiniuj go w pozycji parameters:

parameters:
    contact_email: [email protected]

Powinieneś znaleźć połączenie, które wykonujesz w swoim kontrolerze, teraz działa.

 191
Author: Douglas Greenshields,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-01-30 20:45:33

Podczas gdy rozwiązanie przeniesienia contact_email do parameters.yml jest łatwe, jak zaproponowano w innych odpowiedziach, które mogą łatwo zaśmiecać plik parametrów, jeśli masz do czynienia z wieloma pakietami lub jeśli masz do czynienia z zagnieżdżonymi blokami konfiguracji.

  • Po pierwsze, odpowiem ściśle na pytanie.
  • później podam podejście do pobierania tych configów z usług bez przechodzenia przez wspólną przestrzeń jako parametry.

Pierwsze podejście: oddzielony blok config, uzyskanie go jako parametr

Z rozszerzeniem (więcej o rozszerzeniach tutaj) można łatwo " rozdzielić "na różne bloki w config.yml, a następnie wprowadzić to jako parametr gettable z kontrolera.

Wewnątrz twojej klasy rozszerzeń wewnątrz katalogu DependencyInjection napisz to:

class MyNiceProjectExtension extends Extension
{
    public function load( array $configs, ContainerBuilder $container )
    {
        // The next 2 lines are pretty common to all Extension templates.
        $configuration = new Configuration();
        $processedConfig = $this->processConfiguration( $configuration, $configs );

        // This is the KEY TO YOUR ANSWER
        $container->setParameter( 'my_nice_project.contact_email', $processedConfig[ 'contact_email' ] );

        // Other stuff like loading services.yml
    }

Następnie w konfiguracji.yml, config_dev.yml i tak można ustawić

my_nice_project:
    contact_email: [email protected]

Aby móc przetworzyć to config.yml wewnątrz twojego MyNiceBundleExtension będziesz potrzebował również Configuration klasy w ta sama przestrzeń nazw:

class Configuration implements ConfigurationInterface
{
    public function getConfigTreeBuilder()
    {
        $treeBuilder = new TreeBuilder();
        $rootNode = $treeBuilder->root( 'my_nice_project' );

        $rootNode->children()->scalarNode( 'contact_email' )->end();

        return $treeBuilder;
    }
}

Następnie możesz pobrać konfigurację z kontrolera, zgodnie z życzeniem w oryginalnym pytaniu, ale zachowując parameters.yml w czystości i ustawiając ją w config.yml w oddzielnych sekcjach:

$recipient = $this->container->getParameter( 'my_nice_project.contact_email' );

Druga metoda: oddzielony blok konfiguracyjny, wstrzyknięcie konfiguracji do usługi

Dla czytelników szukających czegoś podobnego, ale dla uzyskania config z serwisu, jest jeszcze ładniejszy sposób, który nigdy nie zaśmieca wspólnej przestrzeni "paramaterów" i nawet nie wymaga przekazania container do serwisu (przejście całego kontenera jest praktyką, aby tego uniknąć).

Powyższa sztuczka nadal "wstrzykuje" do przestrzeni parametrów twojego config.

Niemniej jednak, po załadowaniu definicji usługi, możesz dodać wywołanie metody, takie jak na przykład setConfig(), które wstrzykuje ten blok tylko do usługi.

Na przykład w klasie Extension:

class MyNiceProjectExtension extends Extension
{
    public function load( array $configs, ContainerBuilder $container )
    {
        $configuration = new Configuration();
        $processedConfig = $this->processConfiguration( $configuration, $configs );

        // Do not add a paramater now, just continue reading the services.
        $loader = new YamlFileLoader( $container, new FileLocator( __DIR__ . '/../Resources/config' ) );
        $loader->load( 'services.yml' );

        // Once the services definition are read, get your service and add a method call to setConfig()
        $sillyServiceDefintion = $container->getDefinition( 'my.niceproject.sillymanager' );
        $sillyServiceDefintion->addMethodCall( 'setConfig', array( $processedConfig[ 'contact_email' ] ) );
    }
}

Potem w Twoim services.yml zdefiniujesz swoją służbę jak zwykle, bez żadnej bezwzględnej zmiany:

services:
    my.niceproject.sillymanager:
        class: My\NiceProjectBundle\Model\SillyManager
        arguments: []

A następnie w klasie SillyManager wystarczy dodać metodę:

class SillyManager
{
    private $contact_email;

    public function setConfig( $newConfigContactEmail )
    {
        $this->contact_email = $newConfigContactEmail;
    }
}

Zauważ, że działa to również dla tablic zamiast wartości skalarnych! Wyobraź sobie, że skonfigurujesz kolejkę królików i potrzebujesz hosta, użytkownika i hasła: {]}

my_nice_project:
    amqp:
        host: 192.168.33.55
        user: guest
        password: guest

Oczywiście musisz zmienić swoje drzewo, ale wtedy możesz to zrobić:

$sillyServiceDefintion->addMethodCall( 'setConfig', array( $processedConfig[ 'amqp' ] ) );

A następnie w Serwisie do:

class SillyManager
{
    private $host;
    private $user;
    private $password;

    public function setConfig( $config )
    {
        $this->host = $config[ 'host' ];
        $this->user = $config[ 'user' ];
        $this->password = $config[ 'password' ];
    }
}
Mam nadzieję, że to pomoże!
 163
Author: Xavi Montero,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-11-10 23:56:39

Muszę dodać do odpowiedzi Douglasa, można uzyskać dostęp do globalnej konfiguracji, ale symfony tłumaczy niektóre parametry, na przykład:

# config.yml
... 
framework:
    session:
        domain: 'localhost'
...

$this->container->parameters['session.storage.options']['domain'];

Możesz użyć var_dump, aby wyszukać określony klucz lub wartość.

 34
Author: Felipe Buccioni,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-08-07 22:13:22

Aby móc ujawnić niektóre parametry konfiguracyjne pakietu, należy zapoznać się z dokumentacją w tym celu. To dość łatwe do zrobienia:)

Oto link: jak wyeksponować konfigurację semantyczną dla pakietu

 17
Author: Nikola Petkanski,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-04-15 12:37:57

Tak jak mówiono wcześniej - możesz uzyskać dostęp do dowolnych parametrów za pomocą kontenera wtryskowego i użyć jego właściwości parametru.

"Symfony-Working with Container Service Definitions" to dobry artykuł na ten temat.

 7
Author: Paul Paca-Vaca Seleznev,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-05-25 19:06:18

I learned a easy way from code example of http://tutorial.symblog.co.uk/

1) zwróć uwagę na ZendeskBlueFormBundle i lokalizację pliku

# myproject/app/config/config.yml

imports:
    - { resource: parameters.yml }
    - { resource: security.yml }
    - { resource: @ZendeskBlueFormBundle/Resources/config/config.yml }

framework:

2) zwróć uwagę na Zendesk_BlueForm.e-maile.contact_email and file location

# myproject/src/Zendesk/BlueFormBundle/Resources/config/config.yml

parameters:
    # Zendesk contact email address
    Zendesk_BlueForm.emails.contact_email: [email protected]

3) zauważ jak dostaję to w $ client i lokalizacji pliku kontrolera

# myproject/src/Zendesk/BlueFormBundle/Controller/PageController.php

    public function blueFormAction($name, $arg1, $arg2, $arg3, Request $request)
    {
    $client = new ZendeskAPI($this->container->getParameter("Zendesk_BlueForm.emails.contact_email"));
    ...
    }
 3
Author: Dung,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-11-16 02:29:11