Skip to content

Instantly share code, notes, and snippets.

@odan
Last active August 14, 2017 14:26
Show Gist options
  • Save odan/75d0407c694ffc6a7c4269e2390e08a2 to your computer and use it in GitHub Desktop.
Save odan/75d0407c694ffc6a7c4269e2390e08a2 to your computer and use it in GitHub Desktop.
Dependency Injection with PHP
<?php
class Configuration
{
private $settings = [];
public function __construct(array $settings)
{
$this->settings = $settings;
}
public function getDatabaseConnection()
{
return new DatabaseConnection($this->settings['host'], $this->settings['username'], $this->settings['password']);
}
}
class DatabaseConnection
{
private $host;
private $username;
private $password;
public function __construct($host, $username, $password)
{
$this->host = $host;
$this->username = $username;
$this->password = $password;
}
public function host()
{
return $this->host;
}
public function username()
{
return $this->username;
}
public function password()
{
return $this->password;
}
}
class Factory
{
private $configuration;
private $mysqli;
public function __construct(Configuration $configuration)
{
$this->configuration = $configuration;
}
public function createCustomerRepository() :CustomerRepository
{
return new MysqlCustomerRepository($this->getMysqli());
}
public function createControllerLocator() :ControllerLocator
{
return new ControllerLocator($this);
}
public function createController() :Controller
{
return new Controller($this->createCustomerRepository());
}
private function getMysqli() :MysqliWrapper
{
if ($this->mysqli === null) {
$this->mysqli = $this->createMysqli();
}
return $this->mysqli;
}
private function createMysqli()
{
$databaseConnection = $this->configuration->getDatabaseConnection();
return new MysqliWrapper($databaseConnection->host(), $databaseConnection->username(), $databaseConnection->password());
}
}
class MysqliWrapper
{
}
interface CustomerRepository
{
public function add(Customer $customer);
public function findById(CustomerId $id);
public function commit();
}
class Customer
{
public function promoteToVip()
{
var_dump('vip');
}
}
class CustomerId
{
private $id;
public function __construct($id)
{
$this->id = $id;
}
public function equals(CustomerId $customerId)
{
return $this->id == $customerId->id;
}
public function __toString()
{
return (string)$this->id;
}
}
class MySqlCustomerRepository implements CustomerRepository
{
/**
* @var MysqliWrapper
*/
private $mysqli;
public function __construct(MysqliWrapper $mysqli)
{
$this->mysqli = $mysqli;
}
public function add(Customer $customer)
{
}
public function findById(CustomerId $id)
{
return new Customer;
}
public function commit()
{
}
}
class Controller
{
/**
* @var CustomerRepository
*/
private $customerRepository;
public function __construct(CustomerRepository $customerRepository)
{
$this->customerRepository = $customerRepository;
}
public function execute(HttpRequest $request)
{
$id = $request->get('customer_id');
$customer = $this->customerRepository->findById(new CustomerId($id));
$customer->promoteToVip();
$this->customerRepository->commit();
}
}
class HttpRequest
{
public function get($parameter)
{
return 'the-parameter';
}
}
class ControllerLocator
{
private $factory;
public function __construct(Factory $factory)
{
$this->factory = $factory;
}
public function locateControllerFor($url) :Controller
{
return $this->factory->createController();
}
}
$configuration = new Configuration(parse_ini_file('configuration.ini'));
$factory = new Factory($configuration);
$locator = $factory->createControllerLocator();
$controller = $locator->locateControllerFor('the-url');
$controller->execute(new HttpRequest);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment