2011-01-27 12 views
179

he añadido una opción para mi archivo config.yml como tal:¿Cómo leo la configuración de Symfony2 config.yml?

app.config: 
    contact_email: [email protected] 
    ... 

Para la vida de mí, no puedo encontrar la manera de leer en una variable. He intentado algo como esto en uno de mis controladores:

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

Pero consigo un error diciendo:

El parámetro "contact_email" debe ser definido .

He borrado mi caché, también busqué en todos lados en la documentación del sitio recargo Symfony2, pero no puedo encontrar la manera de hacerlo.

Probablemente estoy demasiado cansado para resolver esto ahora. ¿Alguien puede ayudarme con esto?

Respuesta

190

En lugar de definir contact_email dentro app.config, definirlo en una entrada de parameters:

parameters: 
    contact_email: [email protected] 

que debe encontrar la llamada que está realizando dentro de su controlador ahora trabaja.

+4

¿Cómo funcionaría esto con los entornos Dev/Prod? Entonces para probar quiero que los correos electrónicos se envíen a un correo electrónico de prueba y la producción reciba otro correo electrónico –

+2

@Phill: Si está utilizando el swiftmailer estándar en su symfony2, puede usar la siguiente configuración en su config_dev.yml: 'swiftmailer: delivery_address: dev @ example.com' Puede encontrar más información en el [Symfony2 cookbook] (http://symfony.com/doc/current/cookbook/email/dev_environment.html) – Pierre

+4

Debería inyectar una clase de contenedor en todas partes (controlador, entidad, clase) cuando uso esta declaración ** $ this-> container-> getParameter ('contact_email'); **? o hay una manera más simple de hacerlo sin inyectar clase de contenedor? – webblover

33

tengo que añadir a la respuesta de Douglas, puede acceder a la configuración global, pero Symfony traduce algunos parámetros, por ejemplo:

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

son

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

Usted puede utilizar var_dump a busca una clave o valor especificado.

+0

simple y fácil! gracias – Cowwando

17

Para poder exponer algunos parámetros de configuración para su paquete, debe consultar la documentación para hacerlo. Es bastante fácil de hacer :)

Aquí está el enlace: How to expose a Semantic Configuration for a Bundle

+0

Honestamente, esta pregunta fue hecha hace más de 2 años, en aquel entonces, el artículo anterior no existía. –

+10

Estoy de acuerdo con esa afirmación. He establecido la respuesta en caso de que alguien abra este artículo hoy en día. Gracias por la calificación negativa. Hiciste mi día. –

+0

Mis disculpas, ahora que lo pienso, mi voto fue innecesario. Aprecio tu contribución, intenté votarte pero SO ya no lo permite. El enlace es de lo más útil, y estoy seguro de que otras personas se beneficiarán de ello. Tal vez el administrador puede ayudar a cambiar mi voto negativo? –

154

Mientras que la solución de mover el contact_email a parameters.yml es fácil, tal como se propone en otras respuestas, que pueden Clutter fácilmente los parámetros del archivo si usted trata con muchos paquetes o si se trata de bloques de configuración anidados.

  • En primer lugar, voy a responder estrictamente a la pregunta.
  • Más adelante, daré un enfoque para obtener esas configuraciones de los servicios sin pasar por un espacio común como parámetros.

primera aproximación: bloque de configuración Separado, obteniendo como parámetro

Con una extensión (more on extensions here) se puede mantener esto fácilmente "separados" en diferentes bloques en el config.yml y luego inyectar que, como parámetro gettable desde el controlador.

Dentro de la clase de extensión dentro del directorio DependencyInjection escribir esto:

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 
    } 

Luego, en su config.yml, config_dev.yml y por lo tanto se puede establecer

my_nice_project: 
    contact_email: [email protected] 

Para poder procesar esa config.yml dentro de su MyNiceBundleExtension también necesitará una clase Configuration en el mismo espacio de nombres:

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

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

     return $treeBuilder; 
    } 
} 

entonces se puede obtener la configuración de su controlador, como usted desee en su pregunta original, pero manteniendo el parameters.yml limpio, y se establece en el config.yml en secciones separadas:

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

segundo enfoque: Separado config block, inyectando la configuración en un servicio

Para lectores que buscan algo similar, pero para obtener la configuración de un servicio, hay incluso una manera más agradable que nunca ocupa el espacio común de "parámetros" e incluso no necesita el container para pasar al servicio (pasar el contenedor entero es una práctica para evitar).

Este truco anterior todavía "inyecta" en los parámetros de espacio de su configuración.

Sin embargo, después de cargar su definición del servicio, puede agregar una llamada a un método como por ejemplo setConfig() que inyecta ese bloque solo al servicio.

Por ejemplo, en la clase Extensión:

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' ])); 
    } 
} 

Luego, en su services.yml a definir su servicio como de costumbre, sin ningún cambio absoluto:

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

Y luego en su clase SillyManager, justo agregue el método:

class SillyManager 
{ 
    private $contact_email; 

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

Nota tha ¡Esto también funciona para matrices en lugar de valores escalares!Imagínese que configure una cola de conejo y necesita anfitrión, usuario y contraseña:

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

Por supuesto que necesita para cambiar su árbol, pero luego se puede hacer:

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

y luego en el servicio de hacer :

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

    public function setConfig($config) 
    { 
     $this->host = $config[ 'host' ]; 
     $this->user = $config[ 'user' ]; 
     $this->password = $config[ 'password' ]; 
    } 
} 

Espero que ayude!

+9

¡Excelente! Gracias por la respuesta detallada. – Jekis

+12

¡Esta debería haber sido la respuesta! – nicom974

+0

Si se pregunta qué hay de diferente entre el primer enfoque y la documentación, es que los valores de configuración se convierten en parámetros en el método 'MyNiceProjectExtension-> load()' con esta línea: '$ container-> setParameter ('my_nice_project. contact_email ', $ processedConfig [' contact_email ']); '. Gracias Xavi! – jxmallett

2

aprendí una manera fácil de ejemplo de código de http://tutorial.symblog.co.uk/

1) cuenta de la ZendeskBlueFormBundle y el archivo de ubicación

# myproject/app/config/config.yml 

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

framework: 

2) notar Zendesk_BlueForm.emails.contact_email y ubicación del archivo

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

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

3) observe cómo lo obtengo en $ cliente y la ubicación del archivo del controlador

# 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")); 
    ... 
    } 
Cuestiones relacionadas