2012-09-01 4 views
20

Ich muss einige Konfigurationsparameter von meinem config.yml wie aktivierte Sprachen analysieren. Aber wenn ich versuche, das mit der normalen Symfony-Methode zu tun: $this->container->get('my_params'); schlägt es fehl, weil meine Admin-Klasse Sonata\AdminBundle\Admin\Admin Klasse erweitert, die die Symfony\Component\DependencyInjection\ContainerAware Klasse nicht erweitert.Wie erhält man eine Container-Instanz in der Sonaten-Admin-Klasse?

Bitte, Wie bekomme ich den Container in die Sonate Admin Klasse?

Jetzt behebe ich dieses Problem, indem ich die Sonate-Admin-Klasse überschreibe, damit die ContainerAware erweitert wird.

Antwort

45

wahrscheinlich schon gelöst, weil seine alten Frage, aber nur als Referenz ist der Container bereits ein vailable in Admin-Klasse, die die Konfiguration Pool mit ...

$this->getConfigurationPool()->getContainer(); 

Natürlich ist es besser, Praxis Dienstleistungen in der Admin-Klasse zu injizieren, sondern, wie in den Controllern. Warum sollte sich jemand Zeit nehmen, um die Setter-Injektion zu konfigurieren, wenn der Container bereits verfügbar ist?

1

In Ihrer speziellen Situation könnte es ratsam sein, eine benutzerdefinierte AdminController Klasse die Parameter Ihrer Admin Klasse zu setzen. Dies würde dem MVC-Muster entsprechen und Sie vor dem Ändern von Anbieterbündeln bewahren. Wenn Sie nicht wissen, wie Sie das tun, bitte aktualisieren Sie Ihre Frage und ich werde ausführlicher erklären.

+0

Ich habe dies gelöst, indem ich den Container selbst in meine Admin-Klasse injiziert habe, was ein schlechter Punkt ist. Ich habe die Setter-Injektion anstelle der Konstrukt-Injektion verwendet, weil das Konstrukt genau den gleichen Prototyp des Elternteils haben sollte. – skonsoft

2

Hier ist der beste Weg, Dienstleistungen in sonata Admin-Klassen zu verwenden:

einfach die benötigten Service-Injektion mit Setter injizieren. Konstruktorinjektionen sind in diesem Fall nicht zulässig, da Sie den Konstruktor der übergeordneten Klasse überschreiben müssten. Der Konstruktor der übergeordneten Klasse akzeptiert nur drei Parameter, sodass Sie keinen weiteren hinzufügen können.

Die Lösung lautet:

<!-- file: services.xml --> 

<service id="skonsoft.znata.admin.keyword" class="%skonsoft.znata.admin.keyword.class%"> 
      <tag name="sonata.admin" manager_type="orm" group="Keyword" label="Keyword"/> 
      <argument /> 
      <argument>%skonsoft.znata.admin.keyword.entity.class%</argument> 
      <argument>SonataAdminBundle:CRUD</argument> 
      <call method="setTranslationDomain"> 
       <argument>SkonsoftZnataBundle</argument> 
      </call> 

      <!-- here you inject needed services or parameters --> 
      <call method="setEnabledLocales"> 
       <argument>%skonsoft_znata.locales%</argument> 
      </call> 
     </service> 

Dann nur eine öffentliche Methode in Ihrer Admin-Klasse setEnabledLocales genannt hinzuzufügen.

/* file: MyclassAdmin.php */ 

public function setEnabledLocales($locales){ 
    $this->enabedLocales = $locales; 
} 

Werfen Sie einen Blick auf:

Service Container documentation

+0

Sie können Konstruktorinjektion verwenden, stellen Sie einfach sicher, dass Ihr Admin-Klassenkonstruktor '$ code',' $ class' und '$ baseControllerName' als die ersten drei Parameter und dann Ihre benutzerdefinierten Abhängigkeiten verwendet. Rufen Sie 'parent :: __ construct ($ code, $ class, $ baseControllerName)' auf. Deklarieren Sie schließlich Ihre benutzerdefinierten Abhängigkeiten unterhalb des bereits konfigurierten Abschnitts "arguments" in Ihren Diensten. [Yml | xml | whatever]. – orgasmix

14

Fügen Sie in Ihrem Admin-Klasse

/** @var \Symfony\Component\DependencyInjection\ContainerInterface */ 
private $container; 

public function setContainer (\Symfony\Component\DependencyInjection\ContainerInterface $container) { 
    $this->container = $container; 
} 

Und fügen Sie Anrufe in Dienste-Konfiguration (Konfiguration kann in YAML angegeben werden, XML oder PHP):

YAML

calls: 
    - [ setContainer, [ @service_container ] ] 

XML

<call method="setContainer"> 
    <argument type="service" id="service_container" /> 
</call> 

Jetzt können Sie die normale symfony-Methode: $this->container->get()

Weitere Informationen finden Sie Service Container Dokumentation

+0

Dies funktioniert möglicherweise nicht in einem benutzerdefinierten CRUD-Controller, da der Sonata-Administrator sich selbst zuweisen möchte. –

+0

Im Allgemeinen sollte diese Methode mit beliebigen Diensten funktionieren. siehe [DependencyInjection] (http://symfony.com/doc/master/components/dependency_injection/index.html) –