SlideShare una empresa de Scribd logo
1 de 54
IoC with PHP
     Chris Weldon
  Dallas TechFest 2011
Before We Begin


                                            http://bit.ly/rf1pxR


git://github.com/neraath/ioc-php-talk.git
Your Guide: Chris Weldon

•   Fightin’ Texas Aggie

•   .Net and PHP Developer

•   UNIX and Windows Sysadmin

•   Senior Consultant at Improving Enterprises

•   Contact Me: chris@chrisweldon.net
Agile, Microsoft, Open Technologies, UX
Applied Training, Coaching, Mentoring
Certified Consulting
Rural Sourcing
Recruiting Services
Before We Get to IoC...
<?php
class Authenticator {
    private $_repository;

    public function __construct() {
        $this->_repository = new DataAccessLayer();
    }

    public function authenticate($username, $password) {
        $hashedPassword = md5($password);
        $user = $this->_repository->findByUsernameAndPassword(
            $username, $hashedPassword);
        return $user === null;
    }
}
What are the problems?
What are the problems?

•   Strongly coupled to DataAccessLayer
What are the problems?

•   Strongly coupled to DataAccessLayer
                                                    Authenticator
                                                authenticate() : bool




                                                  DataAccessLayer
                                          findByUsernameAndPassword : array
What are the problems?

•   Strongly coupled to DataAccessLayer

•
                                                    Authenticator
    Very inflexible                              authenticate() : bool




                                                  DataAccessLayer
                                          findByUsernameAndPassword : array
What are the problems?

•   Strongly coupled to DataAccessLayer

•
                                                    Authenticator
    Very inflexible                              authenticate() : bool



•   How to configure DataAccessLayer?
                                                  DataAccessLayer
                                          findByUsernameAndPassword : array
What are the problems?

•   Strongly coupled to DataAccessLayer

•
                                                    Authenticator
    Very inflexible                              authenticate() : bool



•   How to configure DataAccessLayer?

    •
                                                  DataAccessLayer
        Let it read configs?               findByUsernameAndPassword : array
What are the problems?

•   Strongly coupled to DataAccessLayer

•
                                                    Authenticator
    Very inflexible                              authenticate() : bool



•   How to configure DataAccessLayer?

    •
                                                  DataAccessLayer
        Let it read configs?               findByUsernameAndPassword : array


•   How to test the Authenticator?
Let’s solve it


•   What are our goals?

    •   Decrease coupling

    •   Increase configurability
<?php
interface IUserRepository {
    function findByUsernameAndPassword($username, $password);
}
class DataAccessLayer implements IUserRepository {
    private $_configParams;
    private $_database;

    public function __construct(array $configParams) {
        $this->_configParams = $configParams;
        $this->_database = Zend_Db::factory('Pdo_Mysql', $this->_configParams);
    }

    public function findByUsernameAndPassword($username, $password) {
        $query = 'SELECT * FROM users WHERE username = ? AND password = ?';
        $result = $this->_database->fetchAll($query, $username, $password);
        return $result;
    }
}
Our Updated Authenticator
<?php
class Authenticator {
    private $_repository;

    public function __construct(IUserRepository $repository) {
        $this->_repository = $repository;
    }

    public function authenticate($username, $password) {
        $hashedPassword = md5($password);
        $user = $this->_repository->findByUsernameAndPassword(
            $username, $hashedPassword);
        return $user === null;
    }
}
Time to Consume
<?php
class LoginController {
    public function login($username, $password) {
        $configuration = Zend_Registry::get('dbconfig');
        $dal = new DataAccessLayer($configuration);
        $authenticator = new Authenticator($dal);
        if ($authenticator->authenticate($username, $password)) {
            // Do something to log the user in.
        }
    }
}
Goal Recap


•   What were our goals?

    •   Decrease coupling

    •   Increase configurability
Goal Recap


•   What were our goals?

    •   Decrease coupling

    •   Increase configurability
Goal Recap


•   What were our goals?

    •   Decrease coupling

    •   Increase configurability
What You Saw Was IoC
•   Inversion of Control changes direction of responsibility

    •   Someone else responsible for creating and providing my
        dependencies

    •   Most commonly applied pattern: Dependency Injection

    •   Follows Dependency Inversion Principle from SOLID

•   Culture War: IoC vs. DI vs. Naming vs. Principles vs. Ideology
Dependency Inversion


•   “High-level modules should not depend upon low level modules. They
    should depend upon abstractions.

•   “Abstractions should not depend upon details. Details should depend
    upon abstractions.”
                                                           Robert Martin
Let’s Draw
Let’s Draw

          Authenticator
      authenticate() : bool




        DataAccessLayer
findByUsernameAndPassword : array
Let’s Draw

          Authenticator
      authenticate() : bool




        DataAccessLayer
findByUsernameAndPassword : array
Let’s Draw
                                                  Authenticator
                                              authenticate() : bool

          Authenticator
      authenticate() : bool

                                                 IUserRepository
                                        findByUsernameAndPassword : array

        DataAccessLayer
findByUsernameAndPassword : array

                                                DataAccessLayer
                                        findByUsernameAndPassword : array
Benefit: Flexibility
<?php
class WebServiceUserRepository implements IUserRepository {
    public function findByUsernameAndPassword($username, $password) {
        // Fetch our user through JSON or SOAP
    }
}

class OAuthRepository implements IUserRepository {
    public function findByUsernameAndPassword($username, $password) {
        // Connect to your favorite OAuth provider
    }
}
Benefit: Testable
<?php
class WhenAuthenticating extends PHPUnit_Framework_TestCase {
    public function testGivenInvalidUsernameAndPasswordShouldReturnFalse() {
        $stub = $this->getMock('IUserRepository');
        $stub->expects($this->any())
             ->method('findByUsernameAndPassword')
             ->will($this->returnValue(null));

        $authenticator = new Authenticator($stub);

        $this->assertFalse($authenticator->authenticate('user', 'pass'));
    }
}
Dependency Injection

•   Now we can inject our dependencies to our consumer classes

•   Still requires some other class to be tightly coupled to both of those

•   Need a container that can help abstract the relationship between the
    interface and implementation
<?php
class UserRepositoryContainer {
    /** @return IUserRepository **/
    public function getRepository() {
        $container = new DataAccessLayer(array(
            'dsn' => 'mysql://localhost/database',
            'username' => 'user',
            'password' => 'pass'
        ));

        return $container;
    }
}

