Dependency Injection in PHP

Ashish Thakur

@ashish_thakur

About me

  • A mountain guy who lives near a beach
  • Works for Srijan
  • Was a system engineer (c, tcl) before starting with Drupal

@ashish_thakur  | a_thakur

Drupal 7

  • Procedural php
  • The way we did stuff was different from other php frameworks like Laravel, Symfony etc 
  • Happy days :)

Drupal 8

  • Symfony components
  • Composer
  • php-fig
  • Object Oriented PHP
  • Dependency Injection

source: http://cdn4.zyxware.com/files/Migrating_your_Drupal_7_themes_to_Drupal_8.jpg

Dependency Injection

Dependency Injection is providing a component with its dependencies either through constructor injection, method calls or the setting of properties.

The Problem

<?php
namespace Database;

class Database
{
    protected $adapter;

    public function __construct()
    {
        $this->adapter = new MySqlAdapter;
    }
}

class MysqlAdapter {}

http://www.phptherightway.com/#dependency_injection

Solution

<?php
namespace Database;

class Database
{
    protected $adapter;

    public function __construct(MySqlAdapter $adapter)
    {
        $this->adapter = $adapter;
    }
}

class MysqlAdapter {}

http://www.phptherightway.com/#dependency_injection

Before

<?php
namespace Database;

class Database
{
    protected $adapter;

    public function __construct()
    {
        $this->adapter = new MySqlAdapter;
    }
}

class MysqlAdapter {}

After

<?php
namespace Database;

class Database
{
    protected $adapter;

    public function __construct(MySqlAdapter $adapter)
    {
        $this->adapter = $adapter;
    }
}

class MysqlAdapter {}

Depend on Abstactions

<?php
namespace Database;

class Database
{
    protected $adapter;

    public function __construct(AdapterInterface $adapter)
    {
        $this->adapter = $adapter;
    }
}

interface AdapterInterface {}

class MysqlAdapter implements AdapterInterface {}

http://www.phptherightway.com/#dependency_injection

Types of Dependency Injection

Constructor Injection

<?php
namespace Database;

class Database
{
    protected $adapter;

    public function __construct(AdapterInterface $adapter)
    {
        $this->adapter = $adapter;
    }
}

Setter Injection

<?php
namespace Database;

class Database
{
    protected $adapter;

    public function setDatabaseAdapter(AdapterInterface $adapter)
    {
        $this->adapter = $adapter;
    }
}

Property Injection

<?php
namespace Database;

class Database
{
    public $adapter;
}

$adapter = new MysqlAdapter();

$database->adapter = $adapter;

 

Need for Dependency Injection Container

 $adapter = new MysqlAdapter();

 $database = new Database($adapter);

 

 

Need for Dependency Injection Container

Doctrine Query Builder

services:
    d7.query_builder:
        class: Doctrine\DBAL\Query\QueryBuilder
        arguments: ['@doctrine.dbal.connection']

    doctrine.dbal.connection:
        class: Doctrine\DBAL\Connection
        factory: ['Doctrine\DBAL\DriverManager', getConnection]
        arguments: ['%connection_params%','@doctrine.dbal.config']

  doctrine.dbal.config:
        class: Doctrine\DBAL\Configuration

Symfony

Lets hack and understand

Benefits of DI

  • Better separation of concerns
  • Decoupling
  • Better unit testability

Resources

Thank you

@ashish_thakur | a_thakur | business@srijan.net

https://slides.com/ashish-thakur/di/

Dependency Injection

By Ashish Thakur

Dependency Injection

  • 948