From b76e2ff898b23745d4c9aaee49eeb7d88f2896ab Mon Sep 17 00:00:00 2001 From: Carson Fleming Date: Thu, 2 Mar 2017 22:49:24 -0500 Subject: Updated mailgun plugin --- .../php-http/multipart-stream-builder/CHANGELOG.md | 47 ++++ .../php-http/multipart-stream-builder/LICENSE | 19 ++ .../php-http/multipart-stream-builder/README.md | 37 +++ .../php-http/multipart-stream-builder/appveyor.yml | 39 +++ .../multipart-stream-builder/composer.json | 43 ++++ .../src/ApacheMimetypeHelper.php | 142 +++++++++++ .../src/CustomMimetypeHelper.php | 51 ++++ .../src/MimetypeHelper.php | 27 ++ .../src/MultipartStreamBuilder.php | 279 +++++++++++++++++++++ 9 files changed, 684 insertions(+) create mode 100644 inc/mailgun/php-http/multipart-stream-builder/CHANGELOG.md create mode 100644 inc/mailgun/php-http/multipart-stream-builder/LICENSE create mode 100644 inc/mailgun/php-http/multipart-stream-builder/README.md create mode 100644 inc/mailgun/php-http/multipart-stream-builder/appveyor.yml create mode 100644 inc/mailgun/php-http/multipart-stream-builder/composer.json create mode 100644 inc/mailgun/php-http/multipart-stream-builder/src/ApacheMimetypeHelper.php create mode 100644 inc/mailgun/php-http/multipart-stream-builder/src/CustomMimetypeHelper.php create mode 100644 inc/mailgun/php-http/multipart-stream-builder/src/MimetypeHelper.php create mode 100644 inc/mailgun/php-http/multipart-stream-builder/src/MultipartStreamBuilder.php (limited to 'inc/mailgun/php-http/multipart-stream-builder') diff --git a/inc/mailgun/php-http/multipart-stream-builder/CHANGELOG.md b/inc/mailgun/php-http/multipart-stream-builder/CHANGELOG.md new file mode 100644 index 0000000..144cbc4 --- /dev/null +++ b/inc/mailgun/php-http/multipart-stream-builder/CHANGELOG.md @@ -0,0 +1,47 @@ +# Change Log + +## 0.1.6 - 2017-02-16 + +### Fixed + +- Performance improvements by avoid using `uniqid()`. + +## 0.1.5 - 2017-02-14 + +### Fixed + +- Support for non-readable streams. This fix was needed because flaws in Guzzle, Zend and Slims implementations of PSR-7. + +## 0.1.4 - 2016-12-31 + +### Added + +- Added support for resetting the builder + +## 0.1.3 - 2016-12-22 + +### Added + +- Added `CustomMimetypeHelper` to allow you to configure custom mimetypes. + +### Changed + +- Using regular expression instead of `basename($filename)` because basename is depending on locale. + +## 0.1.2 - 2016-08-31 + +### Added + +- Support for Outlook msg files. + +## 0.1.1 - 2016-08-10 + +### Added + +- Support for Apple passbook. + +## 0.1.0 - 2016-07-19 + +### Added + +- Initial release diff --git a/inc/mailgun/php-http/multipart-stream-builder/LICENSE b/inc/mailgun/php-http/multipart-stream-builder/LICENSE new file mode 100644 index 0000000..8e2c4a0 --- /dev/null +++ b/inc/mailgun/php-http/multipart-stream-builder/LICENSE @@ -0,0 +1,19 @@ +Copyright (c) 2015 PHP HTTP Team + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is furnished +to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/inc/mailgun/php-http/multipart-stream-builder/README.md b/inc/mailgun/php-http/multipart-stream-builder/README.md new file mode 100644 index 0000000..10ad058 --- /dev/null +++ b/inc/mailgun/php-http/multipart-stream-builder/README.md @@ -0,0 +1,37 @@ +# PSR-7 Multipart Stream Builder + +[![Latest Version](https://img.shields.io/github/release/php-http/multipart-stream-builder.svg?style=flat-square)](https://github.com/php-http/multipart-stream-builder/releases) +[![Build Status](https://img.shields.io/travis/php-http/multipart-stream-builder.svg?style=flat-square)](https://travis-ci.org/php-http/multipart-stream-builder) +[![Code Coverage](https://img.shields.io/scrutinizer/coverage/g/php-http/multipart-stream-builder.svg?style=flat-square)](https://scrutinizer-ci.com/g/php-http/multipart-stream-builder) +[![Quality Score](https://img.shields.io/scrutinizer/g/php-http/multipart-stream-builder.svg?style=flat-square)](https://scrutinizer-ci.com/g/php-http/multipart-stream-builder) +[![Total Downloads](https://img.shields.io/packagist/dt/php-http/multipart-stream-builder.svg?style=flat-square)](https://packagist.org/packages/php-http/multipart-stream-builder) + +**A builder for Multipart PSR-7 Streams. The builder create streams independenly form any PSR-7 implementation.** + + +## Install + +Via Composer + +``` bash +$ composer require php-http/multipart-stream-builder +``` + +## Documentation + +Please see the [official documentation](http://php-http.readthedocs.org/en/latest/components/multipart-stream-builder.html). + + +## Contributing + +Please see [CONTRIBUTING](CONTRIBUTING.md) and [CONDUCT](CONDUCT.md) for details. + + +## Security + +If you discover any security related issues, please contact us at [security@php-http.org](mailto:security@php-http.org). + + +## License + +The MIT License (MIT). Please see [License File](LICENSE) for more information. diff --git a/inc/mailgun/php-http/multipart-stream-builder/appveyor.yml b/inc/mailgun/php-http/multipart-stream-builder/appveyor.yml new file mode 100644 index 0000000..8d7af73 --- /dev/null +++ b/inc/mailgun/php-http/multipart-stream-builder/appveyor.yml @@ -0,0 +1,39 @@ +build: false +platform: + - x86 + - x64 + +clone_folder: c:\projects\php-http\multipart-stream-builder + +cache: + - c:\tools\php -> appveyor.yml + +init: + - SET PATH=c:\php;%PATH% + - SET COMPOSER_NO_INTERACTION=1 + - SET PHP=1 + + +install: + - IF EXIST c:\php (SET PHP=0) ELSE (mkdir c:\php) + - cd c:\php + - IF %PHP%==1 appveyor DownloadFile http://windows.php.net/downloads/releases/archives/php-7.0.0-nts-Win32-VC14-x86.zip + - IF %PHP%==1 7z x php-7.0.0-nts-Win32-VC14-x86.zip -y >nul + - IF %PHP%==1 del /Q *.zip + - IF %PHP%==1 echo @php %%~dp0composer.phar %%* > composer.bat + - IF %PHP%==1 copy /Y php.ini-development php.ini + - IF %PHP%==1 echo max_execution_time=1200 >> php.ini + - IF %PHP%==1 echo date.timezone="UTC" >> php.ini + - IF %PHP%==1 echo extension_dir=ext >> php.ini + - IF %PHP%==1 echo extension=php_openssl.dll >> php.ini + - IF %PHP%==1 echo extension=php_mbstring.dll >> php.ini + - IF %PHP%==1 echo extension=php_fileinfo.dll >> php.ini + - appveyor DownloadFile https://getcomposer.org/composer.phar + - cd c:\projects\php-http\multipart-stream-builder + - mkdir %APPDATA%\Composer + - composer update --prefer-dist --no-progress --ansi + +test_script: + - cd c:\projects\php-http\multipart-stream-builder + - vendor\bin\phpunit.bat --verbose + diff --git a/inc/mailgun/php-http/multipart-stream-builder/composer.json b/inc/mailgun/php-http/multipart-stream-builder/composer.json new file mode 100644 index 0000000..3a7e47a --- /dev/null +++ b/inc/mailgun/php-http/multipart-stream-builder/composer.json @@ -0,0 +1,43 @@ +{ + "name": "php-http/multipart-stream-builder", + "description": "A builder class that help you create a multipart stream", + "license": "MIT", + "keywords": ["http", "factory", "message", "stream", "multipart stream"], + "homepage": "http://php-http.org", + "authors": [ + { + "name": "Tobias Nyholm", + "email": "tobias.nyholm@gmail.com" + } + ], + "require": { + "php": "^5.5 || ^7.0", + "psr/http-message": "^1.0", + "php-http/message-factory": "^1.0.2", + "php-http/discovery": "^1.0" + }, + "require-dev": { + "phpunit/phpunit": "^4.8 || ^5.4", + "php-http/message": "^1.5", + "zendframework/zend-diactoros": "^1.3.5" + }, + "autoload": { + "psr-4": { + "Http\\Message\\MultipartStream\\": "src/" + } + }, + "autoload-dev": { + "psr-4": { + "tests\\Http\\Message\\MultipartStream\\": "tests/" + } + }, + "scripts": { + "test": "vendor/bin/phpunit", + "test-ci": "vendor/bin/phpunit --coverage-text --coverage-clover=build/coverage.xml" + }, + "extra": { + "branch-alias": { + "dev-master": "0.2-dev" + } + } +} diff --git a/inc/mailgun/php-http/multipart-stream-builder/src/ApacheMimetypeHelper.php b/inc/mailgun/php-http/multipart-stream-builder/src/ApacheMimetypeHelper.php new file mode 100644 index 0000000..6e4ca66 --- /dev/null +++ b/inc/mailgun/php-http/multipart-stream-builder/src/ApacheMimetypeHelper.php @@ -0,0 +1,142 @@ + + */ +class ApacheMimetypeHelper implements MimetypeHelper +{ + /** + * {@inheritdoc} + * + * @see http://svn.apache.org/repos/asf/httpd/httpd/branches/1.3.x/conf/mime.types + */ + public function getMimetypeFromFilename($filename) + { + return $this->getMimetypeFromExtension(pathinfo($filename, PATHINFO_EXTENSION)); + } + + /** + * {@inheritdoc} + * + * @see http://svn.apache.org/repos/asf/httpd/httpd/branches/1.3.x/conf/mime.types + */ + public function getMimetypeFromExtension($extension) + { + static $mimetypes = [ + '7z' => 'application/x-7z-compressed', + 'aac' => 'audio/x-aac', + 'ai' => 'application/postscript', + 'aif' => 'audio/x-aiff', + 'asc' => 'text/plain', + 'asf' => 'video/x-ms-asf', + 'atom' => 'application/atom+xml', + 'avi' => 'video/x-msvideo', + 'bmp' => 'image/bmp', + 'bz2' => 'application/x-bzip2', + 'cer' => 'application/pkix-cert', + 'crl' => 'application/pkix-crl', + 'crt' => 'application/x-x509-ca-cert', + 'css' => 'text/css', + 'csv' => 'text/csv', + 'cu' => 'application/cu-seeme', + 'deb' => 'application/x-debian-package', + 'doc' => 'application/msword', + 'docx' => 'application/vnd.openxmlformats-officedocument.wordprocessingml.document', + 'dvi' => 'application/x-dvi', + 'eot' => 'application/vnd.ms-fontobject', + 'eps' => 'application/postscript', + 'epub' => 'application/epub+zip', + 'etx' => 'text/x-setext', + 'flac' => 'audio/flac', + 'flv' => 'video/x-flv', + 'gif' => 'image/gif', + 'gz' => 'application/gzip', + 'htm' => 'text/html', + 'html' => 'text/html', + 'ico' => 'image/x-icon', + 'ics' => 'text/calendar', + 'ini' => 'text/plain', + 'iso' => 'application/x-iso9660-image', + 'jar' => 'application/java-archive', + 'jpe' => 'image/jpeg', + 'jpeg' => 'image/jpeg', + 'jpg' => 'image/jpeg', + 'js' => 'text/javascript', + 'json' => 'application/json', + 'latex' => 'application/x-latex', + 'log' => 'text/plain', + 'm4a' => 'audio/mp4', + 'm4v' => 'video/mp4', + 'mid' => 'audio/midi', + 'midi' => 'audio/midi', + 'mov' => 'video/quicktime', + 'mp3' => 'audio/mpeg', + 'mp4' => 'video/mp4', + 'mp4a' => 'audio/mp4', + 'mp4v' => 'video/mp4', + 'mpe' => 'video/mpeg', + 'mpeg' => 'video/mpeg', + 'mpg' => 'video/mpeg', + 'mpg4' => 'video/mp4', + 'oga' => 'audio/ogg', + 'ogg' => 'audio/ogg', + 'ogv' => 'video/ogg', + 'ogx' => 'application/ogg', + 'pbm' => 'image/x-portable-bitmap', + 'pdf' => 'application/pdf', + 'pgm' => 'image/x-portable-graymap', + 'png' => 'image/png', + 'pnm' => 'image/x-portable-anymap', + 'ppm' => 'image/x-portable-pixmap', + 'ppt' => 'application/vnd.ms-powerpoint', + 'pptx' => 'application/vnd.openxmlformats-officedocument.presentationml.presentation', + 'ps' => 'application/postscript', + 'qt' => 'video/quicktime', + 'rar' => 'application/x-rar-compressed', + 'ras' => 'image/x-cmu-raster', + 'rss' => 'application/rss+xml', + 'rtf' => 'application/rtf', + 'sgm' => 'text/sgml', + 'sgml' => 'text/sgml', + 'svg' => 'image/svg+xml', + 'swf' => 'application/x-shockwave-flash', + 'tar' => 'application/x-tar', + 'tif' => 'image/tiff', + 'tiff' => 'image/tiff', + 'torrent' => 'application/x-bittorrent', + 'ttf' => 'application/x-font-ttf', + 'txt' => 'text/plain', + 'wav' => 'audio/x-wav', + 'webm' => 'video/webm', + 'wma' => 'audio/x-ms-wma', + 'wmv' => 'video/x-ms-wmv', + 'woff' => 'application/x-font-woff', + 'wsdl' => 'application/wsdl+xml', + 'xbm' => 'image/x-xbitmap', + 'xls' => 'application/vnd.ms-excel', + 'xlsx' => 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet', + 'xml' => 'application/xml', + 'xpm' => 'image/x-xpixmap', + 'xwd' => 'image/x-xwindowdump', + 'yaml' => 'text/yaml', + 'yml' => 'text/yaml', + 'zip' => 'application/zip', + + // Non-Apache standard + 'pkpass' => 'application/vnd.apple.pkpass', + 'msg' => 'application/vnd.ms-outlook', + ]; + + $extension = strtolower($extension); + + return isset($mimetypes[$extension]) + ? $mimetypes[$extension] + : null; + } +} diff --git a/inc/mailgun/php-http/multipart-stream-builder/src/CustomMimetypeHelper.php b/inc/mailgun/php-http/multipart-stream-builder/src/CustomMimetypeHelper.php new file mode 100644 index 0000000..9f3f0d9 --- /dev/null +++ b/inc/mailgun/php-http/multipart-stream-builder/src/CustomMimetypeHelper.php @@ -0,0 +1,51 @@ + + */ +class CustomMimetypeHelper extends ApacheMimetypeHelper +{ + /** + * @var array + */ + private $mimetypes = []; + + /** + * @param array $mimetypes should be of type extension => mimetype + */ + public function __construct(array $mimetypes = []) + { + $this->mimetypes = $mimetypes; + } + + /** + * @param string $extension + * @param string $mimetype + * + * @return $this + */ + public function addMimetype($extension, $mimetype) + { + $this->mimetypes[$extension] = $mimetype; + + return $this; + } + + /** + * {@inheritdoc} + * + * Check if we have any defined mimetypes and of not fallback to ApacheMimetypeHelper + */ + public function getMimetypeFromExtension($extension) + { + $extension = strtolower($extension); + + return isset($this->mimetypes[$extension]) + ? $this->mimetypes[$extension] + : parent::getMimetypeFromExtension($extension); + } +} diff --git a/inc/mailgun/php-http/multipart-stream-builder/src/MimetypeHelper.php b/inc/mailgun/php-http/multipart-stream-builder/src/MimetypeHelper.php new file mode 100644 index 0000000..fa7cf18 --- /dev/null +++ b/inc/mailgun/php-http/multipart-stream-builder/src/MimetypeHelper.php @@ -0,0 +1,27 @@ + + */ +interface MimetypeHelper +{ + /** + * Determines the mimetype of a file by looking at its extension. + * + * @param string $filename + * + * @return null|string + */ + public function getMimetypeFromFilename($filename); + + /** + * Maps a file extensions to a mimetype. + * + * @param string $extension The file extension + * + * @return string|null + */ + public function getMimetypeFromExtension($extension); +} diff --git a/inc/mailgun/php-http/multipart-stream-builder/src/MultipartStreamBuilder.php b/inc/mailgun/php-http/multipart-stream-builder/src/MultipartStreamBuilder.php new file mode 100644 index 0000000..f8170b8 --- /dev/null +++ b/inc/mailgun/php-http/multipart-stream-builder/src/MultipartStreamBuilder.php @@ -0,0 +1,279 @@ + + */ +class MultipartStreamBuilder +{ + /** + * @var StreamFactory + */ + private $streamFactory; + + /** + * @var MimetypeHelper + */ + private $mimetypeHelper; + + /** + * @var string + */ + private $boundary; + + /** + * @var array Element where each Element is an array with keys ['contents', 'headers', 'filename'] + */ + private $data = []; + + /** + * @param StreamFactory|null $streamFactory + */ + public function __construct(StreamFactory $streamFactory = null) + { + $this->streamFactory = $streamFactory ?: StreamFactoryDiscovery::find(); + } + + /** + * Add a resource to the Multipart Stream. If the same $name is used twice the first resource will + * be overwritten. + * + * @param string $name the formpost name + * @param string|resource|StreamInterface $resource + * @param array $options { + * + * @var array $headers additional headers ['header-name' => 'header-value'] + * @var string $filename + * } + * + * @return MultipartStreamBuilder + */ + public function addResource($name, $resource, array $options = []) + { + $stream = $this->streamFactory->createStream($resource); + + // validate options['headers'] exists + if (!isset($options['headers'])) { + $options['headers'] = []; + } + + // Try to add filename if it is missing + if (empty($options['filename'])) { + $options['filename'] = null; + $uri = $stream->getMetadata('uri'); + if (substr($uri, 0, 6) !== 'php://') { + $options['filename'] = $uri; + } + } + + $this->prepareHeaders($name, $stream, $options['filename'], $options['headers']); + $this->data[$name] = ['contents' => $stream, 'headers' => $options['headers'], 'filename' => $options['filename']]; + + return $this; + } + + /** + * Build the stream. + * + * @return StreamInterface + */ + public function build() + { + $streams = ''; + foreach ($this->data as $data) { + // Add start and headers + $streams .= "--{$this->getBoundary()}\r\n". + $this->getHeaders($data['headers'])."\r\n"; + + // Convert the stream to string + /* @var $contentStream StreamInterface */ + $contentStream = $data['contents']; + if ($contentStream->isSeekable()) { + $streams .= $contentStream->__toString(); + } else { + $streams .= $contentStream->getContents(); + } + + $streams .= "\r\n"; + } + + // Append end + $streams .= "--{$this->getBoundary()}--\r\n"; + + return $this->streamFactory->createStream($streams); + } + + /** + * Add extra headers if they are missing. + * + * @param string $name + * @param StreamInterface $stream + * @param string $filename + * @param array &$headers + */ + private function prepareHeaders($name, StreamInterface $stream, $filename, array &$headers) + { + $hasFilename = $filename === '0' || $filename; + + // Set a default content-disposition header if one was not provided + if (!$this->hasHeader($headers, 'content-disposition')) { + $headers['Content-Disposition'] = sprintf('form-data; name="%s"', $name); + if ($hasFilename) { + $headers['Content-Disposition'] .= sprintf('; filename="%s"', $this->basename($filename)); + } + } + + // Set a default content-length header if one was not provided + if (!$this->hasHeader($headers, 'content-length')) { + if ($length = $stream->getSize()) { + $headers['Content-Length'] = (string) $length; + } + } + + // Set a default Content-Type if one was not provided + if (!$this->hasHeader($headers, 'content-type') && $hasFilename) { + if ($type = $this->getMimetypeHelper()->getMimetypeFromFilename($filename)) { + $headers['Content-Type'] = $type; + } + } + } + + /** + * Get the headers formatted for the HTTP message. + * + * @param array $headers + * + * @return string + */ + private function getHeaders(array $headers) + { + $str = ''; + foreach ($headers as $key => $value) { + $str .= sprintf("%s: %s\r\n", $key, $value); + } + + return $str; + } + + /** + * Check if header exist. + * + * @param array $headers + * @param string $key case insensitive + * + * @return bool + */ + private function hasHeader(array $headers, $key) + { + $lowercaseHeader = strtolower($key); + foreach ($headers as $k => $v) { + if (strtolower($k) === $lowercaseHeader) { + return true; + } + } + + return false; + } + + /** + * Get the boundary that separates the streams. + * + * @return string + */ + public function getBoundary() + { + if ($this->boundary === null) { + $this->boundary = uniqid('', true); + } + + return $this->boundary; + } + + /** + * @param string $boundary + * + * @return MultipartStreamBuilder + */ + public function setBoundary($boundary) + { + $this->boundary = $boundary; + + return $this; + } + + /** + * @return MimetypeHelper + */ + private function getMimetypeHelper() + { + if ($this->mimetypeHelper === null) { + $this->mimetypeHelper = new ApacheMimetypeHelper(); + } + + return $this->mimetypeHelper; + } + + /** + * If you have custom file extension you may overwrite the default MimetypeHelper with your own. + * + * @param MimetypeHelper $mimetypeHelper + * + * @return MultipartStreamBuilder + */ + public function setMimetypeHelper(MimetypeHelper $mimetypeHelper) + { + $this->mimetypeHelper = $mimetypeHelper; + + return $this; + } + + /** + * Reset and clear all stored data. This allows you to use builder for a subsequent request. + * + * @return MultipartStreamBuilder + */ + public function reset() + { + $this->data = []; + $this->boundary = null; + + return $this; + } + + /** + * Gets the filename from a given path. + * + * PHP's basename() does not properly support streams or filenames beginning with a non-US-ASCII character. + * + * @author Drupal 8.2 + * + * @param string $path + * + * @return string + */ + private function basename($path) + { + $separators = '/'; + if (DIRECTORY_SEPARATOR != '/') { + // For Windows OS add special separator. + $separators .= DIRECTORY_SEPARATOR; + } + + // Remove right-most slashes when $path points to directory. + $path = rtrim($path, $separators); + + // Returns the trailing part of the $path starting after one of the directory separators. + $filename = preg_match('@[^'.preg_quote($separators, '@').']+$@', $path, $matches) ? $matches[0] : ''; + + return $filename; + } +} -- cgit v1.2.3