class LoginController {
    public function login($username, $password) {
        $container = new UserRepositoryContainer();
        $repository = $container->getRepository();
        $authenticator = new Authenticator($repository);
        // ...
    }
}
Container Woes

•   No uniform interface by which to access services

•   Still tightly coupled with dependencies

•   Configurability of the container difficult

•   How to auto-inject dependency for configured consumer classes?
Symfony Dependency Injection
                 Container

•   Two Ways to Setup and Use sfServiceContainer

    •   Create subclass

    •   Manual registration via code or config
sfServiceContainer Subclass

<?php
class UserRepositoryContainer extends sfServiceContainer {
    protected function getUserRepositoryService() {
        $container = new DataAccessLayer($this['repository.config']);
        return $container;
    }
}
Consuming the Container
<?php
class LoginController {
    public function login($username, $password) {
        $configuration = Zend_Registry::get('dbconfig');

        $container = new UserRepositoryContainer(array(
            'repository.config' => $configuration
        ));
        $repository = $container->userRepository;

        $authenticator = new Authenticator($repository);
        if ($authenticator->authenticate($username, $password)) {
            // Do something to log the user in.
        }
    }
}
That’s Pretty Nice

•   Configurability a lot easier

•   Uniform interface for accessing services

•   How does this scale when there are lots of dependencies?

•   Aren’t we still coupling the container to the implementation at
    compile time?
The Builder

•   Provides a uniform way of describing services, without custom
    containers

•   For each service description, we have the flexibility to configure an
    object:

    •   At instantiation (Constructor Injection)

    •   Post-instantiation (Setter/Method Injection)
How to Describe a Service

•   Code-based or Config-based

    •   Code-based allows for run-time changing of injection parameters

    •   Config-based provides a way to change parameters between
        environments with no code changes

    •   Not mutually exclusive
Code-Based Description
<?php
// Imagine this is a bootstrap file.
$configuration = Zend_Registry::get('dbconfig');

$builder = new sfServiceContainerBuilder();

$builder->register('user_repository', 'DataAccessLayer')
        ->addArgument($configuration)
        // OR ->addArgument('%repository.config%') from earlier
        ->setShared(false);

$builder->register('authenticator', 'Authenticator')
        ->addArgument(new sfServiceReference('user_repository'));

Zend_Registry::set('di_container', $builder);
Config-Based Description
<?xml version="1.0" ?>
<container xmlns="http://symfony-project.org/2.0/container">
  <parameters>
    <parameter key="user_repository.dsn">mysql://localhost/database</parameter>
    <parameter key="user_repository.username">username</parameter>
    <parameter key="user_repository.password">password</parameter>
  </parameters>
  <services>
    <service id="user_repository" class="DataAccessLayer" shared="false">
      <argument type="collection">
        <argument key="dsn">%user_repository.dsn%</argument>
        <argument key="username">%user_repository.username%</argument>
        <argument key="password">%user_repository.password%</argument>
      </argument>
    </service>
    <service id="authenticator" class="Authenticator">
      <argument type="service" id="user_repository" />
    </service>
  </services>
</container>
Loading the Config

<?php
// Imagine this is a bootstrap file.
$builder = new sfServiceContainerBuilder();

$loader = new sfServiceContainerLoaderFileXml($builder);
$loader->load('/pathTo/services.xml');

Zend_Registry::set('di_container', $builder);
Using the Container

<?php
class LoginController {
    public function login($username, $password) {
        $container = Zend_Registry::get('di_container');
        $authenticator = $container->authenticator;
        if ($authenticator->authenticate($username, $password)) {
            // Do something to log the user in.
        }
    }
}
High Level Picture
        DataAccessLayer
findByUsernameAndPassword : array




         IUserRepository
findByUsernameAndPassword : array
                                     sfServiceContainerBuilder
                                   getService : object
                                   setService : void
                                   hasService : bool
            Authenticator
authenticate() : bool




            IAuthenticator
authenticate() : bool



                                     sfServiceContainerInterface
                                   getService : object
           LoginController         setService : void
        login() : void             hasService : bool
When to Use a DI Container
When to Use a DI Container

•   Not for model objects (e.g. Orders, Documents, etc.)
When to Use a DI Container

•   Not for model objects (e.g. Orders, Documents, etc.)

•   Great for resource requirements (e.g. repositories, loggers, etc.)
When to Use a DI Container

•   Not for model objects (e.g. Orders, Documents, etc.)

•   Great for resource requirements (e.g. repositories, loggers, etc.)

•   Really great for plugin-type architecture
When to Use a DI Container

•   Not for model objects (e.g. Orders, Documents, etc.)

•   Great for resource requirements (e.g. repositories, loggers, etc.)

•   Really great for plugin-type architecture

•   But not necessary to use Dependency Injection!
Other Considerations
Other Considerations

•   Learning curve
Other Considerations

•   Learning curve

•   Tracking dependencies
Other Considerations

•   Learning curve

•   Tracking dependencies

•   Dependency changes
Other Considerations

•   Learning curve

•   Tracking dependencies

•   Dependency changes

•   Setter/method vs. constructor injection
Service Lifetimes


•   setShared() allows you to specify context persistence

    •   If shared, acts like a singleton

    •   Useful if construction is expensive or state persistence required
Let’s Code
Thank You!


                                            http://bit.ly/rf1pxR


git://github.com/neraath/ioc-php-talk.git

Más contenido relacionado

La actualidad más candente

Node.js vs Play Framework (with Japanese subtitles)
Node.js vs Play Framework (with Japanese subtitles)Node.js vs Play Framework (with Japanese subtitles)
Node.js vs Play Framework (with Japanese subtitles)Yevgeniy Brikman
 
Cloud Native Identity with SPIFFE
Cloud Native Identity with SPIFFECloud Native Identity with SPIFFE
Cloud Native Identity with SPIFFEPrabath Siriwardena
 
Intro to JavaScript
Intro to JavaScriptIntro to JavaScript
Intro to JavaScriptYakov Fain
 
Domain Driven Design using Laravel
Domain Driven Design using LaravelDomain Driven Design using Laravel
Domain Driven Design using Laravelwajrcs
 
Hibernate training
Hibernate trainingHibernate training
Hibernate trainingTechFerry
 
