symfony-サービスコンテナ

どのアプリケーションでも、オブジェクトはアプリケーションの成長とともに増加する傾向があります。オブジェクトが増えると、オブジェクト間の依存関係も増えます。アプリケーションを成功させるには、オブジェクトの依存関係を適切に処理する必要があります。

コンポーネントの章で説明したように、Symfonyは簡単で効率的なコンポーネントを提供します。 DependencyInjectionオブジェクトの依存関係を処理します。サービスコンテナは、オブジェクト間の依存関係が適切に解決されたオブジェクトのコンテナです。この章では、DependencyInjectionコンポーネントの使用方法を学びましょう。

作成しましょう Greeterクラス。Greeterクラスの目的は、次の例に示すようにユーザーに挨拶することです。

$greeter = new Greeter('Hi'); 
$greeter->greet('Jon'); // print "Hi, Jon"

Greeterクラスの完全なコードは次のとおりです。

class Greeter { 
   private $greetingText; 
   
   public function __construct($greetingText) { 
      $this->greetingText = $greetingText; 
   }  
   public function greet($name) { 
      echo $this->greetingText . ", " . $name . "\r\n"; 
   } 
}

それでは、Greeterクラスをサービスコンテナに追加しましょう。symfonyは提供しますContainerBuilder新しいコンテナを作成します。コンテナが作成されると、コンテナのregisterメソッドを使用してGreeterクラスをコンテナに登録できます。

use Symfony\Component\DependencyInjection\ContainerBuilder; 
$container = new ContainerBuilder(); 
$container 
   ->register('greeter', 'Greeter') 
   ->addArgument('Hi');

ここでは、静的引数を使用して挨拶テキストHiを指定しました。symfonyはパラメータの動的設定も提供します。動的パラメーターを使用するには、名前を選択して%の間で指定する必要があり、パラメーターはコンテナーを使用して設定できます。setParameter 方法。

$container = new ContainerBuilder(); 
$container 
   ->register('greeter', 'Greeter') 
   ->addArgument('%greeter.text%');  
$container->setParameter('greeter.text', 'Hi');

適切な設定でGreeterクラスを登録しました。これで、コンテナーを使用して適切に構成されたGreeterオブジェクトを提供するようにコンテナーに要求できます。get 方法。

$greeter = $container->get('greeter'); 
$greeter->greet('Jon'); // prints "Hi, Jon"

クラスGreeterをコンテナに正常に登録し、コンテナからフェッチして使用しました。それでは、別のクラスを作成しましょうUser、Greeterクラスを使用し、登録方法を確認します。

class User { 
   private $greeter;  
   public $name; 
   public $age;  
   
   public function setGreeter(\Greeter $greeter) { 
      $this->greeter = $greeter; 
   }  
   public function greet() { 
      $this->greeter->greet($this->name); 
   } 
}

Userクラスは、setterメソッドの1つを使用してGreeterクラスを取得します。setGreeter。このシナリオでは、Symfonyはメソッドを提供します。addMethodCall とクラス、 Reference 次のコードに示すように、別のクラスを参照します。

use Symfony\Component\DependencyInjection\Reference;  
$container 
   ->register('user', 'User') 
   ->addMethodCall('setGreeter', array(new Reference('greeter')));

最後に、2つのクラスを登録しました。 Greeter そして Userそれらの間に強い関係を持っています。これで、次のコードに示すように、適切に構成されたGreeterクラスを使用してUserオブジェクトをコンテナーから安全にフェッチできます。

$container->setParameter('greeter.text', 'Hi'); 
$user = $container->get('user'); 
$user->name = "Jon"; 
$user->age = 20; 
$user->greet(); // Prints "Hi, Jon"

PHP自体を使用してコンテナ内のオブジェクトを構成する方法を見てきました。symfonyは他のメカニズムも提供します。それらはXMLおよびYAML構成ファイルです。YAMLを使用してコンテナーを構成する方法を見てみましょう。このために、インストールしますsymfony/config そして symfony/yaml コンポーネントと一緒に symfony/dependency-injection コンポーネント。

cd /path/to/dir 
mkdir dependency-injection-example 
cd dependency-injection-example 
composer require symfony/dependency-injection 
composer require symfony/config 
composer require symfony/yaml

