SlideShare uma empresa Scribd logo
1 de 105
Baixar para ler offline
Design patterns… revisited for PHP 5.3
Fabien Potencier
http://www.flickr.com/photos/revivaling/4979552548
Serial entrepreneur
Developer by passion
Founder of Sensio
Creator and lead developer of Symfony
http://www.twitter.com/fabpot
http://www.github.com/fabpot
http://fabien.potencier.org/
How does PHP 5.3 change the implementation
of some well-known Design Patterns?
http://www.flickr.com/photos/revivaling/4978949121
http://en.wikipedia.org/wiki/Design_pattern_%28computer_science%29
« A design pattern
is a general reusable solution
to a commonly occurring problem »
http://en.wikipedia.org/wiki/Design_pattern_%28computer_science%29
« By definition, a pattern
must be programmed anew
into each application that uses it. »
The Singleton
http://www.flickr.com/photos/revivaling/4979546114
The Singleton may cause
serious damage to your code!
http://www.flickr.com/photos/mattbell/1696868871
class Singleton
{
function &getInstance()
{
static $instance;
if (!$instance) {
$instance = new Singleton();
}
return $instance;
}
}
$obj =& Singleton::getInstance();
You can still
instantiate the class
directly
The Singleton and PHP 4
class Singleton
{
static private $instance;
private function __construct() {}
static public function getInstance()
{
if (null === self::$instance) {
self::$instance = new self();
}
return self::$instance;
}
final private function __clone() {}
}
$obj = Singleton::getInstance();
do not forget to
override __clone()
The Singleton and PHP 5.0/5.1/5.2
abstract class Singleton
{
private static $instances = array();
final private function __construct()
{
if (isset(self::$instances[get_called_class()])) {
throw new Exception("A ".get_called_class()." instance already exists.");
}
static::initialize();
}
protected function initialize() {}
final public static function getInstance()
{
$class = get_called_class();
if (!isset(self::$instances[$class])) {
self::$instances[$class] = new static();
}
return self::$instances[$class];
}
final private function __clone() {}
}
The Singleton and PHP 5.3
class Foo extends Singleton {}
class Bar extends Singleton {}
$a = Foo::getInstance();
$b = Bar::getInstance();
The Singleton and PHP 5.3
Active Record
…Late Static Binding
http://www.flickr.com/photos/revivaling/4979548952
$article = Article::findByPk(1);
$article = Article::findByTitleAndAuthorId('foo', 1);
class Model
{
static public function getMe()
{
return __CLASS__;
}
}
class Article extends Model {}
echo Article::getMe();
class Model
{
static public function getMe()
{
return get_called_class();
}
}
class Article extends Model {}
echo Article::getMe();
class Model
{
static public function findByPk($id)
{
$table = strtolower(get_called_class());
$sql = "SELECT * FROM $this->table WHERE id = ?";
return $this->db->get($sql, $id);
}
}
class Article extends Model {}
$article = Article::findByPk(1);
class Model
{
static public function __callStatic($method, $arguments)
{
$table = strtolower(get_called_class());
$column = strtolower(substr($method, 6));
$value = $arguments[0];
$sql = "SELECT * FROM $this->table WHERE $column = ?";
return $this->db->get($sql, $value);
}
}
class Article extends Model {}
$article = Article::findByTitle('foo');
This is pseudo code with no proper SQL Injection protection!
http://www.flickr.com/photos/zippy/22748510
The Observer Pattern
http://www.flickr.com/photos/revivaling/4978951341
The Observer pattern allows
to extend or change the behavior of classes
without having to change them
When a method is called
on an object (subject),
it notifies other objects (listeners)
of the event
A Dispatcher is an object
that manages connections
between subjects and listeners
class User
{
function setLanguage($language)
{
$this->language = $language;
}
}
class Translator
{
function setLanguage($language)
{
$this->language = $language;
}
}
Dispatcher Listeners
Translator listens
to  ’language_change’
User notifies
‘language_change’ 
Notifiers
1
2 Calls
all listeners
Translator callback
is called
Dispatcher Listeners
Translator listens
to  ’language_change’
User notifies
‘language_change’ 
Notifiers
1
2 Calls
all listeners
Translator callback
is called
Your class listens
to‘language_change’
Your class callback
is called
$dispatcher = new Dispatcher();
$translator = new Translator($dispatcher);
$user = new User($dispatcher);
$user->setLanguage('fr');
class Translator
{
public function __construct($dispatcher)
{
$listener = array($translator, 'listenLanguageChange');
$dispatcher->connect('language_change', $listener);
}
public function listenLanguageChangeEvent($arguments)
{
$this->setLanguage($arguments['language']);
}
}
A PHP callable
The Event name
class User
{
function setLanguage($language)
{
$this->language = $language;
$this->dispatcher->notify('language_change',
array('language' => $language));
}
}
// register the listener with the dispatcher
$dispatcher = new Dispatcher(array(
'foo' => $listener,
));
// notify the event anywhere
$dispatcher->notify(
'foo',
array('name' => 'Fabien')
);
A listener can be any PHP callable
class Dispatcher
{
function __construct($map)
{
$this->map = $map;
}
function notify($name, $args = array())
{
call_user_func($this->map[$name], $args);
}
}
A PHP callable
class Dispatcher
{
function __construct($map)
{
$this->map = $map;
}
function notify($name, $args = array())
{
$this->map[$name]($rags);
}
} An anonymous function
// a function
function foo($args)
{
echo "Hello {$args['name']}n";
};
$listener = 'foo';
// an anonymous function
$listener = function ($args)
{
echo "Hello {$args['name']}n";
};
// register the listener with the dispatcher
$dispatcher = new Dispatcher(array(
'foo' => function ($args)
{
echo "Hello {$args['name']}n";
},
));
// notify the event anywhere
$dispatcher->notify(
'foo',
array('name' => 'Fabien')
);
$dispatcher = new Dispatcher(array(
'foo' => $listener
));
class Dispatcher
{
function connect($name, $listener)
{
if (!isset($this->map[$name])) {
$this->map[$name] = array();
}
$this->map[$name][] = $listener;
}
}
$l1 = function ($args)
{
echo "Hello1 {$args['name']}?n";
};
$l2 = function ($args)
{
echo "Hello2 {$args['name']}?n";
};
$listener = new Listeners($l1, $l2);
$dispatcher = new Dispatcher(array(
'foo' => $listener
));
$dispatcher = new Dispatcher(array(
'foo' => new Listeners($l1, $l2)
));
$listener = new Listeners($l1, $l2);
$listeners($args);
class Listeners
{
function __construct()
{
$this->listeners = func_get_args();
}
function __invoke($args = array())
{
foreach ($this->listeners as $listener) {
$listener($args);
}
}
}
Makes the object callable
Template View
http://www.flickr.com/photos/revivaling/4979557230
Hello {{ name }}
echo render('Hello {{ name }}!', array('name' => 'Fabien'));
echo render(
file_get_contents(__DIR__.'/template.php'),
array('name' => 'Fabien')
);
function render($template, $arguments)
{
$evaluator = function ($match) use ($arguments)
{
if (isset($arguments[$match[1]])) {
return $arguments[$match[1]];
}
return $match[1];
};
return preg_replace_callback('/{{s*(.+?)s*}}/',
$evaluator, $template);
}
Dependency Injector
http://www.flickr.com/photos/revivaling/4978942907
http://www.picoinjector.org/injection.html
« Dependency Injection is where components
are given their dependencies
through their constructors, methods, or directly into fields »
In most web applications, you need to manage the user preferences
–  The user language
–  Whether the user is authenticated or not
–  …
This can be done with a User object
–  setLanguage(), getLanguage()
–  setAuthenticated(), isAuthenticated()
–  …
The User information
need to be persisted
between HTTP requests
We use the PHP session for the Storage
class SessionStorage
{
function __construct($cookieName = 'PHP_SESS_ID')
{
session_name($cookieName);
session_start();
}
function set($key, $value)
{
$_SESSION[$key] = $value;
}
// ...
}
class User
{
protected $storage;
function __construct()
{
$this->storage = new SessionStorage();
}
function setLanguage($language)
{
$this->storage->set('language', $language);
}
// ...
}
$user = new User();
Very easy
to use
Very hard to
customize
class User
{
protected $storage;
function __construct($storage)
{
$this->storage = $storage;
}
}
$storage = new SessionStorage();
$user = new User($storage);
Slightly more
difficult to use
Very easy to
customize
That’s Dependency Injection
Nothing more
Instead of harcoding
the Storage dependency
inside the User class constructor
Inject the Storage dependency
in the User object
A Dependency Injector
Describes objects
and their dependencies
Instantiates and configures
objects on-demand
An injector
SHOULD be able to manage
ANY PHP object (POPO)
The objects MUST not know
that they are managed
by the injector
•  Parameters
–  The SessionStorage implementation we want to use (the class name)
–  The session name
•  Objects
–  SessionStorage
–  User
•  Dependencies
–  User depends on a SessionStorage implementation
Let’s build a simple injector
with PHP 5.3
http://www.flickr.com/photos/22750018@N05/4531762220/
Dependency Injector: Parameters
http://www.flickr.com/photos/revivaling/4979546964
class Injector
{
protected $parameters = array();
public function setParameter($key, $value)
{
$this->parameters[$key] = $value;
}
public function getParameter($key)
{
return $this->parameters[$key];
}
}
$injector = new Injector();
$injector->setParameter('session_name', 'SESSION_ID');
$injector->setParameter('storage_class', 'SessionStorage');
$class = $injector->getParameter('storage_class');
$sessionStorage = new $class($injector->getParameter('session_name'));
$user = new User($sessionStorage);
Decoupling
Customization
Objects creation
class Injector
{
protected $parameters = array();
public function __set($key, $value)
{
$this->parameters[$key] = $value;
}
public function __get($key)
{
return $this->parameters[$key];
}
}
Using PHP
magic methods
$injector = new Injector();
$injector->session_name = 'SESSION_ID';
$injector->storage_class = 'SessionStorage';
$sessionStorage = new $injector->storage_class($injector->session_name);
$user = new User($sessionStorage);
Interface
is cleaner
Dependency Injector: Objects
http://www.flickr.com/photos/revivaling/4979547636
We need a way to describe how to create objects,
without actually instantiating anything!
Anonymous functions to the rescue!
class Injector
{
protected $parameters = array();
protected $objects = array();
public function __set($key, $value)
{
$this->parameters[$key] = $value;
}
public function __get($key)
{
return $this->parameters[$key];
}
public function setService($key, Closure $service)
{
$this->objects[$key] = $service;
}
public function getService($key)
{
return $this->objects[$key]($this);
}
}
Store a lambda
able to create the
object on-demand
Ask the closure to create
the object and pass the
current injector
$injector = new Injector();
$injector->session_name = 'SESSION_ID';
$injector->storage_class = 'SessionStorage';
$injector->setService('user', function ($c)
{
return new User($c->getService('storage'));
});
$injector->setService('storage', function ($c)
{
return new $c->storage_class($c->session_name);
});
$user = $injector->getService('user');
Creating the User
is now as easy as before
Description
class Injector
{
protected $values = array();
function __set($id, $value)
{
$this->values[$id] = $value;
}
function __get($id)
{
if (is_callable($this->values[$id])) {
return $this->values[$id]($this);
} else {
return $this->values[$id];
}
}
}
Simplify the code
$injector = new Injector();
$injector->session_name = 'SESSION_ID';
$injector->storage_class = 'SessionStorage';
$injector->user = function ($c)
{
return new User($c->storage);
};
$injector->storage = function ($c)
{
return new $c->storage_class($c->session_name);
};
$user = $injector->user;
Unified interface
Dependency Injector: Scope
http://www.flickr.com/photos/revivaling/4979545016
For some objects, like the user,
the injector must always
return the same instance
spl_object_hash($injector->user)
!==
spl_object_hash($injector->user)
$injector->user = function ($c)
{
static $user;
if (is_null($user)) {
$user = new User($c->storage);
}
return $user;
};
spl_object_hash($injector->user)
===
spl_object_hash($injector->user)
$injector->user = $injector->asShared(function ($c)
{
return new User($c->storage);
});
function asShared(Closure $lambda)
{
return function ($injector) use ($lambda)
{
static $object;
if (is_null($object)) {
$object = $lambda($injector);
}
return $object;
};
}
class Injector
{
protected $values = array();
function __set($id, $value)
{
$this->values[$id] = $value;
}
function __get($id)
{
if (!isset($this->values[$id])) {
throw new InvalidArgumentException(sprintf('Value "%s" is not
defined.', $id));
}
if (is_callable($this->values[$id])) {
return $this->values[$id]($this);
} else {
return $this->values[$id];
}
}
}
Error management
class Injector
{
protected $values = array();
function __set($id, $value)
{
$this->values[$id] = $value;
}
function __get($id)
{
if (!isset($this->values[$id])) {
throw new InvalidArgumentException(sprintf('Value "%s" is not defined.', $id));
}
if (is_callable($this->values[$id])) {
return $this->values[$id]($this);
} else {
return $this->values[$id];
}
}
function asShared($callable)
{
return function ($c) use ($callable)
{
static $object;
if (is_null($object)) {
$object = $callable($c);
}
return $object;
};
}
}
40 LOC for a fully-
featured injector
Twittee: A Dependency Injection Container in a tweet
•  Implementation does not use PHP 5.3
•  Its usage needs PHP 5.3
class Container {
protected $s=array();
function __set($k, $c) { $this->s[$k]=$c; }
function __get($k) { return $this->s[$k]($this); }
}
twittee.org
Anonymous Functions
Closures
Late Static Binding
__invoke()
…
I’m NOT advocating
the usage of lambdas everywhere
This presentation was about
showing how they work
on practical examples
Questions?
Sensio S.A.
92-98, boulevard Victor Hugo
92 115 Clichy Cedex
FRANCE
Tél. : +33 1 40 99 80 80
Contact
Fabien Potencier
fabien.potencier at sensio.com
http://www.sensiolabs.com/
http://www.symfony-project.org/
http://fabien.potencier.org/
Interlude
…Anonymous Functions
http://www.flickr.com/photos/gregory_bastien/2565132371
An anonymous function
is a function
defined on the fly (no name)
function () { echo 'Hello world!'; };
Can be stored in a variable
$hello = function () { echo 'Hello world!'; };
… to be used later on
$hello();
call_user_func($hello);
… or can be passed as a function argument
function foo(Closure $func)
{
$func();
}
foo($hello);
Fonctions anonymes
$hello = function ($name) { echo 'Hello '.$name; };
$hello('Fabien');
call_user_func($hello, 'Fabien');
Can take arguments
Fonctions anonymes
function foo(Closure $func, $name)
{
$func($name);
}
foo($hello, 'Fabien');
When is it useful?
array_*
Greatly simplify usage of some array_* functions
array_map()
array_reduce()
array_filter()
class Article
{
public function __construct($title)
{
$this->title = $title;
}
public function getTitle()
{
return $this->title;
}
}
How to get an array of all article titles?
$articles = array(
new Article('PHP UK - part 1'),
new Article('PHP UK - part 2'),
new Article('See you next year!'),
);
$titles = array();
foreach ($articles as $article)
{
$titles[] = $article->getTitle();
}
$titles = array_map(
create_function('$article', 'return $article->getTitle();'),
$articles
);
$titles = array_map(
function ($article) { return $article->getTitle(); },
$articles
);
$titles = array();
foreach ($articles as $article)
{
$titles[] = $article->getTitle();
}
100100
$titles = array_map(create_function('$article', 'return $article->getTitle();'), $articles);
1800300
$titles = array_map(function ($article) { return $article->getTitle(); }, $articles);
200100
memory speed
$mapper = function ($article) { return $article->getTitle(); };
$titles = array_map($mapper, $articles);
180100
$mapper = function ($article) {
return $article->getTitle();
};
$titles = array_map($mapper, $articles);
$mapper = function ($article) {
return $article->getAuthor();
};
$authors = array_map($mapper, $articles);
A closure is a lambda
that remembers the context
of its creation…
$mapper = function ($method)
{
return function ($article) use($method)
{
return $article->$method();
};
};
$method = 'getTitle';
$mapper = function ($article) use($method)
{
return $article->$method();
};
$method = 'getAuthor';
$titles = array_map($mapper, $articles);
$titleMapper = $mapper('getTitle');
$titles = array_map($titleMapper, $articles);
$authorMapper = $mapper('getAuthor');
$authors = array_map($authorMapper, $articles);
$titles = array_map($mapper('getTitle'), $articles);
$authors = array_map($mapper('getAuthor'), $articles);

Mais conteúdo relacionado

Mais procurados

Mais procurados (20)

React/Redux
React/ReduxReact/Redux
React/Redux
 
Escalando API's com NodeJS, Docker e RabbitMQ
Escalando API's com NodeJS, Docker e RabbitMQEscalando API's com NodeJS, Docker e RabbitMQ
Escalando API's com NodeJS, Docker e RabbitMQ
 
JavaScript Object Oriented Programming Cheat Sheet
JavaScript Object Oriented Programming Cheat SheetJavaScript Object Oriented Programming Cheat Sheet
JavaScript Object Oriented Programming Cheat Sheet
 
Node.js Express Framework
Node.js Express FrameworkNode.js Express Framework
Node.js Express Framework
 
Hotel Object Oriented Analysis
Hotel Object Oriented AnalysisHotel Object Oriented Analysis
Hotel Object Oriented Analysis
 
HTML/CSS/java Script/Jquery
HTML/CSS/java Script/JqueryHTML/CSS/java Script/Jquery
HTML/CSS/java Script/Jquery
 
Expressjs
ExpressjsExpressjs
Expressjs
 
What is New in DMN 1.4
What is New in DMN 1.4What is New in DMN 1.4
What is New in DMN 1.4
 
Jmenubar
JmenubarJmenubar
Jmenubar
 
Principios orientacion-objetos
Principios orientacion-objetosPrincipios orientacion-objetos
Principios orientacion-objetos
 
ASP.NET MVC Presentation
ASP.NET MVC PresentationASP.NET MVC Presentation
ASP.NET MVC Presentation
 
Introduction to React
Introduction to ReactIntroduction to React
Introduction to React
 
Express JS Middleware Tutorial
Express JS Middleware TutorialExpress JS Middleware Tutorial
Express JS Middleware Tutorial
 
Angular
AngularAngular
Angular
 
OAuth big picture
OAuth big pictureOAuth big picture
OAuth big picture
 
Introdução ao Java Swing (Interface)
Introdução ao Java Swing (Interface)Introdução ao Java Swing (Interface)
Introdução ao Java Swing (Interface)
 
Angular 2.0 forms
Angular 2.0 formsAngular 2.0 forms
Angular 2.0 forms
 
AngularJS
AngularJSAngularJS
AngularJS
 
REST API Design & Development
REST API Design & DevelopmentREST API Design & Development
REST API Design & Development
 
Chapter 4 functions, views, indexing
Chapter 4  functions, views, indexingChapter 4  functions, views, indexing
Chapter 4 functions, views, indexing
 

Destaque

Object Oriented Design Patterns for PHP
Object Oriented Design Patterns for PHPObject Oriented Design Patterns for PHP
Object Oriented Design Patterns for PHPRobertGonzalez
 
Common design patterns in php
Common design patterns in phpCommon design patterns in php
Common design patterns in phpDavid Stockton
 
Design patterns in PHP - PHP TEAM
Design patterns in PHP - PHP TEAMDesign patterns in PHP - PHP TEAM
Design patterns in PHP - PHP TEAMNishant Shrivastava
 
Your first 5 PHP design patterns - ThatConference 2012
Your first 5 PHP design patterns - ThatConference 2012Your first 5 PHP design patterns - ThatConference 2012
Your first 5 PHP design patterns - ThatConference 2012Aaron Saray
 
Dependency injection in PHP 5.3/5.4
Dependency injection in PHP 5.3/5.4Dependency injection in PHP 5.3/5.4
Dependency injection in PHP 5.3/5.4Fabien Potencier
 
The state of Symfony2 - SymfonyDay 2010
The state of Symfony2 - SymfonyDay 2010The state of Symfony2 - SymfonyDay 2010
The state of Symfony2 - SymfonyDay 2010Fabien Potencier
 
Dependency injection - phpday 2010
Dependency injection - phpday 2010Dependency injection - phpday 2010
Dependency injection - phpday 2010Fabien Potencier
 
PHP security audits
PHP security auditsPHP security audits
PHP security auditsDamien Seguy
 
Continuous Improvement in PHP projects
Continuous Improvement in PHP projectsContinuous Improvement in PHP projects
Continuous Improvement in PHP projectsMayflower GmbH
 
Go OO! - Real-life Design Patterns in PHP 5
Go OO! - Real-life Design Patterns in PHP 5Go OO! - Real-life Design Patterns in PHP 5
Go OO! - Real-life Design Patterns in PHP 5Stephan Schmidt
 
Mondongo, un ODM para PHP y MongoDB
Mondongo, un ODM para PHP y MongoDBMondongo, un ODM para PHP y MongoDB
Mondongo, un ODM para PHP y MongoDBpablodip
 
Database version control without pain - the PHP Barcelona version
Database version control without pain - the PHP Barcelona versionDatabase version control without pain - the PHP Barcelona version
Database version control without pain - the PHP Barcelona versionHarrie Verveer
 
Introduction to Twitter's Bootstrap 2
Introduction to Twitter's Bootstrap 2Introduction to Twitter's Bootstrap 2
Introduction to Twitter's Bootstrap 2Julien Renaux
 
News of the Symfony2 World
News of the Symfony2 WorldNews of the Symfony2 World
News of the Symfony2 WorldFabien Potencier
 

Destaque (20)

Object Oriented Design Patterns for PHP
Object Oriented Design Patterns for PHPObject Oriented Design Patterns for PHP
Object Oriented Design Patterns for PHP
 
Common design patterns in php
Common design patterns in phpCommon design patterns in php
Common design patterns in php
 
PHP 5.3 in practice
PHP 5.3 in practicePHP 5.3 in practice
PHP 5.3 in practice
 
Design patterns in PHP - PHP TEAM
Design patterns in PHP - PHP TEAMDesign patterns in PHP - PHP TEAM
Design patterns in PHP - PHP TEAM
 
Your first 5 PHP design patterns - ThatConference 2012
Your first 5 PHP design patterns - ThatConference 2012Your first 5 PHP design patterns - ThatConference 2012
Your first 5 PHP design patterns - ThatConference 2012
 
Design patterns in PHP
Design patterns in PHPDesign patterns in PHP
Design patterns in PHP
 
Varnish
VarnishVarnish
Varnish
 
Object Oriented CSS
Object Oriented CSSObject Oriented CSS
Object Oriented CSS
 
Dependency injection in PHP 5.3/5.4
Dependency injection in PHP 5.3/5.4Dependency injection in PHP 5.3/5.4
Dependency injection in PHP 5.3/5.4
 
The state of Symfony2 - SymfonyDay 2010
The state of Symfony2 - SymfonyDay 2010The state of Symfony2 - SymfonyDay 2010
The state of Symfony2 - SymfonyDay 2010
 
Symfony2 - OSIDays 2010
Symfony2 - OSIDays 2010Symfony2 - OSIDays 2010
Symfony2 - OSIDays 2010
 
Dependency injection - phpday 2010
Dependency injection - phpday 2010Dependency injection - phpday 2010
Dependency injection - phpday 2010
 
PHP security audits
PHP security auditsPHP security audits
PHP security audits
 
Continuous Improvement in PHP projects
Continuous Improvement in PHP projectsContinuous Improvement in PHP projects
Continuous Improvement in PHP projects
 
Go OO! - Real-life Design Patterns in PHP 5
Go OO! - Real-life Design Patterns in PHP 5Go OO! - Real-life Design Patterns in PHP 5
Go OO! - Real-life Design Patterns in PHP 5
 
Refactoring
RefactoringRefactoring
Refactoring
 
Mondongo, un ODM para PHP y MongoDB
Mondongo, un ODM para PHP y MongoDBMondongo, un ODM para PHP y MongoDB
Mondongo, un ODM para PHP y MongoDB
 
Database version control without pain - the PHP Barcelona version
Database version control without pain - the PHP Barcelona versionDatabase version control without pain - the PHP Barcelona version
Database version control without pain - the PHP Barcelona version
 
Introduction to Twitter's Bootstrap 2
Introduction to Twitter's Bootstrap 2Introduction to Twitter's Bootstrap 2
Introduction to Twitter's Bootstrap 2
 
News of the Symfony2 World
News of the Symfony2 WorldNews of the Symfony2 World
News of the Symfony2 World
 

Semelhante a Design patterns revisited with PHP 5.3

Demystifying Object-Oriented Programming #phpbnl18
Demystifying Object-Oriented Programming #phpbnl18Demystifying Object-Oriented Programming #phpbnl18
Demystifying Object-Oriented Programming #phpbnl18Alena Holligan
 
EPHPC Webinar Slides: Unit Testing by Arthur Purnama
EPHPC Webinar Slides: Unit Testing by Arthur PurnamaEPHPC Webinar Slides: Unit Testing by Arthur Purnama
EPHPC Webinar Slides: Unit Testing by Arthur PurnamaEnterprise PHP Center
 
PHP: 4 Design Patterns to Make Better Code
PHP: 4 Design Patterns to Make Better CodePHP: 4 Design Patterns to Make Better Code
PHP: 4 Design Patterns to Make Better CodeSWIFTotter Solutions
 
What's New In Laravel 5
What's New In Laravel 5What's New In Laravel 5
What's New In Laravel 5Darren Craig
 
Intro to OOP PHP and Github
Intro to OOP PHP and GithubIntro to OOP PHP and Github
Intro to OOP PHP and GithubJo Erik San Jose
 
Osiąganie mądrej architektury z Symfony2
Osiąganie mądrej architektury z Symfony2 Osiąganie mądrej architektury z Symfony2
Osiąganie mądrej architektury z Symfony2 3camp
 
Demystifying Object-Oriented Programming - ZendCon 2016
Demystifying Object-Oriented Programming - ZendCon 2016Demystifying Object-Oriented Programming - ZendCon 2016
Demystifying Object-Oriented Programming - ZendCon 2016Alena Holligan
 
Drupaljam xl 2019 presentation multilingualism makes better programmers
Drupaljam xl 2019 presentation   multilingualism makes better programmersDrupaljam xl 2019 presentation   multilingualism makes better programmers
Drupaljam xl 2019 presentation multilingualism makes better programmersAlexander Varwijk
 
Workshop quality assurance for php projects tek12
Workshop quality assurance for php projects tek12Workshop quality assurance for php projects tek12
Workshop quality assurance for php projects tek12Michelangelo van Dam
 
Beyond symfony 1.2 (Symfony Camp 2008)
Beyond symfony 1.2 (Symfony Camp 2008)Beyond symfony 1.2 (Symfony Camp 2008)
Beyond symfony 1.2 (Symfony Camp 2008)Fabien Potencier
 
Demystifying Object-Oriented Programming - PHP[tek] 2017
Demystifying Object-Oriented Programming - PHP[tek] 2017Demystifying Object-Oriented Programming - PHP[tek] 2017
Demystifying Object-Oriented Programming - PHP[tek] 2017Alena Holligan
 
CICON2010: Adam Griffiths - CodeIgniter 2
CICON2010: Adam Griffiths - CodeIgniter 2CICON2010: Adam Griffiths - CodeIgniter 2
CICON2010: Adam Griffiths - CodeIgniter 2CodeIgniter Conference
 
10 PHP Design Patterns #burningkeyboards
10 PHP Design Patterns #burningkeyboards10 PHP Design Patterns #burningkeyboards
10 PHP Design Patterns #burningkeyboardsDenis Ristic
 
Lean Php Presentation
Lean Php PresentationLean Php Presentation
Lean Php PresentationAlan Pinstein
 
TYPO3 Flow 2.0 (International PHP Conference 2013)
TYPO3 Flow 2.0 (International PHP Conference 2013)TYPO3 Flow 2.0 (International PHP Conference 2013)
TYPO3 Flow 2.0 (International PHP Conference 2013)Robert Lemke
 
Demystifying Object-Oriented Programming - Lone Star PHP
Demystifying Object-Oriented Programming - Lone Star PHPDemystifying Object-Oriented Programming - Lone Star PHP
Demystifying Object-Oriented Programming - Lone Star PHPAlena Holligan
 

Semelhante a Design patterns revisited with PHP 5.3 (20)

Demystifying Object-Oriented Programming #phpbnl18
Demystifying Object-Oriented Programming #phpbnl18Demystifying Object-Oriented Programming #phpbnl18
Demystifying Object-Oriented Programming #phpbnl18
 
EPHPC Webinar Slides: Unit Testing by Arthur Purnama
EPHPC Webinar Slides: Unit Testing by Arthur PurnamaEPHPC Webinar Slides: Unit Testing by Arthur Purnama
EPHPC Webinar Slides: Unit Testing by Arthur Purnama
 
Design attern in php
Design attern in phpDesign attern in php
Design attern in php
 
PHP: 4 Design Patterns to Make Better Code
PHP: 4 Design Patterns to Make Better CodePHP: 4 Design Patterns to Make Better Code
PHP: 4 Design Patterns to Make Better Code
 
What's New In Laravel 5
What's New In Laravel 5What's New In Laravel 5
What's New In Laravel 5
 
Intro to OOP PHP and Github
Intro to OOP PHP and GithubIntro to OOP PHP and Github
Intro to OOP PHP and Github
 
Best practices tekx
Best practices tekxBest practices tekx
Best practices tekx
 
Osiąganie mądrej architektury z Symfony2
Osiąganie mądrej architektury z Symfony2 Osiąganie mądrej architektury z Symfony2
Osiąganie mądrej architektury z Symfony2
 
Demystifying Object-Oriented Programming - ZendCon 2016
Demystifying Object-Oriented Programming - ZendCon 2016Demystifying Object-Oriented Programming - ZendCon 2016
Demystifying Object-Oriented Programming - ZendCon 2016
 
Drupaljam xl 2019 presentation multilingualism makes better programmers
Drupaljam xl 2019 presentation   multilingualism makes better programmersDrupaljam xl 2019 presentation   multilingualism makes better programmers
Drupaljam xl 2019 presentation multilingualism makes better programmers
 
Workshop quality assurance for php projects tek12
Workshop quality assurance for php projects tek12Workshop quality assurance for php projects tek12
Workshop quality assurance for php projects tek12
 
Beyond symfony 1.2 (Symfony Camp 2008)
Beyond symfony 1.2 (Symfony Camp 2008)Beyond symfony 1.2 (Symfony Camp 2008)
Beyond symfony 1.2 (Symfony Camp 2008)
 
Demystifying Object-Oriented Programming - PHP[tek] 2017
Demystifying Object-Oriented Programming - PHP[tek] 2017Demystifying Object-Oriented Programming - PHP[tek] 2017
Demystifying Object-Oriented Programming - PHP[tek] 2017
 
CICON2010: Adam Griffiths - CodeIgniter 2
CICON2010: Adam Griffiths - CodeIgniter 2CICON2010: Adam Griffiths - CodeIgniter 2
CICON2010: Adam Griffiths - CodeIgniter 2
 
10 PHP Design Patterns #burningkeyboards
10 PHP Design Patterns #burningkeyboards10 PHP Design Patterns #burningkeyboards
10 PHP Design Patterns #burningkeyboards
 
OOP in PHP
OOP in PHPOOP in PHP
OOP in PHP
 
Lean Php Presentation
Lean Php PresentationLean Php Presentation
Lean Php Presentation
 
Only oop
Only oopOnly oop
Only oop
 
TYPO3 Flow 2.0 (International PHP Conference 2013)
TYPO3 Flow 2.0 (International PHP Conference 2013)TYPO3 Flow 2.0 (International PHP Conference 2013)
TYPO3 Flow 2.0 (International PHP Conference 2013)
 
Demystifying Object-Oriented Programming - Lone Star PHP
Demystifying Object-Oriented Programming - Lone Star PHPDemystifying Object-Oriented Programming - Lone Star PHP
Demystifying Object-Oriented Programming - Lone Star PHP
 

Mais de Fabien Potencier

Dependency injection-zendcon-2010
Dependency injection-zendcon-2010Dependency injection-zendcon-2010
Dependency injection-zendcon-2010Fabien Potencier
 
Dependency Injection IPC 201
Dependency Injection IPC 201Dependency Injection IPC 201
Dependency Injection IPC 201Fabien Potencier
 
Caching on the Edge with Symfony2
Caching on the Edge with Symfony2Caching on the Edge with Symfony2
Caching on the Edge with Symfony2Fabien Potencier
 
Unit and Functional Testing with Symfony2
Unit and Functional Testing with Symfony2Unit and Functional Testing with Symfony2
Unit and Functional Testing with Symfony2Fabien Potencier
 
Dependency Injection - ConFoo 2010
Dependency Injection - ConFoo 2010Dependency Injection - ConFoo 2010
Dependency Injection - ConFoo 2010Fabien Potencier
 
Dependency Injection with PHP 5.3
Dependency Injection with PHP 5.3Dependency Injection with PHP 5.3
Dependency Injection with PHP 5.3Fabien Potencier
 
Dependency Injection with PHP and PHP 5.3
Dependency Injection with PHP and PHP 5.3Dependency Injection with PHP and PHP 5.3
Dependency Injection with PHP and PHP 5.3Fabien Potencier
 
Symfony Components 2.0 on PHP 5.3
Symfony Components 2.0 on PHP 5.3Symfony Components 2.0 on PHP 5.3
Symfony Components 2.0 on PHP 5.3Fabien Potencier
 
Symfony2 San Francisco Meetup 2009
Symfony2 San Francisco Meetup 2009Symfony2 San Francisco Meetup 2009
Symfony2 San Francisco Meetup 2009Fabien Potencier
 
Symfony And Zend Framework Together 2009
Symfony And Zend Framework Together 2009Symfony And Zend Framework Together 2009
Symfony And Zend Framework Together 2009Fabien Potencier
 

Mais de Fabien Potencier (20)

Look beyond PHP
Look beyond PHPLook beyond PHP
Look beyond PHP
 
Dependency injection-zendcon-2010
Dependency injection-zendcon-2010Dependency injection-zendcon-2010
Dependency injection-zendcon-2010
 
Caching on the Edge
Caching on the EdgeCaching on the Edge
Caching on the Edge
 
PhpBB meets Symfony2
PhpBB meets Symfony2PhpBB meets Symfony2
PhpBB meets Symfony2
 
Symfony2 - WebExpo 2010
Symfony2 - WebExpo 2010Symfony2 - WebExpo 2010
Symfony2 - WebExpo 2010
 
Symfony2 - WebExpo 2010
Symfony2 - WebExpo 2010Symfony2 - WebExpo 2010
Symfony2 - WebExpo 2010
 
Dependency Injection IPC 201
Dependency Injection IPC 201Dependency Injection IPC 201
Dependency Injection IPC 201
 
Caching on the Edge with Symfony2
Caching on the Edge with Symfony2Caching on the Edge with Symfony2
Caching on the Edge with Symfony2
 
Unit and Functional Testing with Symfony2
Unit and Functional Testing with Symfony2Unit and Functional Testing with Symfony2
Unit and Functional Testing with Symfony2
 
Dependency Injection - ConFoo 2010
Dependency Injection - ConFoo 2010Dependency Injection - ConFoo 2010
Dependency Injection - ConFoo 2010
 
Dependency Injection
Dependency InjectionDependency Injection
Dependency Injection
 
Symfony Components
Symfony ComponentsSymfony Components
Symfony Components
 
Symfony2 revealed
Symfony2 revealedSymfony2 revealed
Symfony2 revealed
 
Dependency Injection with PHP 5.3
Dependency Injection with PHP 5.3Dependency Injection with PHP 5.3
Dependency Injection with PHP 5.3
 
Dependency Injection with PHP and PHP 5.3
Dependency Injection with PHP and PHP 5.3Dependency Injection with PHP and PHP 5.3
Dependency Injection with PHP and PHP 5.3
 
Symfony Components 2.0 on PHP 5.3
Symfony Components 2.0 on PHP 5.3Symfony Components 2.0 on PHP 5.3
Symfony Components 2.0 on PHP 5.3
 
Playing With PHP 5.3
Playing With PHP 5.3Playing With PHP 5.3
Playing With PHP 5.3
 
Symfony 2.0 on PHP 5.3
Symfony 2.0 on PHP 5.3Symfony 2.0 on PHP 5.3
Symfony 2.0 on PHP 5.3
 
Symfony2 San Francisco Meetup 2009
Symfony2 San Francisco Meetup 2009Symfony2 San Francisco Meetup 2009
Symfony2 San Francisco Meetup 2009
 
Symfony And Zend Framework Together 2009
Symfony And Zend Framework Together 2009Symfony And Zend Framework Together 2009
Symfony And Zend Framework Together 2009
 

Último

Abdul Kader Baba- Managing Cybersecurity Risks and Compliance Requirements i...
Abdul Kader Baba- Managing Cybersecurity Risks  and Compliance Requirements i...Abdul Kader Baba- Managing Cybersecurity Risks  and Compliance Requirements i...
Abdul Kader Baba- Managing Cybersecurity Risks and Compliance Requirements i...itnewsafrica
 
Top 10 Hubspot Development Companies in 2024
Top 10 Hubspot Development Companies in 2024Top 10 Hubspot Development Companies in 2024
Top 10 Hubspot Development Companies in 2024TopCSSGallery
 
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
 
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
 
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 Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptxThe Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptxLoriGlavin3
 
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
 
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
 
Genislab builds better products and faster go-to-market with Lean project man...
Genislab builds better products and faster go-to-market with Lean project man...Genislab builds better products and faster go-to-market with Lean project man...
Genislab builds better products and faster go-to-market with Lean project man...Farhan Tariq
 
Design pattern talk by Kaya Weers - 2024 (v2)
Design pattern talk by Kaya Weers - 2024 (v2)Design pattern talk by Kaya Weers - 2024 (v2)
Design pattern talk by Kaya Weers - 2024 (v2)Kaya Weers
 
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...Wes McKinney
 
Data governance with Unity Catalog Presentation
Data governance with Unity Catalog PresentationData governance with Unity Catalog Presentation
Data governance with Unity Catalog PresentationKnoldus Inc.
 
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
 
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
 
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
 
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...Alkin Tezuysal
 
2024 April Patch Tuesday
2024 April Patch Tuesday2024 April Patch Tuesday
2024 April Patch TuesdayIvanti
 
Zeshan Sattar- Assessing the skill requirements and industry expectations for...
Zeshan Sattar- Assessing the skill requirements and industry expectations for...Zeshan Sattar- Assessing the skill requirements and industry expectations for...
Zeshan Sattar- Assessing the skill requirements and industry expectations for...itnewsafrica
 
How to write a Business Continuity Plan
How to write a Business Continuity PlanHow to write a Business Continuity Plan
How to write a Business Continuity PlanDatabarracks
 
MuleSoft Online Meetup Group - B2B Crash Course: Release SparkNotes
MuleSoft Online Meetup Group - B2B Crash Course: Release SparkNotesMuleSoft Online Meetup Group - B2B Crash Course: Release SparkNotes
MuleSoft Online Meetup Group - B2B Crash Course: Release SparkNotesManik S Magar
 

Último (20)

Abdul Kader Baba- Managing Cybersecurity Risks and Compliance Requirements i...
Abdul Kader Baba- Managing Cybersecurity Risks  and Compliance Requirements i...Abdul Kader Baba- Managing Cybersecurity Risks  and Compliance Requirements i...
Abdul Kader Baba- Managing Cybersecurity Risks and Compliance Requirements i...
 
Top 10 Hubspot Development Companies in 2024
Top 10 Hubspot Development Companies in 2024Top 10 Hubspot Development Companies in 2024
Top 10 Hubspot Development Companies in 2024
 
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
 
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
 
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 Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptxThe Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
 
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
 
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
 
Genislab builds better products and faster go-to-market with Lean project man...
Genislab builds better products and faster go-to-market with Lean project man...Genislab builds better products and faster go-to-market with Lean project man...
Genislab builds better products and faster go-to-market with Lean project man...
 
Design pattern talk by Kaya Weers - 2024 (v2)
Design pattern talk by Kaya Weers - 2024 (v2)Design pattern talk by Kaya Weers - 2024 (v2)
Design pattern talk by Kaya Weers - 2024 (v2)
 
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
 
Data governance with Unity Catalog Presentation
Data governance with Unity Catalog PresentationData governance with Unity Catalog Presentation
Data governance with Unity Catalog Presentation
 
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.
 
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
 
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
 
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
 
2024 April Patch Tuesday
2024 April Patch Tuesday2024 April Patch Tuesday
2024 April Patch Tuesday
 
Zeshan Sattar- Assessing the skill requirements and industry expectations for...
Zeshan Sattar- Assessing the skill requirements and industry expectations for...Zeshan Sattar- Assessing the skill requirements and industry expectations for...
Zeshan Sattar- Assessing the skill requirements and industry expectations for...
 
How to write a Business Continuity Plan
How to write a Business Continuity PlanHow to write a Business Continuity Plan
How to write a Business Continuity Plan
 
MuleSoft Online Meetup Group - B2B Crash Course: Release SparkNotes
MuleSoft Online Meetup Group - B2B Crash Course: Release SparkNotesMuleSoft Online Meetup Group - B2B Crash Course: Release SparkNotes
MuleSoft Online Meetup Group - B2B Crash Course: Release SparkNotes
 

Design patterns revisited with PHP 5.3