version 1.0
This commit is contained in:
commit
941a149097
|
@ -0,0 +1,3 @@
|
|||
.idea/
|
||||
vendor/
|
||||
.DS_Store
|
|
@ -0,0 +1,175 @@
|
|||
<?php
|
||||
|
||||
namespace Bluesquare\StorageBundle\Adaptors;
|
||||
|
||||
use Aws\S3\S3Client;
|
||||
use Bluesquare\StorageBundle\Exceptions\InvalidStorageConfiguration;
|
||||
use Symfony\Component\Config\Definition\Exception\Exception;
|
||||
|
||||
/**
|
||||
* Interface de manipulation du stockage S3
|
||||
* Usage: $storage = new S3Storage('my_storage_name', $config);
|
||||
* @author Maxime Renou
|
||||
*/
|
||||
class S3Storage implements StorageAdaptor
|
||||
{
|
||||
const MODE_PRIVATE = 'private';
|
||||
const MODE_PUBLIC = 'public-read';
|
||||
|
||||
protected $client;
|
||||
protected $bucket;
|
||||
protected $region;
|
||||
|
||||
public function __construct ($storage_name, $config)
|
||||
{
|
||||
if (!($this->configIsNormed($config)))
|
||||
throw new InvalidStorageConfiguration("Invalid $storage_name storage configuration");
|
||||
|
||||
$this->config = $config;
|
||||
$this->bucket = $config['bucket'];
|
||||
$this->bucket_url = $config['bucket_url'];
|
||||
|
||||
$this->client = new S3Client([
|
||||
'version' => isset($config['version']) ? $config['version'] : 'latest',
|
||||
'region' => $config['region'],
|
||||
'endpoint' => $config['endpoint'],
|
||||
'credentials' => [
|
||||
'key' => $config['credentials']['key'],
|
||||
'secret' => $config['credentials']['secret']
|
||||
]
|
||||
]);
|
||||
}
|
||||
|
||||
public function getClient()
|
||||
{
|
||||
return $this->client;
|
||||
}
|
||||
|
||||
public function mode($name)
|
||||
{
|
||||
if ($name == 'public') return self::MODE_PUBLIC;
|
||||
return self::MODE_PRIVATE;
|
||||
}
|
||||
|
||||
private function configIsNormed($config)
|
||||
{
|
||||
return (
|
||||
isset($config['type']) &&
|
||||
isset($config['bucket']) &&
|
||||
isset($config['bucket_url']) &&
|
||||
isset($config['region']) &&
|
||||
isset($config['endpoint']) &&
|
||||
isset($config['credentials']) &&
|
||||
isset($config['credentials']['key']) &&
|
||||
isset($config['credentials']['secret'])
|
||||
);
|
||||
}
|
||||
|
||||
protected function getPrefix($prefix = null)
|
||||
{
|
||||
$ret = '';
|
||||
if (isset($this->config['path']) && !empty($this->config['path']))
|
||||
{
|
||||
$ret = trim($this->config['path'], '/').'/';
|
||||
if (trim($ret) == '/') $ret = '';
|
||||
}
|
||||
if (!is_null($prefix)) {
|
||||
$ret = ltrim($prefix, '/');
|
||||
}
|
||||
return $ret;
|
||||
}
|
||||
|
||||
public function index($prefix = null)
|
||||
{
|
||||
return ($this->client->listObjectsV2([
|
||||
'Bucket' => $this->bucket,
|
||||
'Prefix' => $this->getPrefix($prefix)
|
||||
]));
|
||||
}
|
||||
|
||||
/**
|
||||
* Permet d'obtenir l'URL vers une ressource S3
|
||||
* Cette ressource n'est accessible que si le fichier a été stocké en mode public
|
||||
* @param $target_path
|
||||
* @return string
|
||||
*/
|
||||
public function url ($target_path)
|
||||
{
|
||||
return rtrim($this->bucket_url, '/').'/'.$this->getPrefix().ltrim($target_path, '/');
|
||||
}
|
||||
|
||||
/**
|
||||
* Permet de stocker un fichier dans S3
|
||||
* @param $source_path
|
||||
* @param $target_path
|
||||
* @param string $permissions
|
||||
* @return \Aws\Result
|
||||
*/
|
||||
public function store ($source_path, $target_path, $permissions = self::MODE_PRIVATE)
|
||||
{
|
||||
return $this->client->putObject([
|
||||
'Bucket' => $this->bucket,
|
||||
'Path' => $this->getPrefix().$target_path,
|
||||
'Key' => $this->getPrefix().$target_path,
|
||||
'SourceFile' => $source_path, // Fix memory allocation
|
||||
//'Body' => file_get_contents($source_path),
|
||||
'ACL' => $permissions
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Permet de récupérer un fichier dans S3 pour le stocker en local
|
||||
* @param $distant_path
|
||||
* @param $local_path
|
||||
*/
|
||||
public function retrieve ($distant_path, $local_path)
|
||||
{
|
||||
$file_stream = fopen($local_path, 'w');
|
||||
|
||||
$aws_stream = $this->client->getObject([
|
||||
'Bucket' => $this->bucket,
|
||||
'Key' => $this->getPrefix().$distant_path,
|
||||
'Path' => $this->getPrefix().$distant_path,
|
||||
])->get('Body')->detach();
|
||||
|
||||
stream_copy_to_stream($aws_stream, $file_stream);
|
||||
fclose($file_stream);
|
||||
}
|
||||
|
||||
/**
|
||||
* Ouvre le stream d'un fichier stocké dans S3
|
||||
* @param $distant_path
|
||||
* @param $target_stream
|
||||
*/
|
||||
public function getStream ($distant_path)
|
||||
{
|
||||
return $this->client->getObject([
|
||||
'Bucket' => $this->bucket,
|
||||
'Key' => $this->getPrefix().$distant_path,
|
||||
'Path' => $this->getPrefix().$distant_path,
|
||||
])->get('Body')->detach();
|
||||
}
|
||||
|
||||
/**
|
||||
* Permet de stream un fichier stocké dans S3
|
||||
* @param $distant_path
|
||||
* @param $target_stream
|
||||
*/
|
||||
public function stream ($distant_path, $target_stream)
|
||||
{
|
||||
stream_copy_to_stream($this->getStream($distant_path), $target_stream);
|
||||
}
|
||||
|
||||
/**
|
||||
* Permet de supprimer un fichier stocké dans S3
|
||||
* @param $distant_path
|
||||
*/
|
||||
public function delete ($distant_path)
|
||||
{
|
||||
$this->client->deleteObject([
|
||||
'Bucket' => $this->bucket,
|
||||
'Path' => $this->getPrefix().$distant_path,
|
||||
'Key' => $this->getPrefix().$distant_path,
|
||||
]);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,13 @@
|
|||
<?php
|
||||
|
||||
namespace Bluesquare\StorageBundle\Adaptors;
|
||||
|
||||
interface StorageAdaptor
|
||||
{
|
||||
public function index();
|
||||
public function mode($name);
|
||||
public function store($source_path, $target_path);
|
||||
public function retrieve($distant_path, $local_path);
|
||||
public function stream($distant_path, $target_stream);
|
||||
public function delete($distant_path);
|
||||
}
|
|
@ -0,0 +1,31 @@
|
|||
<?php
|
||||
|
||||
namespace Bluesquare\StorageBundle\Annotations;
|
||||
|
||||
use Doctrine\ORM\Mapping as ORM;
|
||||
|
||||
/**
|
||||
* @Annotation
|
||||
*/
|
||||
class Storage implements ORM\Annotation
|
||||
{
|
||||
/**
|
||||
* @var string
|
||||
*/
|
||||
public $name;
|
||||
|
||||
/**
|
||||
* @var mixed
|
||||
*/
|
||||
public $prefix = null;
|
||||
|
||||
/**
|
||||
* @var mixed
|
||||
*/
|
||||
public $mode = null;
|
||||
|
||||
/**
|
||||
* @var mixed
|
||||
*/
|
||||
public $mime = null;
|
||||
}
|
|
@ -0,0 +1,41 @@
|
|||
<?php
|
||||
|
||||
namespace Bluesquare\StorageBundle\DependencyInjection;
|
||||
|
||||
use Symfony\Component\Config\Definition\Builder\TreeBuilder;
|
||||
use Symfony\Component\Config\Definition\ConfigurationInterface;
|
||||
|
||||
class Configuration implements ConfigurationInterface
|
||||
{
|
||||
|
||||
/**
|
||||
* Generates the configuration tree builder.
|
||||
*
|
||||
* @return \Symfony\Component\Config\Definition\Builder\TreeBuilder The tree builder
|
||||
*/
|
||||
public function getConfigTreeBuilder()
|
||||
{
|
||||
$treeBuilder = new TreeBuilder('storage');
|
||||
$root = $treeBuilder->root('storage');
|
||||
$root->useAttributeAsKey('storage_name')
|
||||
->prototype('array')
|
||||
->children()
|
||||
->scalarNode('type')->isRequired()->cannotBeEmpty()->end()
|
||||
->scalarNode('bucket')->end()
|
||||
->scalarNode('bucket_url')->end()
|
||||
->scalarNode('region')->end()
|
||||
->scalarNode('endpoint')->end()
|
||||
->arrayNode('credentials')
|
||||
->children()
|
||||
->scalarNode('key')->end()
|
||||
->scalarNode('secret')->end()
|
||||
->end()
|
||||
->end()
|
||||
->scalarNode('version')->end()
|
||||
->scalarNode('path')->end()
|
||||
->end()
|
||||
->end()
|
||||
->end();
|
||||
return ($treeBuilder);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,42 @@
|
|||
<?php
|
||||
|
||||
namespace Bluesquare\StorageBundle\DependencyInjection;
|
||||
|
||||
use Symfony\Component\Config\FileLocator;
|
||||
use Symfony\Component\DependencyInjection\Container;
|
||||
use Symfony\Component\DependencyInjection\ContainerBuilder;
|
||||
use Symfony\Component\DependencyInjection\Definition;
|
||||
use Symfony\Component\DependencyInjection\Extension\Extension;
|
||||
use Symfony\Component\DependencyInjection\Extension\PrependExtensionInterface;
|
||||
use Symfony\Component\DependencyInjection\Loader\YamlFileLoader;
|
||||
|
||||
class StorageExtension extends Extension
|
||||
{
|
||||
|
||||
/**
|
||||
* Loads a specific configuration.
|
||||
*
|
||||
* @throws \InvalidArgumentException When provided tag is not defined in this extension
|
||||
*/
|
||||
public function load(array $configs, ContainerBuilder $container)
|
||||
{
|
||||
$loader = new YamlFileLoader($container, new FileLocator(__DIR__ . '/../Ressources/config'));
|
||||
$loader->load('services.yaml');
|
||||
|
||||
$configuration = $this->getConfiguration($configs, $container);
|
||||
|
||||
$config = $this->processConfiguration($configuration, $configs);
|
||||
|
||||
$definition = $container->getDefinition('bluesquare.storage');
|
||||
$definition->setArgument(0, $config);
|
||||
|
||||
return $config;
|
||||
}
|
||||
|
||||
|
||||
public function getAlias()
|
||||
{
|
||||
// return ('bluesquare\\storage');
|
||||
return parent::getAlias(); // TODO: Change the autogenerated stub
|
||||
}
|
||||
}
|
|
@ -0,0 +1,8 @@
|
|||
<?php
|
||||
|
||||
namespace Bluesquare\StorageBundle\Exceptions;
|
||||
|
||||
class InvalidFileException extends \Exception
|
||||
{
|
||||
|
||||
}
|
|
@ -0,0 +1,8 @@
|
|||
<?php
|
||||
|
||||
namespace Bluesquare\StorageBundle\Exceptions;
|
||||
|
||||
class InvalidStorageConfiguration extends \Exception
|
||||
{
|
||||
|
||||
}
|
|
@ -0,0 +1,8 @@
|
|||
<?php
|
||||
|
||||
namespace Bluesquare\StorageBundle\Exceptions;
|
||||
|
||||
class MimeTypeException extends \Exception
|
||||
{
|
||||
|
||||
}
|
|
@ -0,0 +1,8 @@
|
|||
<?php
|
||||
|
||||
namespace Bluesquare\StorageBundle\Exceptions;
|
||||
|
||||
class MissingStorageAnnotation extends \Exception
|
||||
{
|
||||
|
||||
}
|
|
@ -0,0 +1,8 @@
|
|||
<?php
|
||||
|
||||
namespace Bluesquare\StorageBundle\Exceptions;
|
||||
|
||||
class UnknownStorage extends \Exception
|
||||
{
|
||||
|
||||
}
|
|
@ -0,0 +1,2 @@
|
|||
imports:
|
||||
- { ressource: '%kernel.root_dir%/config/packages/bluesquare/storage.yaml' }
|
|
@ -0,0 +1,7 @@
|
|||
services:
|
||||
bluesquare.storage:
|
||||
class: Bluesquare\StorageBundle\Storage
|
||||
autowire: true
|
||||
public: true
|
||||
arguments: ['user_storage']
|
||||
Bluesquare\StorageBundle\Storage: '@bluesquare.storage'
|
|
@ -0,0 +1,166 @@
|
|||
<?php
|
||||
|
||||
namespace Bluesquare\StorageBundle;
|
||||
|
||||
use Aws\S3\S3Client;
|
||||
use Bluesquare\StorageBundle\Adaptors\S3Storage;
|
||||
use Bluesquare\StorageBundle\Exceptions\InvalidFileException;
|
||||
use Bluesquare\StorageBundle\Exceptions\MimeTypeException;
|
||||
use Bluesquare\StorageBundle\Exceptions\MissingStorageAnnotation;
|
||||
use Bluesquare\StorageBundle\Exceptions\UnknownStorage;
|
||||
use Symfony\Component\HttpFoundation\File\UploadedFile;
|
||||
use Bluesquare\StorageBundle\Annotations\Storage as StorageAnnotation;
|
||||
use Symfony\Component\DependencyInjection\Container;
|
||||
use Doctrine\Common\Annotations\AnnotationReader;
|
||||
|
||||
/**
|
||||
* Interface de manipulation des stockages préconfigurés
|
||||
* Usage par injection
|
||||
*/
|
||||
class Storage
|
||||
{
|
||||
private $config_storage = [];
|
||||
|
||||
public function __construct(array $user_config = [])
|
||||
{
|
||||
// dump($user_config); die;
|
||||
$this->config_storage = $user_config;
|
||||
}
|
||||
|
||||
public function get($storage_name)
|
||||
{
|
||||
if (array_key_exists($storage_name, $this->config_storage))
|
||||
{
|
||||
$config = $this->config_storage[$storage_name];
|
||||
|
||||
switch ($config['type'])
|
||||
{
|
||||
case 's3': return (new S3Storage($storage_name, $config));
|
||||
}
|
||||
}
|
||||
|
||||
return (null);
|
||||
}
|
||||
|
||||
protected function getStorageAnnotation($entity, $attribute)
|
||||
{
|
||||
$reflection = new \ReflectionProperty($entity, $attribute);
|
||||
|
||||
$reader = new AnnotationReader();
|
||||
$annotations = $reader->getPropertyAnnotations($reflection);
|
||||
|
||||
$storage_annotation = null;
|
||||
|
||||
foreach ($annotations as $annotation)
|
||||
{
|
||||
if ($annotation instanceof StorageAnnotation) {
|
||||
$storage_annotation = $annotation;
|
||||
}
|
||||
}
|
||||
|
||||
if (is_null($storage_annotation))
|
||||
{
|
||||
throw new MissingStorageAnnotation("Missing Storage annotation for $attribute in ".get_class($entity));
|
||||
}
|
||||
|
||||
return $storage_annotation;
|
||||
}
|
||||
|
||||
public function getStorageFor($entity, $attribute)
|
||||
{
|
||||
$annotation = $this->getStorageAnnotation($entity, $attribute);
|
||||
return $annotation->name;
|
||||
}
|
||||
|
||||
public function url($entity, $attribute, $class = null)
|
||||
{
|
||||
$annotation = $this->getStorageAnnotation(!is_null($class) ? $class : $entity, $attribute);
|
||||
$storage = $this->get($annotation->name);
|
||||
$prefix = is_null($annotation->prefix) || empty($annotation->prefix) ? '' : trim($annotation->prefix, '/').'/';
|
||||
$camel = ucfirst(Container::camelize($attribute));
|
||||
return $storage->url("$prefix{$entity->{"get".$camel}()}");
|
||||
}
|
||||
|
||||
public function delete($entity, $attribute)
|
||||
{
|
||||
$annotation = $this->getStorageAnnotation($entity, $attribute);
|
||||
$storage = $this->get($annotation->name);
|
||||
$prefix = is_null($annotation->prefix) || empty($annotation->prefix) ? '' : trim($annotation->prefix, '/').'/';
|
||||
$camel = ucfirst(Container::camelize($attribute));
|
||||
return $storage->delete("$prefix{$entity->{"get".$camel}()}");
|
||||
}
|
||||
|
||||
public function retrieve($entity, $attribute, $local_path)
|
||||
{
|
||||
$annotation = $this->getStorageAnnotation($entity, $attribute);
|
||||
$storage = $this->get($annotation->name);
|
||||
$prefix = is_null($annotation->prefix) || empty($annotation->prefix) ? '' : trim($annotation->prefix, '/').'/';
|
||||
$camel = ucfirst(Container::camelize($attribute));
|
||||
return $storage->retrieve("$prefix{$entity->{"get".$camel}()}", $local_path);
|
||||
}
|
||||
|
||||
public function stream($entity, $attribute, $target_stream = null)
|
||||
{
|
||||
$annotation = $this->getStorageAnnotation($entity, $attribute);
|
||||
$storage = $this->get($annotation->name);
|
||||
$prefix = is_null($annotation->prefix) || empty($annotation->prefix) ? '' : trim($annotation->prefix, '/').'/';
|
||||
$camel = ucfirst(Container::camelize($attribute));
|
||||
|
||||
if (is_null($target_stream)) {
|
||||
return $storage->getStream("$prefix{$entity->{"get".$camel}()}");
|
||||
}
|
||||
|
||||
return $storage->stream("$prefix{$entity->{"get".$camel}()}", $target_stream);
|
||||
}
|
||||
|
||||
public function store($entity, $attribute, $file)
|
||||
{
|
||||
$storage_annotation = $this->getStorageAnnotation($entity, $attribute);
|
||||
$file_hash = hash('sha256', time().$attribute.uniqid());
|
||||
$storage = $this->get($storage_annotation->name);
|
||||
|
||||
if (is_null($storage))
|
||||
{
|
||||
throw new UnknownStorage("Unknown storage {$storage_annotation->name} for $attribute in ".get_class($entity));
|
||||
}
|
||||
|
||||
$prefix = is_null($storage_annotation->prefix) || empty($storage_annotation->prefix) ? '' : trim($storage_annotation->prefix, '/').'/';
|
||||
$mode = $storage->mode($storage_annotation->mode);
|
||||
$camel = ucfirst(Container::camelize($attribute));
|
||||
|
||||
if ($file instanceof UploadedFile) {
|
||||
$file_hash .= strlen($file->getClientOriginalExtension()) > 0 ? '.'.$file->getClientOriginalExtension() : '';
|
||||
|
||||
if (!is_null($storage_annotation->mime))
|
||||
{
|
||||
$valid = true;
|
||||
if (count(explode('/', $storage_annotation->mime)) > 1) {
|
||||
$valid = strtolower($storage_annotation->mime) == $file->getMimeType();
|
||||
}
|
||||
else {
|
||||
$valid = strtolower($storage_annotation->mime) == explode('/', $file->getMimeType())[0];
|
||||
}
|
||||
|
||||
if (!$valid) {
|
||||
throw new MimeTypeException("Invalid mime type");
|
||||
}
|
||||
}
|
||||
|
||||
$storage->store($file->getRealPath(), "$prefix$file_hash", $mode);
|
||||
$previous_file_hash = $entity->{"get$camel"}();
|
||||
if (!is_null($previous_file_hash) && !empty($previous_file_hash)) {
|
||||
$storage->delete("$prefix$previous_file_hash");
|
||||
}
|
||||
}
|
||||
elseif (is_string($file) && file_exists($file)) {
|
||||
$storage->store($file, "$prefix$file_hash", $mode);
|
||||
}
|
||||
else {
|
||||
throw new InvalidFileException("Invalid file argument");
|
||||
}
|
||||
|
||||
$entity->{"set$camel"}($file_hash);
|
||||
|
||||
return $file_hash;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,22 @@
|
|||
<?php
|
||||
|
||||
namespace Bluesquare\StorageBundle;
|
||||
|
||||
use Bluesquare\StorageBundle\DependencyInjection\StorageExtension;
|
||||
use Symfony\Component\DependencyInjection\ContainerBuilder;
|
||||
use Symfony\Component\HttpKernel\Bundle\Bundle;
|
||||
|
||||
class StorageBundle extends Bundle
|
||||
{
|
||||
public function build(ContainerBuilder $container)
|
||||
{
|
||||
parent::build($container);
|
||||
}
|
||||
|
||||
public function getContainerExtension()
|
||||
{
|
||||
if (null === $this->extension)
|
||||
$this->extension = new StorageExtension();
|
||||
return $this->extension;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,23 @@
|
|||
{
|
||||
"name": "bluesquare-packages/symfony-storage",
|
||||
"description": "Cryptor created by Bluesquare Computing",
|
||||
"keywords": ["template", "composer", "package"],
|
||||
"license": "proprietary",
|
||||
"authors": [
|
||||
{
|
||||
"name": "RENOU Maxime",
|
||||
"email": "maxime@bluesquare.io"
|
||||
}
|
||||
],
|
||||
"type": "symfony-bundle",
|
||||
"require": {
|
||||
"php": ">=7.1",
|
||||
"aws/aws-sdk-php": "^3.81",
|
||||
"doctrine/event-manager": "*"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"Bluesquare\\StorageBundle\\": "StorageBundle/"
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,504 @@
|
|||
{
|
||||
"_readme": [
|
||||
"This file locks the dependencies of your project to a known state",
|
||||
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
|
||||
"This file is @generated automatically"
|
||||
],
|
||||
"content-hash": "e0fd4d7a1648530618008debe3b39eb2",
|
||||
"packages": [
|
||||
{
|
||||
"name": "aws/aws-sdk-php",
|
||||
"version": "3.87.15",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/aws/aws-sdk-php.git",
|
||||
"reference": "21a4dd314e2a3c44b5538dd56d3770733a3d03e6"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/aws/aws-sdk-php/zipball/21a4dd314e2a3c44b5538dd56d3770733a3d03e6",
|
||||
"reference": "21a4dd314e2a3c44b5538dd56d3770733a3d03e6",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"ext-json": "*",
|
||||
"ext-pcre": "*",
|
||||
"ext-simplexml": "*",
|
||||
"guzzlehttp/guzzle": "^5.3.3|^6.2.1",
|
||||
"guzzlehttp/promises": "~1.0",
|
||||
"guzzlehttp/psr7": "^1.4.1",
|
||||
"mtdowling/jmespath.php": "~2.2",
|
||||
"php": ">=5.5"
|
||||
},
|
||||
"require-dev": {
|
||||
"andrewsville/php-token-reflection": "^1.4",
|
||||
"aws/aws-php-sns-message-validator": "~1.0",
|
||||
"behat/behat": "~3.0",
|
||||
"doctrine/cache": "~1.4",
|
||||
"ext-dom": "*",
|
||||
"ext-openssl": "*",
|
||||
"ext-pcntl": "*",
|
||||
"ext-sockets": "*",
|
||||
"nette/neon": "^2.3",
|
||||
"phpunit/phpunit": "^4.8.35|^5.4.3",
|
||||
"psr/cache": "^1.0"
|
||||
},
|
||||
"suggest": {
|
||||
"aws/aws-php-sns-message-validator": "To validate incoming SNS notifications",
|
||||
"doctrine/cache": "To use the DoctrineCacheAdapter",
|
||||
"ext-curl": "To send requests using cURL",
|
||||
"ext-openssl": "Allows working with CloudFront private distributions and verifying received SNS messages",
|
||||
"ext-sockets": "To use client-side monitoring"
|
||||
},
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "3.0-dev"
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"Aws\\": "src/"
|
||||
},
|
||||
"files": [
|
||||
"src/functions.php"
|
||||
]
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"Apache-2.0"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Amazon Web Services",
|
||||
"homepage": "http://aws.amazon.com"
|
||||
}
|
||||
],
|
||||
"description": "AWS SDK for PHP - Use Amazon Web Services in your PHP project",
|
||||
"homepage": "http://aws.amazon.com/sdkforphp",
|
||||
"keywords": [
|
||||
"amazon",
|
||||
"aws",
|
||||
"cloud",
|
||||
"dynamodb",
|
||||
"ec2",
|
||||
"glacier",
|
||||
"s3",
|
||||
"sdk"
|
||||
],
|
||||
"time": "2019-02-20T19:11:08+00:00"
|
||||
},
|
||||
{
|
||||
"name": "doctrine/event-manager",
|
||||
"version": "v1.0.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/doctrine/event-manager.git",
|
||||
"reference": "a520bc093a0170feeb6b14e9d83f3a14452e64b3"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/doctrine/event-manager/zipball/a520bc093a0170feeb6b14e9d83f3a14452e64b3",
|
||||
"reference": "a520bc093a0170feeb6b14e9d83f3a14452e64b3",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": "^7.1"
|
||||
},
|
||||
"conflict": {
|
||||
"doctrine/common": "<2.9@dev"
|
||||
},
|
||||
"require-dev": {
|
||||
"doctrine/coding-standard": "^4.0",
|
||||
"phpunit/phpunit": "^7.0"
|
||||
},
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "1.0.x-dev"
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"Doctrine\\Common\\": "lib/Doctrine/Common"
|
||||
}
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Roman Borschel",
|
||||
"email": "roman@code-factory.org"
|
||||
},
|
||||
{
|
||||
"name": "Benjamin Eberlei",
|
||||
"email": "kontakt@beberlei.de"
|
||||
},
|
||||
{
|
||||
"name": "Guilherme Blanco",
|
||||
"email": "guilhermeblanco@gmail.com"
|
||||
},
|
||||
{
|
||||
"name": "Jonathan Wage",
|
||||
"email": "jonwage@gmail.com"
|
||||
},
|
||||
{
|
||||
"name": "Johannes Schmitt",
|
||||
"email": "schmittjoh@gmail.com"
|
||||
},
|
||||
{
|
||||
"name": "Marco Pivetta",
|
||||
"email": "ocramius@gmail.com"
|
||||
}
|
||||
],
|
||||
"description": "Doctrine Event Manager component",
|
||||
"homepage": "https://www.doctrine-project.org/projects/event-manager.html",
|
||||
"keywords": [
|
||||
"event",
|
||||
"eventdispatcher",
|
||||
"eventmanager"
|
||||
],
|
||||
"time": "2018-06-11T11:59:03+00:00"
|
||||
},
|
||||
{
|
||||
"name": "guzzlehttp/guzzle",
|
||||
"version": "6.3.3",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/guzzle/guzzle.git",
|
||||
"reference": "407b0cb880ace85c9b63c5f9551db498cb2d50ba"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/guzzle/guzzle/zipball/407b0cb880ace85c9b63c5f9551db498cb2d50ba",
|
||||
"reference": "407b0cb880ace85c9b63c5f9551db498cb2d50ba",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"guzzlehttp/promises": "^1.0",
|
||||
"guzzlehttp/psr7": "^1.4",
|
||||
"php": ">=5.5"
|
||||
},
|
||||
"require-dev": {
|
||||
"ext-curl": "*",
|
||||
"phpunit/phpunit": "^4.8.35 || ^5.7 || ^6.4 || ^7.0",
|
||||
"psr/log": "^1.0"
|
||||
},
|
||||
"suggest": {
|
||||
"psr/log": "Required for using the Log middleware"
|
||||
},
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "6.3-dev"
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
"files": [
|
||||
"src/functions_include.php"
|
||||
],
|
||||
"psr-4": {
|
||||
"GuzzleHttp\\": "src/"
|
||||
}
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Michael Dowling",
|
||||
"email": "mtdowling@gmail.com",
|
||||
"homepage": "https://github.com/mtdowling"
|
||||
}
|
||||
],
|
||||
"description": "Guzzle is a PHP HTTP client library",
|
||||
"homepage": "http://guzzlephp.org/",
|
||||
"keywords": [
|
||||
"client",
|
||||
"curl",
|
||||
"framework",
|
||||
"http",
|
||||
"http client",
|
||||
"rest",
|
||||
"web service"
|
||||
],
|
||||
"time": "2018-04-22T15:46:56+00:00"
|
||||
},
|
||||
{
|
||||
"name": "guzzlehttp/promises",
|
||||
"version": "v1.3.1",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/guzzle/promises.git",
|
||||
"reference": "a59da6cf61d80060647ff4d3eb2c03a2bc694646"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/guzzle/promises/zipball/a59da6cf61d80060647ff4d3eb2c03a2bc694646",
|
||||
"reference": "a59da6cf61d80060647ff4d3eb2c03a2bc694646",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=5.5.0"
|
||||
},
|
||||
"require-dev": {
|
||||
"phpunit/phpunit": "^4.0"
|
||||
},
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "1.4-dev"
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"GuzzleHttp\\Promise\\": "src/"
|
||||
},
|
||||
"files": [
|
||||
"src/functions_include.php"
|
||||
]
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Michael Dowling",
|
||||
"email": "mtdowling@gmail.com",
|
||||
"homepage": "https://github.com/mtdowling"
|
||||
}
|
||||
],
|
||||
"description": "Guzzle promises library",
|
||||
"keywords": [
|
||||
"promise"
|
||||
],
|
||||
"time": "2016-12-20T10:07:11+00:00"
|
||||
},
|
||||
{
|
||||
"name": "guzzlehttp/psr7",
|
||||
"version": "1.5.2",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/guzzle/psr7.git",
|
||||
"reference": "9f83dded91781a01c63574e387eaa769be769115"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/guzzle/psr7/zipball/9f83dded91781a01c63574e387eaa769be769115",
|
||||
"reference": "9f83dded91781a01c63574e387eaa769be769115",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=5.4.0",
|
||||
"psr/http-message": "~1.0",
|
||||
"ralouphie/getallheaders": "^2.0.5"
|
||||
},
|
||||
"provide": {
|
||||
"psr/http-message-implementation": "1.0"
|
||||
},
|
||||
"require-dev": {
|
||||
"phpunit/phpunit": "~4.8.36 || ^5.7.27 || ^6.5.8"
|
||||
},
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "1.5-dev"
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"GuzzleHttp\\Psr7\\": "src/"
|
||||
},
|
||||
"files": [
|
||||
"src/functions_include.php"
|
||||
]
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Michael Dowling",
|
||||
"email": "mtdowling@gmail.com",
|
||||
"homepage": "https://github.com/mtdowling"
|
||||
},
|
||||
{
|
||||
"name": "Tobias Schultze",
|
||||
"homepage": "https://github.com/Tobion"
|
||||
}
|
||||
],
|
||||
"description": "PSR-7 message implementation that also provides common utility methods",
|
||||
"keywords": [
|
||||
"http",
|
||||
"message",
|
||||
"psr-7",
|
||||
"request",
|
||||
"response",
|
||||
"stream",
|
||||
"uri",
|
||||
"url"
|
||||
],
|
||||
"time": "2018-12-04T20:46:45+00:00"
|
||||
},
|
||||
{
|
||||
"name": "mtdowling/jmespath.php",
|
||||
"version": "2.4.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/jmespath/jmespath.php.git",
|
||||
"reference": "adcc9531682cf87dfda21e1fd5d0e7a41d292fac"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/jmespath/jmespath.php/zipball/adcc9531682cf87dfda21e1fd5d0e7a41d292fac",
|
||||
"reference": "adcc9531682cf87dfda21e1fd5d0e7a41d292fac",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=5.4.0"
|
||||
},
|
||||
"require-dev": {
|
||||
"phpunit/phpunit": "~4.0"
|
||||
},
|
||||
"bin": [
|
||||
"bin/jp.php"
|
||||
],
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "2.0-dev"
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"JmesPath\\": "src/"
|
||||
},
|
||||
"files": [
|
||||
"src/JmesPath.php"
|
||||
]
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Michael Dowling",
|
||||
"email": "mtdowling@gmail.com",
|
||||
"homepage": "https://github.com/mtdowling"
|
||||
}
|
||||
],
|
||||
"description": "Declaratively specify how to extract elements from a JSON document",
|
||||
"keywords": [
|
||||
"json",
|
||||
"jsonpath"
|
||||
],
|
||||
"time": "2016-12-03T22:08:25+00:00"
|
||||
},
|
||||
{
|
||||
"name": "psr/http-message",
|
||||
"version": "1.0.1",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/php-fig/http-message.git",
|
||||
"reference": "f6561bf28d520154e4b0ec72be95418abe6d9363"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/php-fig/http-message/zipball/f6561bf28d520154e4b0ec72be95418abe6d9363",
|
||||
"reference": "f6561bf28d520154e4b0ec72be95418abe6d9363",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=5.3.0"
|
||||
},
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "1.0.x-dev"
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"Psr\\Http\\Message\\": "src/"
|
||||
}
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "PHP-FIG",
|
||||
"homepage": "http://www.php-fig.org/"
|
||||
}
|
||||
],
|
||||
"description": "Common interface for HTTP messages",
|
||||
"homepage": "https://github.com/php-fig/http-message",
|
||||
"keywords": [
|
||||
"http",
|
||||
"http-message",
|
||||
"psr",
|
||||
"psr-7",
|
||||
"request",
|
||||
"response"
|
||||
],
|
||||
"time": "2016-08-06T14:39:51+00:00"
|
||||
},
|
||||
{
|
||||
"name": "ralouphie/getallheaders",
|
||||
"version": "2.0.5",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/ralouphie/getallheaders.git",
|
||||
"reference": "5601c8a83fbba7ef674a7369456d12f1e0d0eafa"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/ralouphie/getallheaders/zipball/5601c8a83fbba7ef674a7369456d12f1e0d0eafa",
|
||||
"reference": "5601c8a83fbba7ef674a7369456d12f1e0d0eafa",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=5.3"
|
||||
},
|
||||
"require-dev": {
|
||||
"phpunit/phpunit": "~3.7.0",
|
||||
"satooshi/php-coveralls": ">=1.0"
|
||||
},
|
||||
"type": "library",
|
||||
"autoload": {
|
||||
"files": [
|
||||
"src/getallheaders.php"
|
||||
]
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Ralph Khattar",
|
||||
"email": "ralph.khattar@gmail.com"
|
||||
}
|
||||
],
|
||||
"description": "A polyfill for getallheaders.",
|
||||
"time": "2016-02-11T07:05:27+00:00"
|
||||
}
|
||||
],
|
||||
"packages-dev": [],
|
||||
"aliases": [],
|
||||
"minimum-stability": "stable",
|
||||
"stability-flags": [],
|
||||
"prefer-stable": false,
|
||||
"prefer-lowest": false,
|
||||
"platform": {
|
||||
"php": ">=7.1"
|
||||
},
|
||||
"platform-dev": []
|
||||
}
|
Loading…
Reference in New Issue