YAML構成は別のファイルに書き込まれます。 services.yml。YAML構成は2つのセクションで構成されています。parameters そして services。パラメータセクションでは、必要なすべてのパラメータを定義します。サービスセクションはすべてのオブジェクトを定義します。サービスセクションはさらに複数のセクションに分かれています。class, arguments, そして calls。Classは、実際のクラスを指定します。Argumentsは、コンストラクターの引数を指定します。最後に、呼び出しはsetterメソッドを指定します。@記号、@ greeterを使用して別のクラスを参照できます。

parameters: 
   greeter.text: 'Hello' 
services: 
   greeter: 
      class: Greeter
      arguments: ['%greeter.text%'] 
   user: 
      class: User 
      calls: 
         - [setGreeter, ['@greeter']]

さて、 services.yml を使用してロードおよび構成できます FileLoader そして YamlFileLoader 次のコードに示すように。

use Symfony\Component\Config\FileLocator; 
use Symfony\Component\DependencyInjection\Loader\YamlFileLoader;  

$yamlContainer = new ContainerBuilder(); 
$loader = new YamlFileLoader($yamlContainer, new FileLocator(__DIR__)); 
$loader->load('services.yml');  

$yamlUser = $yamlContainer->get('user'); 
$yamlUser->name = "Jon"; 
$yamlUser->age = 25; 
$yamlUser->greet();

完全なコードリストは次のとおりです。

main.php

<?php  
   require __DIR__ . '/vendor/autoload.php';  
   use Symfony\Component\DependencyInjection\ContainerBuilder; 
   use Symfony\Component\Config\FileLocator; 
   use Symfony\Component\DependencyInjection\Loader\YamlFileLoader; 
   use Symfony\Component\DependencyInjection\Reference;  
   
   class Greeter { 
      private $greetingText; 
      
      public function __construct($greetingText) {
         $this->greetingText = $greetingText; 
      }  
      public function greet($name) { 
         echo $this->greetingText . ", " . $name . "\r\n"; 
      } 
   }  
   class User { 
      private $greeter;  
      public $name; 
      public $age;  
      
      public function setGreeter(\Greeter $greeter) { 
         $this->greeter = $greeter; 
      }  
      public function greet() { 
         $this->greeter->greet($this->name); 
      } 
   }  
   $container = new ContainerBuilder(); 
   $container 
      ->register('greeter', 'Greeter') 
      ->addArgument('%greeter.text%');  
   $container 
      ->register('user', 'User') 
      ->addMethodCall('setGreeter', array(new Reference('greeter')));
   
   $container->setParameter('greeter.text', 'Hi'); 
   $greeter = $container->get('greeter'); 
   $greeter->greet('Jon'); 
   
   $user = $container->get('user'); 
   $user->name = "Jon"; 
   $user->age = 20; 
   $user->greet();  
   
   $yamlContainer = new ContainerBuilder(); 
   $loader = new YamlFileLoader($yamlContainer, new FileLocator(__DIR__)); 
   $loader->load('services.yml');  

   $yamlHello = $yamlContainer->get('greeter'); 
   $yamlHello->greet('Jon'); 
   
   $yamlUser = $yamlContainer->get('user'); 
   $yamlUser->name = "Jon"; 
   $yamlUser->age = 25; 
   $yamlUser->greet();  
?>

services.yml

parameters: 
   greeter.text: 'Hello' 
services: 
   greeter: 
      class: Greeter 
      arguments: ['%greeter.text%'] 
   user: 
      class: User 
      calls: 
         - [setGreeter, ['@greeter']]

symfony Webフレームワークは、依存性注入コンポーネントを広範囲に使用します。すべてのコンポーネントは、一元化されたサービスコンテナによってバインドされます。symfony Webフレームワークは、そのすべてのコンテナを公開しますController 使って containerプロパティ。ロガー、メーラーなど、すべてのオブジェクトを登録することができます。

$logger = $this->container->get('logger'); 
$logger->info('Hi');

コンテナに登録されているオブジェクトを見つけるには、次のコマンドを使用します。

cd /path/to/app 
php bin/console debug:container

には約200以上のオブジェクトがあります hello インストールの章で作成されたWebアプリ。