Symfony2 DI Container

study-group-07

Created by Juan Manuel Torres / @onema / onema.io

Follow Live

http://slides.com/onema/symfony2-dependency-injection/live  

DI Container

The DependencyInjection component allows you to standardize and centralize the way objects are constructed in your application.

Remember the Car Class From Studygroup 06

We can update it to set the make and the number of passengers it can accomodate

class Car implements Vehicle {
    // . . . 
    public function __construct($make, $size = 5) {
        $this->make = $make;
        $this->size = $size;
    }
    // . . . 
    public function getMake() {
        return $this->make;
    }

    public function getSize() {
        return $this->size;
    }

    public function getPerson($name, $type = Person::PASSENGER) {
        return $this->personList[$type][$name];
    }
}

Use the DI Container

To create a new Car

use Symfony\Component\DependencyInjection\ContainerBuilder;

$container = new ContainerBuilder();
$container->register('car', '\SDPHP\StudyGroup07\Car')
    ->addArgument('Toyota')
    ->addArgument(12);



$car = $container->get('car');


echo $car->getMake() . ' Size: ' . $car->getSize();

Toyota Size: 12

Set Constructor Parameters

Set an ID and fully qualified Class

Use the DI Container

To create a more flexible vehicles using Parameters (config values)

use Symfony\Component\DependencyInjection\ContainerBuilder;

$container = new ContainerBuilder();
$container->setParameter('car.make', 'Mazda');
$container->setParameter('car.size', 2);


$container->register('car', '\SDPHP\StudyGroup07\Car')
    ->addArgument('%car.make%')
    ->addArgument('%car.size%');

$car = $container->get('car');

echo $car->getMake() . ' Size: ' . $car->getSize();

Mazda Size: 2

Parameters instead of hard coded values

Create parameter values

Use the DI Container

Let's make sure every car has a driver

use Symfony\Component\DependencyInjection\Reference;
use SDPHP\StudyGroup07\Person;

// . . .
$container->register('person_driver.class', '\SDPHP\StudyGroup07\Person')
    ->addArgument('Juan')
    ->addArgument(Person::DRIVER);

$container->register('car', '\SDPHP\StudyGroup07\Car')
    ->addArgument('%car.make%')
    ->addArgument('%car.size%')
    ->addMethodCall(
        'addPerson', 
        [new Reference('person_driver.class')]);
$car = $container->get('car');
echo $car->getMake() . ' Size: ' . $car->getSize() . '. ';
echo 'The Driver name is: ' . $car->getPerson('Juan', Person::DRIVER)->getName();

Mazda Size: 2. The Driver name is: Juan

Use  'addMethodCall' to inject a new instance of the Driver

Register a new driver in the container

Setting up the COntainer with Configuration Files

Use the DI Container

To create set other values. Let's make sure every car has a driver

use Symfony\Component\DependencyInjection\ContainerBuilder;
use Symfony\Component\Config\FileLocator;
use Symfony\Component\DependencyInjection\Loader\YamlFileLoader;
use SDPHP\StudyGroup07\Person;

$container = new ContainerBuilder();
$loader = new YamlFileLoader($container, new FileLocator(__DIR__));
$loader->load('/vagrant/studygroup/app/config/services.yml');

$car = $container->get('car');

echo $car->getMake() . ' Size: ' . $car->getSize() . PHP_EOL;
echo 'The Driver name is: ' . $car->getPerson('Joe', Person::DRIVER)->getName();

Ford Size: 4. The Driver name is: Joe

Use the container as usual

Use the FileLoader to get the services.yml file

services.yml

parameters:
    car.make: Ford
    car.size: 4
services:
    person_driver.class:
        class: \SDPHP\StudyGroup07\Person
        arguments: ["Joe", "driver"]
    car:
        class: \SDPHP\StudyGroup07\Car
        arguments: ["%car.make%", "%car.size%"]
        calls:
            - [addPerson, ["@person_driver.class"] ]

Homework

Simplify the front controller to use the DI Container 

  1. RequestContext
  2. ControllerResolver
  3. EventDispatcher
  4. TestSubscriber
  5. BeforeAfterSubscriber
  6. SGFramework

THE END

BY Juan Manuel Torres / onema.io / @onema / kinojman@gmail.com

Reference

Symfony2 Dependency Injection Container

By Juan Manuel Torres

Symfony2 Dependency Injection Container

  • 1,599