From 82698364acd09003014c6a08a30177093873703f Mon Sep 17 00:00:00 2001 From: Thibaud Fabre Date: Thu, 10 Dec 2015 18:05:38 +0100 Subject: [PATCH 1/3] Make TeleporterContainer a standalone container --- src/Resource/TeleporterContainer.php | 41 +++++++++++++++++++++------- 1 file changed, 31 insertions(+), 10 deletions(-) diff --git a/src/Resource/TeleporterContainer.php b/src/Resource/TeleporterContainer.php index e9db19b..a3e0797 100644 --- a/src/Resource/TeleporterContainer.php +++ b/src/Resource/TeleporterContainer.php @@ -20,10 +20,20 @@ /** * A container of TeleporterInterface */ -class TeleporterContainer extends \Pimple +class TeleporterContainer { /** - * Returns the appropriate TeleporterInterface given a Resource + * @var TeleporterInterface[] + */ + private $teleporters = array(); + + /** + * @var callable[] + */ + private $factories = array(); + + /** + * Returns the appropriate TeleporterInterface for a given Resource * * @param Resource $resource * @return TeleporterInterface @@ -39,7 +49,7 @@ public function fromResource(Resource $resource) if (!isset($data['scheme']) || 'file' === $data['scheme']) { $teleporter = 'local-teleporter'; - } elseif (in_array($data['scheme'], array('http', 'https')) && isset($this['guzzle-teleporter'])) { + } elseif (in_array($data['scheme'], array('http', 'https')) && isset($this->factories['guzzle-teleporter'])) { $teleporter = 'guzzle-teleporter'; } else { $teleporter = 'stream-teleporter'; @@ -49,7 +59,17 @@ public function fromResource(Resource $resource) throw new InvalidArgumentException('No teleporter found'); } - return $this[$teleporter]; + return $this->getTeleporter($teleporter); + } + + private function getTeleporter($typeName) + { + if (! isset($this->teleporters[$typeName])) { + $factory = $this->factories[$typeName]; + $this->teleporters[$typeName] = $factory(); + } + + return $this->teleporters[$typeName]; } /** @@ -61,17 +81,18 @@ public static function load() { $container = new static(); - $container['stream-teleporter'] = $container->share(function () { + $container->factories['stream-teleporter'] = function () { return StreamTeleporter::create(); - }); - $container['local-teleporter'] = $container->share(function () { + }; + + $container->factories['local-teleporter'] = function () { return LocalTeleporter::create(); - }); + }; if (class_exists('Guzzle\Http\Client')) { - $container['guzzle-teleporter'] = $container->share(function () { + $container->factories['guzzle-teleporter'] = function () { return GuzzleTeleporter::create(); - }); + }; } return $container; From 5016f8b4472bc0daaf1dd50bb1719141a6431a01 Mon Sep 17 00:00:00 2001 From: Thibaud Fabre Date: Tue, 15 Dec 2015 10:08:09 +0100 Subject: [PATCH 2/3] Add type hints --- src/Zippy.php | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/src/Zippy.php b/src/Zippy.php index 60fb596..3097d51 100644 --- a/src/Zippy.php +++ b/src/Zippy.php @@ -29,7 +29,14 @@ class Zippy { + /** + * @var AdapterContainer + */ public $adapters; + + /** + * @var FileStrategyInterface[] + */ private $strategies = array(); public function __construct(AdapterContainer $adapters) From 93e1a79c44eb9acfa600d502f2e5d946265209ef Mon Sep 17 00:00:00 2001 From: Thibaud Fabre Date: Tue, 15 Dec 2015 11:42:38 +0100 Subject: [PATCH 3/3] Convert ContainerAdapter to standalone container --- composer.json | 1 - src/Adapter/AdapterContainer.php | 135 ++++++++++++++++----- src/FileStrategy/FileStrategyInterface.php | 4 +- src/Resource/TeleporterContainer.php | 69 ++++++++++- src/Zippy.php | 2 +- 5 files changed, 176 insertions(+), 35 deletions(-) diff --git a/composer.json b/composer.json index 3429f40..1a52652 100644 --- a/composer.json +++ b/composer.json @@ -14,7 +14,6 @@ "require": { "php": ">=5.3.3", "doctrine/collections": "~1.0", - "pimple/pimple": "~1.0", "symfony/filesystem": "^2.0.5|^3.0", "symfony/process": "^2.1|^3.0" }, diff --git a/src/Adapter/AdapterContainer.php b/src/Adapter/AdapterContainer.php index ee3b188..520f610 100644 --- a/src/Adapter/AdapterContainer.php +++ b/src/Adapter/AdapterContainer.php @@ -25,8 +25,11 @@ use Symfony\Component\Filesystem\Filesystem; use Symfony\Component\Process\ExecutableFinder; -class AdapterContainer extends \Pimple +class AdapterContainer implements \ArrayAccess { + + private $items = array(); + /** * Builds the adapter container * @@ -39,110 +42,180 @@ public static function load() $container['zip.inflator'] = null; $container['zip.deflator'] = null; - $container['resource-manager'] = $container->share(function ($container) { + $container['resource-manager'] = function ($container) { return new ResourceManager( $container['request-mapper'], $container['resource-teleporter'], $container['filesystem'] ); - }); + }; - $container['executable-finder'] = $container->share(function ($container) { + $container['executable-finder'] = function ($container) { return new ExecutableFinder(); - }); + }; - $container['request-mapper'] = $container->share(function ($container) { + $container['request-mapper'] = function ($container) { return new RequestMapper($container['target-locator']); - }); + }; - $container['target-locator'] = $container->share(function () { + $container['target-locator'] = function () { return new TargetLocator(); - }); + }; - $container['teleporter-container'] = $container->share(function ($container) { + $container['teleporter-container'] = function ($container) { return TeleporterContainer::load(); - }); + }; - $container['resource-teleporter'] = $container->share(function ($container) { + $container['resource-teleporter'] = function ($container) { return new ResourceTeleporter($container['teleporter-container']); - }); + }; - $container['filesystem'] = $container->share(function () { + $container['filesystem'] = function () { return new Filesystem(); - }); + }; - $container['Alchemy\\Zippy\\Adapter\\ZipAdapter'] = $container->share(function ($container) { + $container['Alchemy\\Zippy\\Adapter\\ZipAdapter'] = function ($container) { return ZipAdapter::newInstance( $container['executable-finder'], $container['resource-manager'], $container['zip.inflator'], $container['zip.deflator'] ); - }); + }; $container['gnu-tar.inflator'] = null; $container['gnu-tar.deflator'] = null; - $container['Alchemy\\Zippy\\Adapter\\GNUTar\\TarGNUTarAdapter'] = $container->share(function ($container) { + $container['Alchemy\\Zippy\\Adapter\\GNUTar\\TarGNUTarAdapter'] = function ($container) { return TarGNUTarAdapter::newInstance( $container['executable-finder'], $container['resource-manager'], $container['gnu-tar.inflator'], $container['gnu-tar.deflator'] ); - }); + }; - $container['Alchemy\\Zippy\\Adapter\\GNUTar\\TarGzGNUTarAdapter'] = $container->share(function ($container) { + $container['Alchemy\\Zippy\\Adapter\\GNUTar\\TarGzGNUTarAdapter'] = function ($container) { return TarGzGNUTarAdapter::newInstance( $container['executable-finder'], $container['resource-manager'], $container['gnu-tar.inflator'], $container['gnu-tar.deflator'] ); - }); + }; - $container['Alchemy\\Zippy\\Adapter\\GNUTar\\TarBz2GNUTarAdapter'] = $container->share(function ($container) { + $container['Alchemy\\Zippy\\Adapter\\GNUTar\\TarBz2GNUTarAdapter'] = function ($container) { return TarBz2GNUTarAdapter::newInstance( $container['executable-finder'], $container['resource-manager'], $container['gnu-tar.inflator'], $container['gnu-tar.deflator'] ); - }); + }; $container['bsd-tar.inflator'] = null; $container['bsd-tar.deflator'] = null; - $container['Alchemy\\Zippy\\Adapter\\BSDTar\\TarBSDTarAdapter'] = $container->share(function ($container) { + $container['Alchemy\\Zippy\\Adapter\\BSDTar\\TarBSDTarAdapter'] = function ($container) { return TarBSDTarAdapter::newInstance( $container['executable-finder'], $container['resource-manager'], $container['bsd-tar.inflator'], $container['bsd-tar.deflator'] ); - }); + }; - $container['Alchemy\\Zippy\\Adapter\\BSDTar\\TarGzBSDTarAdapter'] = $container->share(function ($container) { + $container['Alchemy\\Zippy\\Adapter\\BSDTar\\TarGzBSDTarAdapter'] = function ($container) { return TarGzBSDTarAdapter::newInstance( $container['executable-finder'], $container['resource-manager'], $container['bsd-tar.inflator'], $container['bsd-tar.deflator'] ); - }); + }; - $container['Alchemy\\Zippy\\Adapter\\BSDTar\\TarBz2BSDTarAdapter'] = $container->share(function ($container) { + $container['Alchemy\\Zippy\\Adapter\\BSDTar\\TarBz2BSDTarAdapter'] = function ($container) { return TarBz2BSDTarAdapter::newInstance( $container['executable-finder'], $container['resource-manager'], $container['bsd-tar.inflator'], $container['bsd-tar.deflator']); - }); + }; - $container['Alchemy\\Zippy\\Adapter\\ZipExtensionAdapter'] = $container->share(function () { + $container['Alchemy\\Zippy\\Adapter\\ZipExtensionAdapter'] = function () { return ZipExtensionAdapter::newInstance(); - }); + }; return $container; } + + /** + * (PHP 5 >= 5.0.0)
+ * Whether a offset exists + * @link http://php.net/manual/en/arrayaccess.offsetexists.php + * @param mixed $offset

+ * An offset to check for. + *

+ * @return boolean true on success or false on failure. + *

+ *

+ * The return value will be casted to boolean if non-boolean was returned. + */ + public function offsetExists($offset) + { + return isset($this->items[$offset]); + } + + /** + * (PHP 5 >= 5.0.0)
+ * Offset to retrieve + * @link http://php.net/manual/en/arrayaccess.offsetget.php + * @param mixed $offset

+ * The offset to retrieve. + *

+ * @return mixed Can return all value types. + */ + public function offsetGet($offset) + { + if (array_key_exists($offset, $this->items) && is_callable($this->items[$offset])) { + $this->items[$offset] = call_user_func($this->items[$offset], $this); + } + + if (array_key_exists($offset, $this->items)) { + return $this->items[$offset]; + } + + throw new \InvalidArgumentException(); + } + + /** + * (PHP 5 >= 5.0.0)
+ * Offset to set + * @link http://php.net/manual/en/arrayaccess.offsetset.php + * @param mixed $offset

+ * The offset to assign the value to. + *

+ * @param mixed $value

+ * The value to set. + *

+ * @return void + */ + public function offsetSet($offset, $value) + { + $this->items[$offset] = $value; + } + + /** + * (PHP 5 >= 5.0.0)
+ * Offset to unset + * @link http://php.net/manual/en/arrayaccess.offsetunset.php + * @param mixed $offset

+ * The offset to unset. + *

+ * @return void + */ + public function offsetUnset($offset) + { + unset($this->items[$offset]); + } } diff --git a/src/FileStrategy/FileStrategyInterface.php b/src/FileStrategy/FileStrategyInterface.php index 7d6cf20..1b24f5b 100644 --- a/src/FileStrategy/FileStrategyInterface.php +++ b/src/FileStrategy/FileStrategyInterface.php @@ -11,12 +11,14 @@ namespace Alchemy\Zippy\FileStrategy; +use Alchemy\Zippy\Adapter\AdapterInterface; + interface FileStrategyInterface { /** * Returns an array of adapters that match the strategy * - * @return array + * @return AdapterInterface[] */ public function getAdapters(); diff --git a/src/Resource/TeleporterContainer.php b/src/Resource/TeleporterContainer.php index a3e0797..34dd49f 100644 --- a/src/Resource/TeleporterContainer.php +++ b/src/Resource/TeleporterContainer.php @@ -20,7 +20,7 @@ /** * A container of TeleporterInterface */ -class TeleporterContainer +class TeleporterContainer implements \ArrayAccess, \Countable { /** * @var TeleporterInterface[] @@ -97,4 +97,71 @@ public static function load() return $container; } + + /** + * (PHP 5 >= 5.0.0)
+ * Whether a offset exists + * @link http://php.net/manual/en/arrayaccess.offsetexists.php + * @param mixed $offset

+ * An offset to check for. + *

+ * @return boolean true on success or false on failure. + *

+ *

+ * The return value will be casted to boolean if non-boolean was returned. + */ + public function offsetExists($offset) + { + return isset($this->teleporters[$offset]); + } + + /** + * (PHP 5 >= 5.0.0)
+ * Offset to retrieve + * @link http://php.net/manual/en/arrayaccess.offsetget.php + * @param mixed $offset

+ * The offset to retrieve. + *

+ * @return mixed Can return all value types. + */ + public function offsetGet($offset) + { + return $this->getTeleporter($offset); + } + + /** + * (PHP 5 >= 5.0.0)
+ * Offset to set + * @link http://php.net/manual/en/arrayaccess.offsetset.php + * @param mixed $offset

+ * The offset to assign the value to. + *

+ * @param mixed $value

+ * The value to set. + *

+ * @return void + */ + public function offsetSet($offset, $value) + { + throw new \BadMethodCallException(); + } + + /** + * (PHP 5 >= 5.0.0)
+ * Offset to unset + * @link http://php.net/manual/en/arrayaccess.offsetunset.php + * @param mixed $offset

+ * The offset to unset. + *

+ * @return void + */ + public function offsetUnset($offset) + { + throw new \BadMethodCallException(); + } + + public function count() + { + return count($this->teleporters); + } } diff --git a/src/Zippy.php b/src/Zippy.php index 3097d51..f2601b0 100644 --- a/src/Zippy.php +++ b/src/Zippy.php @@ -35,7 +35,7 @@ class Zippy public $adapters; /** - * @var FileStrategyInterface[] + * @var FileStrategyInterface[][] */ private $strategies = array();