Recipes to build Code Generators for Non-Xtext Models with Xtend
Recipes to build Code Generators for Non-Xtext Models with XtendRecipes to build Code Generators for Non-Xtext Models with Xtend
Recipes to build Code Generators for Non-Xtext Models with XtendKarsten Thoms
 
Working Effectively With Legacy Code
Working Effectively With Legacy CodeWorking Effectively With Legacy Code
Working Effectively With Legacy Codescidept
 
AspMVC4 start101
AspMVC4 start101AspMVC4 start101
AspMVC4 start101Rich Helton
 
Better Testing With PHP Unit
Better Testing With PHP UnitBetter Testing With PHP Unit
Better Testing With PHP Unitsitecrafting
 
Spring training
Spring trainingSpring training
Spring trainingTechFerry
 
Code Generation idioms with Xtend
Code Generation idioms with XtendCode Generation idioms with Xtend
Code Generation idioms with XtendHolger Schill
 
Connect.Tech- Enhancing Your Workflow With Xcode Source Editor Extensions
Connect.Tech- Enhancing Your Workflow With Xcode Source Editor ExtensionsConnect.Tech- Enhancing Your Workflow With Xcode Source Editor Extensions
Connect.Tech- Enhancing Your Workflow With Xcode Source Editor Extensionsstable|kernel
 
Apex Code Analysis Using the Tooling API and Canvas
Apex Code Analysis Using the Tooling API and CanvasApex Code Analysis Using the Tooling API and Canvas
Apex Code Analysis Using the Tooling API and CanvasSalesforce Developers
 
TDD with PhpSpec - Lone Star PHP 2016
TDD with PhpSpec - Lone Star PHP 2016TDD with PhpSpec - Lone Star PHP 2016
TDD with PhpSpec - Lone Star PHP 2016CiaranMcNulty
 
TangoWithDjango - ch8
TangoWithDjango - ch8TangoWithDjango - ch8
TangoWithDjango - ch8Asika Kuo
 

La actualidad más candente (20)

Node.js vs Play Framework (with Japanese subtitles)
Node.js vs Play Framework (with Japanese subtitles)Node.js vs Play Framework (with Japanese subtitles)
Node.js vs Play Framework (with Japanese subtitles)
 
Cloud Native Identity with SPIFFE
Cloud Native Identity with SPIFFECloud Native Identity with SPIFFE
Cloud Native Identity with SPIFFE
 
Intro to JavaScript
Intro to JavaScriptIntro to JavaScript
Intro to JavaScript
 
Domain Driven Design using Laravel
Domain Driven Design using LaravelDomain Driven Design using Laravel
Domain Driven Design using Laravel
 
Hibernate training
Hibernate trainingHibernate training
Hibernate training
 
Data Validation models
Data Validation modelsData Validation models
Data Validation models
 
Recipes to build Code Generators for Non-Xtext Models with Xtend
Recipes to build Code Generators for Non-Xtext Models with XtendRecipes to build Code Generators for Non-Xtext Models with Xtend
Recipes to build Code Generators for Non-Xtext Models with Xtend
 
Working Effectively With Legacy Code
Working Effectively With Legacy CodeWorking Effectively With Legacy Code
Working Effectively With Legacy Code
 
AspMVC4 start101
AspMVC4 start101AspMVC4 start101
AspMVC4 start101
 
Better Testing With PHP Unit
Better Testing With PHP UnitBetter Testing With PHP Unit
Better Testing With PHP Unit
 
Spring training
Spring trainingSpring training
Spring training
 
Code Generation idioms with Xtend
Code Generation idioms with XtendCode Generation idioms with Xtend
Code Generation idioms with Xtend
 
Connect.Tech- Enhancing Your Workflow With Xcode Source Editor Extensions
Connect.Tech- Enhancing Your Workflow With Xcode Source Editor ExtensionsConnect.Tech- Enhancing Your Workflow With Xcode Source Editor Extensions
Connect.Tech- Enhancing Your Workflow With Xcode Source Editor Extensions
 
Apex Code Analysis Using the Tooling API and Canvas
Apex Code Analysis Using the Tooling API and CanvasApex Code Analysis Using the Tooling API and Canvas
Apex Code Analysis Using the Tooling API and Canvas
 
ExtJs Basic Part-1
ExtJs Basic Part-1ExtJs Basic Part-1
ExtJs Basic Part-1
 
Dependency Injection
Dependency InjectionDependency Injection
Dependency Injection
 
TDD with PhpSpec - Lone Star PHP 2016
TDD with PhpSpec - Lone Star PHP 2016TDD with PhpSpec - Lone Star PHP 2016
TDD with PhpSpec - Lone Star PHP 2016
 
Web API with ASP.NET MVC by Software development company in india
Web API with ASP.NET  MVC  by Software development company in indiaWeb API with ASP.NET  MVC  by Software development company in india
Web API with ASP.NET MVC by Software development company in india
 
TangoWithDjango - ch8
TangoWithDjango - ch8TangoWithDjango - ch8
TangoWithDjango - ch8
 
2007 Zend Con Mvc
2007 Zend Con Mvc2007 Zend Con Mvc
2007 Zend Con Mvc
 

Destacado

Ioc & in direction
Ioc & in directionIoc & in direction
Ioc & in direction育汶 郭
 
2007 5 30 肖镜辉 统计语言模型简介
2007 5 30 肖镜辉 统计语言模型简介2007 5 30 肖镜辉 统计语言模型简介
2007 5 30 肖镜辉 统计语言模型简介xceman
 
PHP Unit-Testing With Doubles
PHP Unit-Testing With DoublesPHP Unit-Testing With Doubles
PHP Unit-Testing With DoublesMihail Irintchev
 
PHPUnit でよりよくテストを書くために
PHPUnit でよりよくテストを書くためにPHPUnit でよりよくテストを書くために
PHPUnit でよりよくテストを書くためにYuya Takeyama
 
Zensations Drupal 8 GraphQL Presentation 2015
Zensations Drupal 8 GraphQL Presentation 2015Zensations Drupal 8 GraphQL Presentation 2015
Zensations Drupal 8 GraphQL Presentation 2015Zensations GmbH
 
PHPUnit 入門介紹
PHPUnit 入門介紹PHPUnit 入門介紹
PHPUnit 入門介紹Jace Ju
 
PHPUnit best practices presentation
PHPUnit best practices presentationPHPUnit best practices presentation
PHPUnit best practices presentationThanh Robi
 
Introduction to Unit Testing with PHPUnit
Introduction to Unit Testing with PHPUnitIntroduction to Unit Testing with PHPUnit
Introduction to Unit Testing with PHPUnitMichelangelo van Dam
 
Jmeter Performance Testing
Jmeter Performance TestingJmeter Performance Testing
Jmeter Performance TestingAtul Pant
 
Di – ioc (ninject)
Di – ioc (ninject)Di – ioc (ninject)
Di – ioc (ninject)ZealousysDev
 
Advanced PHPUnit Testing
Advanced PHPUnit TestingAdvanced PHPUnit Testing
Advanced PHPUnit TestingMike Lively
 

Destacado (12)

Ioc & in direction
Ioc & in directionIoc & in direction
Ioc & in direction
 
2007 5 30 肖镜辉 统计语言模型简介
2007 5 30 肖镜辉 统计语言模型简介2007 5 30 肖镜辉 统计语言模型简介
2007 5 30 肖镜辉 统计语言模型简介
 
Stub you!
Stub you!Stub you!
Stub you!
 
PHP Unit-Testing With Doubles
PHP Unit-Testing With DoublesPHP Unit-Testing With Doubles
PHP Unit-Testing With Doubles
 
PHPUnit でよりよくテストを書くために
PHPUnit でよりよくテストを書くためにPHPUnit でよりよくテストを書くために
PHPUnit でよりよくテストを書くために
 
Zensations Drupal 8 GraphQL Presentation 2015
Zensations Drupal 8 GraphQL Presentation 2015Zensations Drupal 8 GraphQL Presentation 2015
Zensations Drupal 8 GraphQL Presentation 2015
 
PHPUnit 入門介紹
PHPUnit 入門介紹PHPUnit 入門介紹
PHPUnit 入門介紹
 
PHPUnit best practices presentation
PHPUnit best practices presentationPHPUnit best practices presentation
PHPUnit best practices presentation
 
Introduction to Unit Testing with PHPUnit
Introduction to Unit Testing with PHPUnitIntroduction to Unit Testing with PHPUnit
Introduction to Unit Testing with PHPUnit
 
Jmeter Performance Testing
Jmeter Performance TestingJmeter Performance Testing
Jmeter Performance Testing
 
Di – ioc (ninject)
Di – ioc (ninject)Di – ioc (ninject)
Di – ioc (ninject)
 
Advanced PHPUnit Testing
Advanced PHPUnit TestingAdvanced PHPUnit Testing
Advanced PHPUnit Testing
 

Similar a IoC with PHP

Implementing access control with zend framework
Implementing access control with zend frameworkImplementing access control with zend framework
Implementing access control with zend frameworkGeorge Mihailov
 
Third Party Auth in WebObjects
Third Party Auth in WebObjectsThird Party Auth in WebObjects
Third Party Auth in WebObjectsWO Community
 
Becoming a better WordPress Developer
Becoming a better WordPress DeveloperBecoming a better WordPress Developer
Becoming a better WordPress DeveloperJoey Kudish
 
Java EE 8 security and JSON binding API
Java EE 8 security and JSON binding APIJava EE 8 security and JSON binding API
Java EE 8 security and JSON binding APIAlex Theedom
 
Building Better Applications with Data::Manager
Building Better Applications with Data::ManagerBuilding Better Applications with Data::Manager
Building Better Applications with Data::ManagerJay Shirley
 
Azure Table Storage: The Good, the Bad, the Ugly (15 min. lightning talk)
Azure Table Storage: The Good, the Bad, the Ugly (15 min. lightning talk)Azure Table Storage: The Good, the Bad, the Ugly (15 min. lightning talk)
Azure Table Storage: The Good, the Bad, the Ugly (15 min. lightning talk)Sirar Salih
 
10 Rules for Safer Code
10 Rules for Safer Code10 Rules for Safer Code
10 Rules for Safer CodeQuang Ngoc
 
Persistant Cookies and LDAP Injection
Persistant Cookies and LDAP InjectionPersistant Cookies and LDAP Injection
Persistant Cookies and LDAP InjectionMaulikLakhani
 
10 Rules for Safer Code [Odoo Experience 2016]
10 Rules for Safer Code [Odoo Experience 2016]10 Rules for Safer Code [Odoo Experience 2016]
10 Rules for Safer Code [Odoo Experience 2016]Olivier Dony
 
Simple Web Development in Java
Simple Web Development in JavaSimple Web Development in Java
Simple Web Development in JavaVincent Tencé
 
Jakość dostarczanego oprogramowania oparta o testy
Jakość dostarczanego oprogramowania oparta o testyJakość dostarczanego oprogramowania oparta o testy
Jakość dostarczanego oprogramowania oparta o testyPaweł Tekliński
 
Security in laravel
Security in laravelSecurity in laravel
Security in laravelSayed Ahmed
 
Code your Own: Authentication Provider for Blackboard Learn
Code your Own: Authentication Provider for Blackboard LearnCode your Own: Authentication Provider for Blackboard Learn
Code your Own: Authentication Provider for Blackboard LearnDan Rinzel
 
State of the art authentication mit Java EE 8
State of the art authentication mit Java EE 8State of the art authentication mit Java EE 8
State of the art authentication mit Java EE 8OPEN KNOWLEDGE GmbH
 
STATE OF THE ART AUTHENTICATION MIT JAVA EE 8
STATE OF THE ART AUTHENTICATION MIT JAVA EE 8STATE OF THE ART AUTHENTICATION MIT JAVA EE 8
STATE OF THE ART AUTHENTICATION MIT JAVA EE 8OPEN KNOWLEDGE GmbH
 
Authentication with zend framework
Authentication with zend frameworkAuthentication with zend framework
Authentication with zend frameworkGeorge Mihailov
 
devise tutorial - 2011 rubyconf taiwan
devise tutorial - 2011 rubyconf taiwandevise tutorial - 2011 rubyconf taiwan
devise tutorial - 2011 rubyconf taiwanTse-Ching Ho
 

Similar a IoC with PHP (20)

Implementing access control with zend framework
Implementing access control with zend frameworkImplementing access control with zend framework
Implementing access control with zend framework
 
Third Party Auth in WebObjects
Third Party Auth in WebObjectsThird Party Auth in WebObjects
Third Party Auth in WebObjects
 
Becoming a better WordPress Developer
Becoming a better WordPress DeveloperBecoming a better WordPress Developer
Becoming a better WordPress Developer
 
Java EE 8 security and JSON binding API
Java EE 8 security and JSON binding APIJava EE 8 security and JSON binding API
Java EE 8 security and JSON binding API
 
Building Better Applications with Data::Manager
Building Better Applications with Data::ManagerBuilding Better Applications with Data::Manager
Building Better Applications with Data::Manager
 
Azure Table Storage: The Good, the Bad, the Ugly (15 min. lightning talk)
Azure Table Storage: The Good, the Bad, the Ugly (15 min. lightning talk)Azure Table Storage: The Good, the Bad, the Ugly (15 min. lightning talk)
Azure Table Storage: The Good, the Bad, the Ugly (15 min. lightning talk)
 
10 Rules for Safer Code
10 Rules for Safer Code10 Rules for Safer Code
10 Rules for Safer Code
 
Persistant Cookies and LDAP Injection
Persistant Cookies and LDAP InjectionPersistant Cookies and LDAP Injection
Persistant Cookies and LDAP Injection
 
10 Rules for Safer Code [Odoo Experience 2016]
10 Rules for Safer Code [Odoo Experience 2016]10 Rules for Safer Code [Odoo Experience 2016]
10 Rules for Safer Code [Odoo Experience 2016]
 
Simple Web Development in Java
Simple Web Development in JavaSimple Web Development in Java
Simple Web Development in Java
 
Jakość dostarczanego oprogramowania oparta o testy
Jakość dostarczanego oprogramowania oparta o testyJakość dostarczanego oprogramowania oparta o testy
Jakość dostarczanego oprogramowania oparta o testy
 
Security in laravel
Security in laravelSecurity in laravel
Security in laravel
 
Code your Own: Authentication Provider for Blackboard Learn
Code your Own: Authentication Provider for Blackboard LearnCode your Own: Authentication Provider for Blackboard Learn
Code your Own: Authentication Provider for Blackboard Learn
 
Real World MVC
Real World MVCReal World MVC
Real World MVC
 
State of the art authentication mit Java EE 8
State of the art authentication mit Java EE 8State of the art authentication mit Java EE 8
State of the art authentication mit Java EE 8
 
STATE OF THE ART AUTHENTICATION MIT JAVA EE 8
STATE OF THE ART AUTHENTICATION MIT JAVA EE 8STATE OF THE ART AUTHENTICATION MIT JAVA EE 8
STATE OF THE ART AUTHENTICATION MIT JAVA EE 8
 
Phactory
PhactoryPhactory
Phactory
 
Authentication with zend framework
Authentication with zend frameworkAuthentication with zend framework
Authentication with zend framework
 
Javascript Php Crud
Javascript Php CrudJavascript Php Crud
Javascript Php Crud
 
devise tutorial - 2011 rubyconf taiwan
devise tutorial - 2011 rubyconf taiwandevise tutorial - 2011 rubyconf taiwan
devise tutorial - 2011 rubyconf taiwan
 

Más de Chris Weldon

REST Easy - Building RESTful Services in Zend Framework
REST Easy - Building RESTful Services in Zend FrameworkREST Easy - Building RESTful Services in Zend Framework
REST Easy - Building RESTful Services in Zend FrameworkChris Weldon
 
Beyond TDD: Enabling Your Team to Continuously Deliver Software
Beyond TDD: Enabling Your Team to Continuously Deliver SoftwareBeyond TDD: Enabling Your Team to Continuously Deliver Software
Beyond TDD: Enabling Your Team to Continuously Deliver SoftwareChris Weldon
 
SOLID - Not Just a State of Matter, It's Principles for OO Propriety
SOLID - Not Just a State of Matter, It's Principles for OO ProprietySOLID - Not Just a State of Matter, It's Principles for OO Propriety
SOLID - Not Just a State of Matter, It's Principles for OO ProprietyChris Weldon
 
Unit Testing in SharePoint 2010
Unit Testing in SharePoint 2010Unit Testing in SharePoint 2010
Unit Testing in SharePoint 2010Chris Weldon
 

Más de Chris Weldon (7)

Keat presentation
Keat presentationKeat presentation
Keat presentation
 
REST Easy - Building RESTful Services in Zend Framework
REST Easy - Building RESTful Services in Zend FrameworkREST Easy - Building RESTful Services in Zend Framework
REST Easy - Building RESTful Services in Zend Framework
 
Beyond TDD: Enabling Your Team to Continuously Deliver Software
Beyond TDD: Enabling Your Team to Continuously Deliver SoftwareBeyond TDD: Enabling Your Team to Continuously Deliver Software
Beyond TDD: Enabling Your Team to Continuously Deliver Software
 
SOLID - Not Just a State of Matter, It's Principles for OO Propriety
SOLID - Not Just a State of Matter, It's Principles for OO ProprietySOLID - Not Just a State of Matter, It's Principles for OO Propriety
SOLID - Not Just a State of Matter, It's Principles for OO Propriety
 
SOLID Principles
SOLID PrinciplesSOLID Principles
SOLID Principles
 
Unit Testing in SharePoint 2010
Unit Testing in SharePoint 2010Unit Testing in SharePoint 2010
Unit Testing in SharePoint 2010
 
PHP & MVC
PHP & MVCPHP & MVC
PHP & MVC
 

Último

How to Effectively Monitor SD-WAN and SASE Environments with ThousandEyes
How to Effectively Monitor SD-WAN and SASE Environments with ThousandEyesHow to Effectively Monitor SD-WAN and SASE Environments with ThousandEyes
How to Effectively Monitor SD-WAN and SASE Environments with ThousandEyesThousandEyes
 
Time Series Foundation Models - current state and future directions
Time Series Foundation Models - current state and future directionsTime Series Foundation Models - current state and future directions
Time Series Foundation Models - current state and future directionsNathaniel Shimoni
 
Modern Roaming for Notes and Nomad – Cheaper Faster Better Stronger
Modern Roaming for Notes and Nomad – Cheaper Faster Better StrongerModern Roaming for Notes and Nomad – Cheaper Faster Better Stronger
Modern Roaming for Notes and Nomad – Cheaper Faster Better Strongerpanagenda
 
The Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptx
The Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptxThe Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptx
The Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptxLoriGlavin3
 
Long journey of Ruby standard library at RubyConf AU 2024
Long journey of Ruby standard library at RubyConf AU 2024Long journey of Ruby standard library at RubyConf AU 2024
Long journey of Ruby standard library at RubyConf AU 2024Hiroshi SHIBATA
 
Potential of AI (Generative AI) in Business: Learnings and Insights
Potential of AI (Generative AI) in Business: Learnings and InsightsPotential of AI (Generative AI) in Business: Learnings and Insights
Potential of AI (Generative AI) in Business: Learnings and InsightsRavi Sanghani
 
Moving Beyond Passwords: FIDO Paris Seminar.pdf
Moving Beyond Passwords: FIDO Paris Seminar.pdfMoving Beyond Passwords: FIDO Paris Seminar.pdf
Moving Beyond Passwords: FIDO Paris Seminar.pdfLoriGlavin3
 
Scale your database traffic with Read & Write split using MySQL Router
Scale your database traffic with Read & Write split using MySQL RouterScale your database traffic with Read & Write split using MySQL Router
Scale your database traffic with Read & Write split using MySQL RouterMydbops
 
Connecting the Dots for Information Discovery.pdf
Connecting the Dots for Information Discovery.pdfConnecting the Dots for Information Discovery.pdf
Connecting the Dots for Information Discovery.pdfNeo4j
 
(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...
(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...
(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...AliaaTarek5
 
2024 April Patch Tuesday
2024 April Patch Tuesday2024 April Patch Tuesday
2024 April Patch TuesdayIvanti
 
Manual 508 Accessibility Compliance Audit
Manual 508 Accessibility Compliance AuditManual 508 Accessibility Compliance Audit
Manual 508 Accessibility Compliance AuditSkynet Technologies
 
Testing tools and AI - ideas what to try with some tool examples
Testing tools and AI - ideas what to try with some tool examplesTesting tools and AI - ideas what to try with some tool examples
Testing tools and AI - ideas what to try with some tool examplesKari Kakkonen
 
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptx
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptxMerck Moving Beyond Passwords: FIDO Paris Seminar.pptx
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptxLoriGlavin3
 
How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.Curtis Poe
 
Emixa Mendix Meetup 11 April 2024 about Mendix Native development
Emixa Mendix Meetup 11 April 2024 about Mendix Native developmentEmixa Mendix Meetup 11 April 2024 about Mendix Native development
Emixa Mendix Meetup 11 April 2024 about Mendix Native developmentPim van der Noll
 
Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24
Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24
Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24Mark Goldstein
 
The State of Passkeys with FIDO Alliance.pptx
The State of Passkeys with FIDO Alliance.pptxThe State of Passkeys with FIDO Alliance.pptx
The State of Passkeys with FIDO Alliance.pptxLoriGlavin3
 
TrustArc Webinar - How to Build Consumer Trust Through Data Privacy
TrustArc Webinar - How to Build Consumer Trust Through Data PrivacyTrustArc Webinar - How to Build Consumer Trust Through Data Privacy
TrustArc Webinar - How to Build Consumer Trust Through Data PrivacyTrustArc
 
The Ultimate Guide to Choosing WordPress Pros and Cons
The Ultimate Guide to Choosing WordPress Pros and ConsThe Ultimate Guide to Choosing WordPress Pros and Cons
The Ultimate Guide to Choosing WordPress Pros and ConsPixlogix Infotech
 

Último (20)

How to Effectively Monitor SD-WAN and SASE Environments with ThousandEyes
How to Effectively Monitor SD-WAN and SASE Environments with ThousandEyesHow to Effectively Monitor SD-WAN and SASE Environments with ThousandEyes
How to Effectively Monitor SD-WAN and SASE Environments with ThousandEyes
 
Time Series Foundation Models - current state and future directions
Time Series Foundation Models - current state and future directionsTime Series Foundation Models - current state and future directions
Time Series Foundation Models - current state and future directions
 
Modern Roaming for Notes and Nomad – Cheaper Faster Better Stronger
Modern Roaming for Notes and Nomad – Cheaper Faster Better StrongerModern Roaming for Notes and Nomad – Cheaper Faster Better Stronger
Modern Roaming for Notes and Nomad – Cheaper Faster Better Stronger
 
The Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptx
The Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptxThe Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptx
The Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptx
 
Long journey of Ruby standard library at RubyConf AU 2024
Long journey of Ruby standard library at RubyConf AU 2024Long journey of Ruby standard library at RubyConf AU 2024
Long journey of Ruby standard library at RubyConf AU 2024
 
Potential of AI (Generative AI) in Business: Learnings and Insights
Potential of AI (Generative AI) in Business: Learnings and InsightsPotential of AI (Generative AI) in Business: Learnings and Insights
Potential of AI (Generative AI) in Business: Learnings and Insights
 
Moving Beyond Passwords: FIDO Paris Seminar.pdf
Moving Beyond Passwords: FIDO Paris Seminar.pdfMoving Beyond Passwords: FIDO Paris Seminar.pdf
Moving Beyond Passwords: FIDO Paris Seminar.pdf
 
Scale your database traffic with Read & Write split using MySQL Router
Scale your database traffic with Read & Write split using MySQL RouterScale your database traffic with Read & Write split using MySQL Router
Scale your database traffic with Read & Write split using MySQL Router
 
Connecting the Dots for Information Discovery.pdf
Connecting the Dots for Information Discovery.pdfConnecting the Dots for Information Discovery.pdf
Connecting the Dots for Information Discovery.pdf
 
(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...
(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...
(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...
 
2024 April Patch Tuesday
2024 April Patch Tuesday2024 April Patch Tuesday
2024 April Patch Tuesday
 
Manual 508 Accessibility Compliance Audit
Manual 508 Accessibility Compliance AuditManual 508 Accessibility Compliance Audit
Manual 508 Accessibility Compliance Audit
 
Testing tools and AI - ideas what to try with some tool examples
Testing tools and AI - ideas what to try with some tool examplesTesting tools and AI - ideas what to try with some tool examples
Testing tools and AI - ideas what to try with some tool examples
 
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptx
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptxMerck Moving Beyond Passwords: FIDO Paris Seminar.pptx
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptx
 
How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.
 
Emixa Mendix Meetup 11 April 2024 about Mendix Native development
Emixa Mendix Meetup 11 April 2024 about Mendix Native developmentEmixa Mendix Meetup 11 April 2024 about Mendix Native development
Emixa Mendix Meetup 11 April 2024 about Mendix Native development
 
Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24
Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24
Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24
 
The State of Passkeys with FIDO Alliance.pptx
The State of Passkeys with FIDO Alliance.pptxThe State of Passkeys with FIDO Alliance.pptx
The State of Passkeys with FIDO Alliance.pptx
 
TrustArc Webinar - How to Build Consumer Trust Through Data Privacy
TrustArc Webinar - How to Build Consumer Trust Through Data PrivacyTrustArc Webinar - How to Build Consumer Trust Through Data Privacy
TrustArc Webinar - How to Build Consumer Trust Through Data Privacy
 
The Ultimate Guide to Choosing WordPress Pros and Cons
The Ultimate Guide to Choosing WordPress Pros and ConsThe Ultimate Guide to Choosing WordPress Pros and Cons
The Ultimate Guide to Choosing WordPress Pros and Cons
 

IoC with PHP

  • 1. IoC with PHP Chris Weldon Dallas TechFest 2011
  • 2. Before We Begin http://bit.ly/rf1pxR git://github.com/neraath/ioc-php-talk.git
  • 3. Your Guide: Chris Weldon • Fightin’ Texas Aggie • .Net and PHP Developer • UNIX and Windows Sysadmin • Senior Consultant at Improving Enterprises • Contact Me: chris@chrisweldon.net
  • 4. Agile, Microsoft, Open Technologies, UX Applied Training, Coaching, Mentoring Certified Consulting Rural Sourcing Recruiting Services
  • 5. Before We Get to IoC... <?php class Authenticator { private $_repository; public function __construct() { $this->_repository = new DataAccessLayer(); } public function authenticate($username, $password) { $hashedPassword = md5($password); $user = $this->_repository->findByUsernameAndPassword( $username, $hashedPassword); return $user === null; } }
  • 6. What are the problems?
  • 7. What are the problems? • Strongly coupled to DataAccessLayer
  • 8. What are the problems? • Strongly coupled to DataAccessLayer Authenticator authenticate() : bool DataAccessLayer findByUsernameAndPassword : array
  • 9. What are the problems? • Strongly coupled to DataAccessLayer • Authenticator Very inflexible authenticate() : bool DataAccessLayer findByUsernameAndPassword : array
  • 10. What are the problems? • Strongly coupled to DataAccessLayer • Authenticator Very inflexible authenticate() : bool • How to configure DataAccessLayer? DataAccessLayer findByUsernameAndPassword : array
  • 11. What are the problems? • Strongly coupled to DataAccessLayer • Authenticator Very inflexible authenticate() : bool • How to configure DataAccessLayer? • DataAccessLayer Let it read configs? findByUsernameAndPassword : array
  • 12. What are the problems? • Strongly coupled to DataAccessLayer • Authenticator Very inflexible authenticate() : bool • How to configure DataAccessLayer? • DataAccessLayer Let it read configs? findByUsernameAndPassword : array • How to test the Authenticator?
  • 13. Let’s solve it • What are our goals? • Decrease coupling • Increase configurability
  • 14. <?php interface IUserRepository { function findByUsernameAndPassword($username, $password); } class DataAccessLayer implements IUserRepository { private $_configParams; private $_database; public function __construct(array $configParams) { $this->_configParams = $configParams; $this->_database = Zend_Db::factory('Pdo_Mysql', $this->_configParams); } public function findByUsernameAndPassword($username, $password) { $query = 'SELECT * FROM users WHERE username = ? AND password = ?'; $result = $this->_database->fetchAll($query, $username, $password); return $result; } }
  • 15. Our Updated Authenticator <?php class Authenticator { private $_repository; public function __construct(IUserRepository $repository) { $this->_repository = $repository; } public function authenticate($username, $password) { $hashedPassword = md5($password); $user = $this->_repository->findByUsernameAndPassword( $username, $hashedPassword); return $user === null; } }
  • 16. Time to Consume <?php class LoginController { public function login($username, $password) { $configuration = Zend_Registry::get('dbconfig'); $dal = new DataAccessLayer($configuration); $authenticator = new Authenticator($dal); if ($authenticator->authenticate($username, $password)) { // Do something to log the user in. } } }
  • 17. Goal Recap • What were our goals? • Decrease coupling • Increase configurability
  • 18. Goal Recap • What were our goals? • Decrease coupling • Increase configurability
  • 19. Goal Recap • What were our goals? • Decrease coupling • Increase configurability
  • 20. What You Saw Was IoC • Inversion of Control changes direction of responsibility • Someone else responsible for creating and providing my dependencies • Most commonly applied pattern: Dependency Injection • Follows Dependency Inversion Principle from SOLID • Culture War: IoC vs. DI vs. Naming vs. Principles vs. Ideology
  • 21. Dependency Inversion • “High-level modules should not depend upon low level modules. They should depend upon abstractions. • “Abstractions should not depend upon details. Details should depend upon abstractions.” Robert Martin
  • 23. Let’s Draw Authenticator authenticate() : bool DataAccessLayer findByUsernameAndPassword : array
  • 24. Let’s Draw Authenticator authenticate() : bool DataAccessLayer findByUsernameAndPassword : array
  • 25. Let’s Draw Authenticator authenticate() : bool Authenticator authenticate() : bool IUserRepository findByUsernameAndPassword : array DataAccessLayer findByUsernameAndPassword : array DataAccessLayer findByUsernameAndPassword : array
  • 26. Benefit: Flexibility <?php class WebServiceUserRepository implements IUserRepository { public function findByUsernameAndPassword($username, $password) { // Fetch our user through JSON or SOAP } } class OAuthRepository implements IUserRepository { public function findByUsernameAndPassword($username, $password) { // Connect to your favorite OAuth provider } }
  • 27. Benefit: Testable <?php class WhenAuthenticating extends PHPUnit_Framework_TestCase { public function testGivenInvalidUsernameAndPasswordShouldReturnFalse() { $stub = $this->getMock('IUserRepository'); $stub->expects($this->any()) ->method('findByUsernameAndPassword') ->will($this->returnValue(null)); $authenticator = new Authenticator($stub); $this->assertFalse($authenticator->authenticate('user', 'pass')); } }
  • 28. Dependency Injection • Now we can inject our dependencies to our consumer classes • Still requires some other class to be tightly coupled to both of those • Need a container that can help abstract the relationship between the interface and implementation
  • 29. <?php class UserRepositoryContainer { /** @return IUserRepository **/ public function getRepository() { $container = new DataAccessLayer(array( 'dsn' => 'mysql://localhost/database', 'username' => 'user', 'password' => 'pass' )); return $container; } } class LoginController { public function login($username, $password) { $container = new UserRepositoryContainer(); $repository = $container->getRepository(); $authenticator = new Authenticator($repository); // ... } }
  • 30. Container Woes • No uniform interface by which to access services • Still tightly coupled with dependencies • Configurability of the container difficult • How to auto-inject dependency for configured consumer classes?
  • 31. Symfony Dependency Injection Container • Two Ways to Setup and Use sfServiceContainer • Create subclass • Manual registration via code or config
  • 32. sfServiceContainer Subclass <?php class UserRepositoryContainer extends sfServiceContainer { protected function getUserRepositoryService() { $container = new DataAccessLayer($this['repository.config']); return $container; } }
  • 33. Consuming the Container <?php class LoginController { public function login($username, $password) { $configuration = Zend_Registry::get('dbconfig'); $container = new UserRepositoryContainer(array( 'repository.config' => $configuration )); $repository = $container->userRepository; $authenticator = new Authenticator($repository); if ($authenticator->authenticate($username, $password)) { // Do something to log the user in. } } }
  • 34. That’s Pretty Nice • Configurability a lot easier • Uniform interface for accessing services • How does this scale when there are lots of dependencies? • Aren’t we still coupling the container to the implementation at compile time?
  • 35. The Builder • Provides a uniform way of describing services, without custom containers • For each service description, we have the flexibility to configure an object: • At instantiation (Constructor Injection) • Post-instantiation (Setter/Method Injection)
  • 36. How to Describe a Service • Code-based or Config-based • Code-based allows for run-time changing of injection parameters • Config-based provides a way to change parameters between environments with no code changes • Not mutually exclusive
  • 37. Code-Based Description <?php // Imagine this is a bootstrap file. $configuration = Zend_Registry::get('dbconfig'); $builder = new sfServiceContainerBuilder(); $builder->register('user_repository', 'DataAccessLayer') ->addArgument($configuration) // OR ->addArgument('%repository.config%') from earlier ->setShared(false); $builder->register('authenticator', 'Authenticator') ->addArgument(new sfServiceReference('user_repository')); Zend_Registry::set('di_container', $builder);
  • 38. Config-Based Description <?xml version="1.0" ?> <container xmlns="http://symfony-project.org/2.0/container"> <parameters> <parameter key="user_repository.dsn">mysql://localhost/database</parameter> <parameter key="user_repository.username">username</parameter> <parameter key="user_repository.password">password</parameter> </parameters> <services> <service id="user_repository" class="DataAccessLayer" shared="false"> <argument type="collection"> <argument key="dsn">%user_repository.dsn%</argument> <argument key="username">%user_repository.username%</argument> <argument key="password">%user_repository.password%</argument> </argument> </service> <service id="authenticator" class="Authenticator"> <argument type="service" id="user_repository" /> </service> </services> </container>
  • 39. Loading the Config <?php // Imagine this is a bootstrap file. $builder = new sfServiceContainerBuilder(); $loader = new sfServiceContainerLoaderFileXml($builder); $loader->load('/pathTo/services.xml'); Zend_Registry::set('di_container', $builder);
  • 40. Using the Container <?php class LoginController { public function login($username, $password) { $container = Zend_Registry::get('di_container'); $authenticator = $container->authenticator; if ($authenticator->authenticate($username, $password)) { // Do something to log the user in. } } }
  • 41. High Level Picture DataAccessLayer findByUsernameAndPassword : array IUserRepository findByUsernameAndPassword : array sfServiceContainerBuilder getService : object setService : void hasService : bool Authenticator authenticate() : bool IAuthenticator authenticate() : bool sfServiceContainerInterface getService : object LoginController setService : void login() : void hasService : bool
  • 42. When to Use a DI Container
  • 43. When to Use a DI Container • Not for model objects (e.g. Orders, Documents, etc.)
  • 44. When to Use a DI Container • Not for model objects (e.g. Orders, Documents, etc.) • Great for resource requirements (e.g. repositories, loggers, etc.)
  • 45. When to Use a DI Container • Not for model objects (e.g. Orders, Documents, etc.) • Great for resource requirements (e.g. repositories, loggers, etc.) • Really great for plugin-type architecture
  • 46. When to Use a DI Container • Not for model objects (e.g. Orders, Documents, etc.) • Great for resource requirements (e.g. repositories, loggers, etc.) • Really great for plugin-type architecture • But not necessary to use Dependency Injection!
  • 48. Other Considerations • Learning curve
  • 49. Other Considerations • Learning curve • Tracking dependencies
  • 50. Other Considerations • Learning curve • Tracking dependencies • Dependency changes
  • 51. Other Considerations • Learning curve • Tracking dependencies • Dependency changes • Setter/method vs. constructor injection
  • 52. Service Lifetimes • setShared() allows you to specify context persistence • If shared, acts like a singleton • Useful if construction is expensive or state persistence required
  • 54. Thank You! http://bit.ly/rf1pxR git://github.com/neraath/ioc-php-talk.git

Notas del editor

  1. \n
  2. \n
  3. \n
  4. \n
  5. \n
  6. \n
  7. \n
  8. \n
  9. \n
  10. \n
  11. \n
  12. \n
  13. \n
  14. \n
  15. \n
  16. \n
  17. \n
  18. \n
  19. \n
  20. \n
  21. \n
  22. \n
  23. \n
  24. \n
  25. \n
  26. \n
  27. \n
  28. \n
  29. \n
  30. \n
  31. \n
  32. \n
  33. \n
  34. \n
  35. \n
  36. \n
  37. \n
  38. \n
  39. \n
  40. \n
  41. \n
  42. \n
  43. \n
  44. \n
  45. \n
  46. \n
  47. \n
  48. \n
  49. \n