├── .editorconfig ├── .gitignore ├── .idea ├── .name ├── Stream.iml ├── composerJson.xml ├── copyright │ └── profiles_settings.xml ├── encodings.xml ├── inspectionProfiles │ ├── Project_Default.xml │ └── profiles_settings.xml ├── modules.xml ├── php.xml ├── scopes │ └── scope_settings.xml └── vcs.xml ├── .scrutinizer.yml ├── .travis.yml ├── CHANGELOG.md ├── CONTRIBUTING.md ├── LICENSE.md ├── README.md ├── build.xml ├── composer.json ├── composer.lock ├── phpunit.xml.dist ├── sami-config.php ├── src ├── ByteOrder.php ├── Exception │ ├── BadMethodCallException.php │ ├── ExceptionInterface.php │ ├── IOException.php │ └── InvalidArgumentException.php └── Stream.php └── tests └── src ├── ByteOrderTest.php ├── Helper ├── ByteOrderHelper.php └── ResourceHelper.php └── StreamTest.php /.editorconfig: -------------------------------------------------------------------------------- 1 | ; This file is for unifying the coding style for different editors and IDEs. 2 | ; More information at http://editorconfig.org 3 | 4 | root = true 5 | 6 | [*] 7 | indent_size = 4 8 | indent_style = space 9 | end_of_line = lf 10 | insert_final_newline = true 11 | trim_trailing_whitespace = true 12 | 13 | [*.md] 14 | trim_trailing_whitespace = false 15 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | .idea/deployment.xml 2 | .idea/workspace.xml 3 | build/ 4 | cache/ 5 | vendor/ 6 | composer.phar 7 | coverage.clover 8 | phpunit.xml 9 | -------------------------------------------------------------------------------- /.idea/.name: -------------------------------------------------------------------------------- 1 | Stream -------------------------------------------------------------------------------- /.idea/Stream.iml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /.idea/composerJson.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /.idea/copyright/profiles_settings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | -------------------------------------------------------------------------------- /.idea/encodings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /.idea/inspectionProfiles/Project_Default.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 10 | -------------------------------------------------------------------------------- /.idea/inspectionProfiles/profiles_settings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 7 | -------------------------------------------------------------------------------- /.idea/modules.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /.idea/php.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /.idea/scopes/scope_settings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 5 | -------------------------------------------------------------------------------- /.idea/vcs.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /.scrutinizer.yml: -------------------------------------------------------------------------------- 1 | filter: 2 | excluded_paths: 3 | - "tests/*" 4 | 5 | checks: 6 | php: 7 | remove_extra_empty_lines: true 8 | remove_php_closing_tag: true 9 | remove_trailing_whitespace: true 10 | fix_use_statements: 11 | remove_unused: true 12 | preserve_multiple: false 13 | preserve_blanklines: true 14 | order_alphabetically: true 15 | fix_php_opening_tag: true 16 | fix_linefeed: true 17 | fix_line_ending: true 18 | fix_identation_4spaces: true 19 | fix_doc_comments: true 20 | 21 | tools: 22 | external_code_coverage: 23 | timeout: 600 24 | runs: 2 25 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | language: "php" 2 | 3 | php: 4 | - "5.6" 5 | - "7.0" 6 | 7 | before_install: 8 | - "composer self-update" 9 | 10 | install: 11 | - "composer install" 12 | 13 | script: 14 | - "php vendor/bin/phpunit --coverage-clover=coverage.clover --coverage-text --verbose" 15 | 16 | after_script: 17 | - "php vendor/bin/ocular code-coverage:upload --format=php-clover coverage.clover" 18 | -------------------------------------------------------------------------------- /CHANGELOG.md: -------------------------------------------------------------------------------- 1 | # Changelog 2 | 3 | All Notable changes to `gravitymedia/stream` will be documented in this file. 4 | This project adheres to [Semantic Versioning](http://semver.org/). 5 | 6 | ## NEXT - YYYY-MM-DD 7 | 8 | ### Added 9 | - Nothing 10 | 11 | ### Changed 12 | - Nothing 13 | 14 | ### Deprecated 15 | - Nothing 16 | 17 | ### Removed 18 | - Nothing 19 | 20 | ### Fixed 21 | - Nothing 22 | 23 | ### Security 24 | - Nothing 25 | -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contributing 2 | 3 | Contributions are **welcome** and will be fully **credited**. 4 | 5 | We accept contributions via Pull Requests on [Github](https://github.com/GravityMedia/Stream). 6 | 7 | ## Pull Requests 8 | 9 | - **[PSR-2 Coding Standard](https://github.com/php-fig/fig-standards/blob/master/accepted/PSR-2-coding-style-guide.md)** - The easiest way to apply the conventions is to install [PHP Code Sniffer](http://pear.php.net/package/PHP_CodeSniffer). 10 | 11 | - **Add tests!** - Your patch won't be accepted if it doesn't have tests. 12 | 13 | - **Document any change in behaviour** - Make sure the `README.md` and any other relevant documentation are kept up-to-date. 14 | 15 | - **Consider our release cycle** - We try to follow [SemVer v2.0.0](http://semver.org/). Randomly breaking public APIs is not an option. 16 | 17 | - **Create feature branches** - Don't ask us to pull from your master branch. 18 | 19 | - **One pull request per feature** - If you want to do more than one thing, send multiple pull requests. 20 | 21 | - **Send coherent history** - Make sure each individual commit in your pull request is meaningful. If you had to make multiple intermediate commits while developing, please [squash them](http://www.git-scm.com/book/en/v2/Git-Tools-Rewriting-History#Changing-Multiple-Commit-Messages) before submitting. 22 | 23 | ## Running Tests 24 | 25 | ``` bash 26 | $ php vendor/bin/phpunit --coverage-text --verbose 27 | ``` 28 | -------------------------------------------------------------------------------- /LICENSE.md: -------------------------------------------------------------------------------- 1 | # The MIT License (MIT) 2 | 3 | Copyright (c) 2015 Daniel Schröder 4 | 5 | > Permission is hereby granted, free of charge, to any person obtaining a copy 6 | > of this software and associated documentation files (the "Software"), to deal 7 | > in the Software without restriction, including without limitation the rights 8 | > to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | > copies of the Software, and to permit persons to whom the Software is 10 | > furnished to do so, subject to the following conditions: 11 | > 12 | > The above copyright notice and this permission notice shall be included in 13 | > all copies or substantial portions of the Software. 14 | > 15 | > THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | > IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | > FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | > AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | > LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | > OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | > THE SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Stream 2 | 3 | [![Latest Version on Packagist](https://img.shields.io/packagist/v/gravitymedia/stream.svg)](https://packagist.org/packages/gravitymedia/stream) 4 | [![Software License](https://img.shields.io/packagist/l/gravitymedia/stream.svg)](LICENSE.md) 5 | [![Build Status](https://img.shields.io/travis/GravityMedia/Stream.svg)](https://travis-ci.org/GravityMedia/Stream) 6 | [![Coverage Status](https://img.shields.io/scrutinizer/coverage/g/GravityMedia/Stream.svg)](https://scrutinizer-ci.com/g/GravityMedia/Stream/code-structure) 7 | [![Quality Score](https://img.shields.io/scrutinizer/g/GravityMedia/Stream.svg)](https://scrutinizer-ci.com/g/GravityMedia/Stream) 8 | [![Total Downloads](https://img.shields.io/packagist/dt/gravitymedia/stream.svg)](https://packagist.org/packages/gravitymedia/stream) 9 | [![Dependency Status](https://img.shields.io/versioneye/d/php/gravitymedia:stream.svg)](https://www.versioneye.com/user/projects/54f76e264f31083e1b0017e2) 10 | 11 | Stream is an object oriented library for reading and writing binary streams in PHP. 12 | 13 | ## Requirements 14 | 15 | This library has the following requirements: 16 | 17 | - PHP 5.6+ 18 | 19 | ## Installation 20 | 21 | Install Composer in your project: 22 | 23 | ```bash 24 | $ curl -s https://getcomposer.org/installer | php 25 | ``` 26 | 27 | Add the package to your `composer.json` and install it via Composer: 28 | 29 | ```bash 30 | $ php composer.phar require gravitymedia/stream 31 | ``` 32 | 33 | ## Usage 34 | 35 | This is a simple usage example for character streams but is applicable for binary data streams. 36 | 37 | ```php 38 | require 'vendor/autoload.php'; 39 | 40 | use GravityMedia\Stream\Stream; 41 | 42 | // create resource 43 | $resource = fopen('php://temp', 'r+'); 44 | 45 | // create new stream object 46 | $stream = Stream::fromResource($resource); 47 | 48 | // write some data 49 | $stream->write("\x63\x6f\x6e\x74\x65\x6e\x74\x73"); 50 | 51 | // seek a position 52 | $stream->seek(4); 53 | 54 | // print 32 bit unsigned integer 55 | print $stream->readUInt32() . PHP_EOL; 56 | 57 | // rewind stream 58 | $stream->rewind(); 59 | 60 | // print the data previously written 61 | while (!$stream->eof()) { 62 | print $stream->read(1); 63 | } 64 | print PHP_EOL; 65 | 66 | // print position 67 | print $stream->tell() . PHP_EOL; 68 | 69 | // rewind stream 70 | $stream->rewind(); 71 | 72 | // truncate random data 73 | $stream->truncate(7); 74 | 75 | // print the truncated data 76 | while (!$stream->eof()) { 77 | print $stream->read(1); 78 | } 79 | print PHP_EOL; 80 | ``` 81 | 82 | ## Testing 83 | 84 | Clone this repository, install Composer and all dependencies: 85 | 86 | ```bash 87 | $ php composer.phar install 88 | ``` 89 | 90 | Run the test suite: 91 | 92 | ```bash 93 | $ php vendor/bin/phing test 94 | ``` 95 | 96 | ## Generating documentation 97 | 98 | Clone this repository, install Composer and all dependencies: 99 | 100 | ```bash 101 | $ php composer.phar install 102 | ``` 103 | 104 | Generate the documentation to the `build/docs` directory: 105 | 106 | ```bash 107 | $ php vendor/bin/phing doc 108 | ``` 109 | 110 | ## Contributing 111 | 112 | Please see [CONTRIBUTING](CONTRIBUTING.md) for details. 113 | 114 | ## Credits 115 | 116 | - [Daniel Schröder](https://github.com/pCoLaSD) 117 | - [All Contributors](../../contributors) 118 | 119 | ## License 120 | 121 | The MIT License (MIT). Please see [License File](LICENSE.md) for more information. 122 | -------------------------------------------------------------------------------- /build.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | -------------------------------------------------------------------------------- /composer.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "gravitymedia/stream", 3 | "description": "Stream is an object oriented library for reading and writing binary streams in PHP.", 4 | "keywords": [ 5 | "gravitymedia", 6 | "stream", 7 | "binary", 8 | "fread", 9 | "fwrite" 10 | ], 11 | "homepage": "https://github.com/GravityMedia/Stream", 12 | "license": "MIT", 13 | "authors": [ 14 | { 15 | "name": "Daniel Schröder", 16 | "email": "daniel.schroeder@gravitymedia.de", 17 | "homepage": "https://github.com/pCoLaSD", 18 | "role": "Developer" 19 | } 20 | ], 21 | "require": { 22 | "php": "^5.6 || ^7.0" 23 | }, 24 | "require-dev": { 25 | "phing/phing": "^2.14", 26 | "phpunit/phpunit": "^5.3", 27 | "sami/sami": "^3.2", 28 | "scrutinizer/ocular": "^1.3", 29 | "symfony/finder": "^2.8" 30 | }, 31 | "autoload": { 32 | "psr-4": { 33 | "GravityMedia\\Stream\\": "src/" 34 | } 35 | }, 36 | "autoload-dev": { 37 | "psr-4": { 38 | "GravityMedia\\StreamTest\\": "tests/src/" 39 | } 40 | }, 41 | "extra": { 42 | "branch-alias": { 43 | "dev-master": "1.0-dev" 44 | } 45 | }, 46 | "archive": { 47 | "exclude": [ 48 | "/.*", 49 | "/*.php", 50 | "/build.*", 51 | "/composer.*", 52 | "/phpunit.*", 53 | "/tests" 54 | ] 55 | } 56 | } 57 | -------------------------------------------------------------------------------- /composer.lock: -------------------------------------------------------------------------------- 1 | { 2 | "_readme": [ 3 | "This file locks the dependencies of your project to a known state", 4 | "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#composer-lock-the-lock-file", 5 | "This file is @generated automatically" 6 | ], 7 | "hash": "1221c8f3362a41eabccb2f2614f65b93", 8 | "content-hash": "a2eccfac77779089abd302096c323960", 9 | "packages": [], 10 | "packages-dev": [ 11 | { 12 | "name": "blackfire/php-sdk", 13 | "version": "v1.5.12", 14 | "source": { 15 | "type": "git", 16 | "url": "https://github.com/blackfireio/php-sdk.git", 17 | "reference": "fee598740a7927db7781e645d279142a7a77bb4b" 18 | }, 19 | "dist": { 20 | "type": "zip", 21 | "url": "https://api.github.com/repos/blackfireio/php-sdk/zipball/fee598740a7927db7781e645d279142a7a77bb4b", 22 | "reference": "fee598740a7927db7781e645d279142a7a77bb4b", 23 | "shasum": "" 24 | }, 25 | "require": { 26 | "php": ">=5.2.0" 27 | }, 28 | "suggest": { 29 | "ext-blackfire": "The C version of the Blackfire probe", 30 | "ext-xhprof": "XHProf is required as a fallback" 31 | }, 32 | "type": "library", 33 | "extra": { 34 | "branch-alias": { 35 | "dev-master": "1.5.x-dev" 36 | } 37 | }, 38 | "autoload": { 39 | "files": [ 40 | "src/autostart.php" 41 | ], 42 | "psr-4": { 43 | "Blackfire\\": "src/Blackfire" 44 | } 45 | }, 46 | "notification-url": "https://packagist.org/downloads/", 47 | "license": [ 48 | "MIT" 49 | ], 50 | "authors": [ 51 | { 52 | "name": "Blackfire.io", 53 | "email": "support@blackfire.io" 54 | } 55 | ], 56 | "description": "Blackfire.io PHP SDK", 57 | "keywords": [ 58 | "performance", 59 | "profiler", 60 | "uprofiler", 61 | "xhprof" 62 | ], 63 | "time": "2016-03-17 15:37:22" 64 | }, 65 | { 66 | "name": "doctrine/annotations", 67 | "version": "v1.2.7", 68 | "source": { 69 | "type": "git", 70 | "url": "https://github.com/doctrine/annotations.git", 71 | "reference": "f25c8aab83e0c3e976fd7d19875f198ccf2f7535" 72 | }, 73 | "dist": { 74 | "type": "zip", 75 | "url": "https://api.github.com/repos/doctrine/annotations/zipball/f25c8aab83e0c3e976fd7d19875f198ccf2f7535", 76 | "reference": "f25c8aab83e0c3e976fd7d19875f198ccf2f7535", 77 | "shasum": "" 78 | }, 79 | "require": { 80 | "doctrine/lexer": "1.*", 81 | "php": ">=5.3.2" 82 | }, 83 | "require-dev": { 84 | "doctrine/cache": "1.*", 85 | "phpunit/phpunit": "4.*" 86 | }, 87 | "type": "library", 88 | "extra": { 89 | "branch-alias": { 90 | "dev-master": "1.3.x-dev" 91 | } 92 | }, 93 | "autoload": { 94 | "psr-0": { 95 | "Doctrine\\Common\\Annotations\\": "lib/" 96 | } 97 | }, 98 | "notification-url": "https://packagist.org/downloads/", 99 | "license": [ 100 | "MIT" 101 | ], 102 | "authors": [ 103 | { 104 | "name": "Roman Borschel", 105 | "email": "roman@code-factory.org" 106 | }, 107 | { 108 | "name": "Benjamin Eberlei", 109 | "email": "kontakt@beberlei.de" 110 | }, 111 | { 112 | "name": "Guilherme Blanco", 113 | "email": "guilhermeblanco@gmail.com" 114 | }, 115 | { 116 | "name": "Jonathan Wage", 117 | "email": "jonwage@gmail.com" 118 | }, 119 | { 120 | "name": "Johannes Schmitt", 121 | "email": "schmittjoh@gmail.com" 122 | } 123 | ], 124 | "description": "Docblock Annotations Parser", 125 | "homepage": "http://www.doctrine-project.org", 126 | "keywords": [ 127 | "annotations", 128 | "docblock", 129 | "parser" 130 | ], 131 | "time": "2015-08-31 12:32:49" 132 | }, 133 | { 134 | "name": "doctrine/instantiator", 135 | "version": "1.0.5", 136 | "source": { 137 | "type": "git", 138 | "url": "https://github.com/doctrine/instantiator.git", 139 | "reference": "8e884e78f9f0eb1329e445619e04456e64d8051d" 140 | }, 141 | "dist": { 142 | "type": "zip", 143 | "url": "https://api.github.com/repos/doctrine/instantiator/zipball/8e884e78f9f0eb1329e445619e04456e64d8051d", 144 | "reference": "8e884e78f9f0eb1329e445619e04456e64d8051d", 145 | "shasum": "" 146 | }, 147 | "require": { 148 | "php": ">=5.3,<8.0-DEV" 149 | }, 150 | "require-dev": { 151 | "athletic/athletic": "~0.1.8", 152 | "ext-pdo": "*", 153 | "ext-phar": "*", 154 | "phpunit/phpunit": "~4.0", 155 | "squizlabs/php_codesniffer": "~2.0" 156 | }, 157 | "type": "library", 158 | "extra": { 159 | "branch-alias": { 160 | "dev-master": "1.0.x-dev" 161 | } 162 | }, 163 | "autoload": { 164 | "psr-4": { 165 | "Doctrine\\Instantiator\\": "src/Doctrine/Instantiator/" 166 | } 167 | }, 168 | "notification-url": "https://packagist.org/downloads/", 169 | "license": [ 170 | "MIT" 171 | ], 172 | "authors": [ 173 | { 174 | "name": "Marco Pivetta", 175 | "email": "ocramius@gmail.com", 176 | "homepage": "http://ocramius.github.com/" 177 | } 178 | ], 179 | "description": "A small, lightweight utility to instantiate objects in PHP without invoking their constructors", 180 | "homepage": "https://github.com/doctrine/instantiator", 181 | "keywords": [ 182 | "constructor", 183 | "instantiate" 184 | ], 185 | "time": "2015-06-14 21:17:01" 186 | }, 187 | { 188 | "name": "doctrine/lexer", 189 | "version": "v1.0.1", 190 | "source": { 191 | "type": "git", 192 | "url": "https://github.com/doctrine/lexer.git", 193 | "reference": "83893c552fd2045dd78aef794c31e694c37c0b8c" 194 | }, 195 | "dist": { 196 | "type": "zip", 197 | "url": "https://api.github.com/repos/doctrine/lexer/zipball/83893c552fd2045dd78aef794c31e694c37c0b8c", 198 | "reference": "83893c552fd2045dd78aef794c31e694c37c0b8c", 199 | "shasum": "" 200 | }, 201 | "require": { 202 | "php": ">=5.3.2" 203 | }, 204 | "type": "library", 205 | "extra": { 206 | "branch-alias": { 207 | "dev-master": "1.0.x-dev" 208 | } 209 | }, 210 | "autoload": { 211 | "psr-0": { 212 | "Doctrine\\Common\\Lexer\\": "lib/" 213 | } 214 | }, 215 | "notification-url": "https://packagist.org/downloads/", 216 | "license": [ 217 | "MIT" 218 | ], 219 | "authors": [ 220 | { 221 | "name": "Roman Borschel", 222 | "email": "roman@code-factory.org" 223 | }, 224 | { 225 | "name": "Guilherme Blanco", 226 | "email": "guilhermeblanco@gmail.com" 227 | }, 228 | { 229 | "name": "Johannes Schmitt", 230 | "email": "schmittjoh@gmail.com" 231 | } 232 | ], 233 | "description": "Base library for a lexer that can be used in Top-Down, Recursive Descent Parsers.", 234 | "homepage": "http://www.doctrine-project.org", 235 | "keywords": [ 236 | "lexer", 237 | "parser" 238 | ], 239 | "time": "2014-09-09 13:34:57" 240 | }, 241 | { 242 | "name": "guzzle/guzzle", 243 | "version": "v3.9.3", 244 | "source": { 245 | "type": "git", 246 | "url": "https://github.com/guzzle/guzzle3.git", 247 | "reference": "0645b70d953bc1c067bbc8d5bc53194706b628d9" 248 | }, 249 | "dist": { 250 | "type": "zip", 251 | "url": "https://api.github.com/repos/guzzle/guzzle3/zipball/0645b70d953bc1c067bbc8d5bc53194706b628d9", 252 | "reference": "0645b70d953bc1c067bbc8d5bc53194706b628d9", 253 | "shasum": "" 254 | }, 255 | "require": { 256 | "ext-curl": "*", 257 | "php": ">=5.3.3", 258 | "symfony/event-dispatcher": "~2.1" 259 | }, 260 | "replace": { 261 | "guzzle/batch": "self.version", 262 | "guzzle/cache": "self.version", 263 | "guzzle/common": "self.version", 264 | "guzzle/http": "self.version", 265 | "guzzle/inflection": "self.version", 266 | "guzzle/iterator": "self.version", 267 | "guzzle/log": "self.version", 268 | "guzzle/parser": "self.version", 269 | "guzzle/plugin": "self.version", 270 | "guzzle/plugin-async": "self.version", 271 | "guzzle/plugin-backoff": "self.version", 272 | "guzzle/plugin-cache": "self.version", 273 | "guzzle/plugin-cookie": "self.version", 274 | "guzzle/plugin-curlauth": "self.version", 275 | "guzzle/plugin-error-response": "self.version", 276 | "guzzle/plugin-history": "self.version", 277 | "guzzle/plugin-log": "self.version", 278 | "guzzle/plugin-md5": "self.version", 279 | "guzzle/plugin-mock": "self.version", 280 | "guzzle/plugin-oauth": "self.version", 281 | "guzzle/service": "self.version", 282 | "guzzle/stream": "self.version" 283 | }, 284 | "require-dev": { 285 | "doctrine/cache": "~1.3", 286 | "monolog/monolog": "~1.0", 287 | "phpunit/phpunit": "3.7.*", 288 | "psr/log": "~1.0", 289 | "symfony/class-loader": "~2.1", 290 | "zendframework/zend-cache": "2.*,<2.3", 291 | "zendframework/zend-log": "2.*,<2.3" 292 | }, 293 | "suggest": { 294 | "guzzlehttp/guzzle": "Guzzle 5 has moved to a new package name. The package you have installed, Guzzle 3, is deprecated." 295 | }, 296 | "type": "library", 297 | "extra": { 298 | "branch-alias": { 299 | "dev-master": "3.9-dev" 300 | } 301 | }, 302 | "autoload": { 303 | "psr-0": { 304 | "Guzzle": "src/", 305 | "Guzzle\\Tests": "tests/" 306 | } 307 | }, 308 | "notification-url": "https://packagist.org/downloads/", 309 | "license": [ 310 | "MIT" 311 | ], 312 | "authors": [ 313 | { 314 | "name": "Michael Dowling", 315 | "email": "mtdowling@gmail.com", 316 | "homepage": "https://github.com/mtdowling" 317 | }, 318 | { 319 | "name": "Guzzle Community", 320 | "homepage": "https://github.com/guzzle/guzzle/contributors" 321 | } 322 | ], 323 | "description": "PHP HTTP client. This library is deprecated in favor of https://packagist.org/packages/guzzlehttp/guzzle", 324 | "homepage": "http://guzzlephp.org/", 325 | "keywords": [ 326 | "client", 327 | "curl", 328 | "framework", 329 | "http", 330 | "http client", 331 | "rest", 332 | "web service" 333 | ], 334 | "time": "2015-03-18 18:23:50" 335 | }, 336 | { 337 | "name": "jms/metadata", 338 | "version": "1.5.1", 339 | "source": { 340 | "type": "git", 341 | "url": "https://github.com/schmittjoh/metadata.git", 342 | "reference": "22b72455559a25777cfd28c4ffda81ff7639f353" 343 | }, 344 | "dist": { 345 | "type": "zip", 346 | "url": "https://api.github.com/repos/schmittjoh/metadata/zipball/22b72455559a25777cfd28c4ffda81ff7639f353", 347 | "reference": "22b72455559a25777cfd28c4ffda81ff7639f353", 348 | "shasum": "" 349 | }, 350 | "require": { 351 | "php": ">=5.3.0" 352 | }, 353 | "require-dev": { 354 | "doctrine/cache": "~1.0" 355 | }, 356 | "type": "library", 357 | "extra": { 358 | "branch-alias": { 359 | "dev-master": "1.5.x-dev" 360 | } 361 | }, 362 | "autoload": { 363 | "psr-0": { 364 | "Metadata\\": "src/" 365 | } 366 | }, 367 | "notification-url": "https://packagist.org/downloads/", 368 | "license": [ 369 | "Apache" 370 | ], 371 | "authors": [ 372 | { 373 | "name": "Johannes Schmitt", 374 | "email": "schmittjoh@gmail.com", 375 | "homepage": "https://github.com/schmittjoh", 376 | "role": "Developer of wrapped JMSSerializerBundle" 377 | } 378 | ], 379 | "description": "Class/method/property metadata management in PHP", 380 | "keywords": [ 381 | "annotations", 382 | "metadata", 383 | "xml", 384 | "yaml" 385 | ], 386 | "time": "2014-07-12 07:13:19" 387 | }, 388 | { 389 | "name": "jms/parser-lib", 390 | "version": "1.0.0", 391 | "source": { 392 | "type": "git", 393 | "url": "https://github.com/schmittjoh/parser-lib.git", 394 | "reference": "c509473bc1b4866415627af0e1c6cc8ac97fa51d" 395 | }, 396 | "dist": { 397 | "type": "zip", 398 | "url": "https://api.github.com/repos/schmittjoh/parser-lib/zipball/c509473bc1b4866415627af0e1c6cc8ac97fa51d", 399 | "reference": "c509473bc1b4866415627af0e1c6cc8ac97fa51d", 400 | "shasum": "" 401 | }, 402 | "require": { 403 | "phpoption/phpoption": ">=0.9,<2.0-dev" 404 | }, 405 | "type": "library", 406 | "extra": { 407 | "branch-alias": { 408 | "dev-master": "1.0-dev" 409 | } 410 | }, 411 | "autoload": { 412 | "psr-0": { 413 | "JMS\\": "src/" 414 | } 415 | }, 416 | "notification-url": "https://packagist.org/downloads/", 417 | "license": [ 418 | "Apache2" 419 | ], 420 | "description": "A library for easily creating recursive-descent parsers.", 421 | "time": "2012-11-18 18:08:43" 422 | }, 423 | { 424 | "name": "jms/serializer", 425 | "version": "1.1.0", 426 | "source": { 427 | "type": "git", 428 | "url": "https://github.com/schmittjoh/serializer.git", 429 | "reference": "fe13a1f993ea3456e195b7820692f2eb2b6bbb48" 430 | }, 431 | "dist": { 432 | "type": "zip", 433 | "url": "https://api.github.com/repos/schmittjoh/serializer/zipball/fe13a1f993ea3456e195b7820692f2eb2b6bbb48", 434 | "reference": "fe13a1f993ea3456e195b7820692f2eb2b6bbb48", 435 | "shasum": "" 436 | }, 437 | "require": { 438 | "doctrine/annotations": "1.*", 439 | "doctrine/instantiator": "~1.0.3", 440 | "jms/metadata": "~1.1", 441 | "jms/parser-lib": "1.*", 442 | "php": ">=5.4.0", 443 | "phpcollection/phpcollection": "~0.1" 444 | }, 445 | "conflict": { 446 | "twig/twig": "<1.12" 447 | }, 448 | "require-dev": { 449 | "doctrine/orm": "~2.1", 450 | "doctrine/phpcr-odm": "~1.0.1", 451 | "jackalope/jackalope-doctrine-dbal": "1.0.*", 452 | "phpunit/phpunit": "~4.0", 453 | "propel/propel1": "~1.7", 454 | "symfony/filesystem": "2.*", 455 | "symfony/form": "~2.1", 456 | "symfony/translation": "~2.0", 457 | "symfony/validator": "~2.0", 458 | "symfony/yaml": "2.*", 459 | "twig/twig": "~1.12|~2.0" 460 | }, 461 | "suggest": { 462 | "symfony/yaml": "Required if you'd like to serialize data to YAML format." 463 | }, 464 | "type": "library", 465 | "extra": { 466 | "branch-alias": { 467 | "dev-master": "1.1-dev" 468 | } 469 | }, 470 | "autoload": { 471 | "psr-0": { 472 | "JMS\\Serializer": "src/" 473 | } 474 | }, 475 | "notification-url": "https://packagist.org/downloads/", 476 | "license": [ 477 | "Apache2" 478 | ], 479 | "authors": [ 480 | { 481 | "name": "Johannes M. Schmitt", 482 | "email": "schmittjoh@gmail.com" 483 | } 484 | ], 485 | "description": "Library for (de-)serializing data of any complexity; supports XML, JSON, and YAML.", 486 | "homepage": "http://jmsyst.com/libs/serializer", 487 | "keywords": [ 488 | "deserialization", 489 | "jaxb", 490 | "json", 491 | "serialization", 492 | "xml" 493 | ], 494 | "time": "2015-10-27 09:24:41" 495 | }, 496 | { 497 | "name": "michelf/php-markdown", 498 | "version": "1.6.0", 499 | "source": { 500 | "type": "git", 501 | "url": "https://github.com/michelf/php-markdown.git", 502 | "reference": "156e56ee036505ec637d761ee62dc425d807183c" 503 | }, 504 | "dist": { 505 | "type": "zip", 506 | "url": "https://api.github.com/repos/michelf/php-markdown/zipball/156e56ee036505ec637d761ee62dc425d807183c", 507 | "reference": "156e56ee036505ec637d761ee62dc425d807183c", 508 | "shasum": "" 509 | }, 510 | "require": { 511 | "php": ">=5.3.0" 512 | }, 513 | "type": "library", 514 | "extra": { 515 | "branch-alias": { 516 | "dev-lib": "1.4.x-dev" 517 | } 518 | }, 519 | "autoload": { 520 | "psr-0": { 521 | "Michelf": "" 522 | } 523 | }, 524 | "notification-url": "https://packagist.org/downloads/", 525 | "license": [ 526 | "BSD-3-Clause" 527 | ], 528 | "authors": [ 529 | { 530 | "name": "Michel Fortin", 531 | "email": "michel.fortin@michelf.ca", 532 | "homepage": "https://michelf.ca/", 533 | "role": "Developer" 534 | }, 535 | { 536 | "name": "John Gruber", 537 | "homepage": "https://daringfireball.net/" 538 | } 539 | ], 540 | "description": "PHP Markdown", 541 | "homepage": "https://michelf.ca/projects/php-markdown/", 542 | "keywords": [ 543 | "markdown" 544 | ], 545 | "time": "2015-12-24 01:37:31" 546 | }, 547 | { 548 | "name": "myclabs/deep-copy", 549 | "version": "1.5.1", 550 | "source": { 551 | "type": "git", 552 | "url": "https://github.com/myclabs/DeepCopy.git", 553 | "reference": "a8773992b362b58498eed24bf85005f363c34771" 554 | }, 555 | "dist": { 556 | "type": "zip", 557 | "url": "https://api.github.com/repos/myclabs/DeepCopy/zipball/a8773992b362b58498eed24bf85005f363c34771", 558 | "reference": "a8773992b362b58498eed24bf85005f363c34771", 559 | "shasum": "" 560 | }, 561 | "require": { 562 | "php": ">=5.4.0" 563 | }, 564 | "require-dev": { 565 | "doctrine/collections": "1.*", 566 | "phpunit/phpunit": "~4.1" 567 | }, 568 | "type": "library", 569 | "autoload": { 570 | "psr-4": { 571 | "DeepCopy\\": "src/DeepCopy/" 572 | } 573 | }, 574 | "notification-url": "https://packagist.org/downloads/", 575 | "license": [ 576 | "MIT" 577 | ], 578 | "description": "Create deep copies (clones) of your objects", 579 | "homepage": "https://github.com/myclabs/DeepCopy", 580 | "keywords": [ 581 | "clone", 582 | "copy", 583 | "duplicate", 584 | "object", 585 | "object graph" 586 | ], 587 | "time": "2015-11-20 12:04:31" 588 | }, 589 | { 590 | "name": "nikic/php-parser", 591 | "version": "v1.4.1", 592 | "source": { 593 | "type": "git", 594 | "url": "https://github.com/nikic/PHP-Parser.git", 595 | "reference": "f78af2c9c86107aa1a34cd1dbb5bbe9eeb0d9f51" 596 | }, 597 | "dist": { 598 | "type": "zip", 599 | "url": "https://api.github.com/repos/nikic/PHP-Parser/zipball/f78af2c9c86107aa1a34cd1dbb5bbe9eeb0d9f51", 600 | "reference": "f78af2c9c86107aa1a34cd1dbb5bbe9eeb0d9f51", 601 | "shasum": "" 602 | }, 603 | "require": { 604 | "ext-tokenizer": "*", 605 | "php": ">=5.3" 606 | }, 607 | "type": "library", 608 | "extra": { 609 | "branch-alias": { 610 | "dev-master": "1.4-dev" 611 | } 612 | }, 613 | "autoload": { 614 | "files": [ 615 | "lib/bootstrap.php" 616 | ] 617 | }, 618 | "notification-url": "https://packagist.org/downloads/", 619 | "license": [ 620 | "BSD-3-Clause" 621 | ], 622 | "authors": [ 623 | { 624 | "name": "Nikita Popov" 625 | } 626 | ], 627 | "description": "A PHP parser written in PHP", 628 | "keywords": [ 629 | "parser", 630 | "php" 631 | ], 632 | "time": "2015-09-19 14:15:08" 633 | }, 634 | { 635 | "name": "phing/phing", 636 | "version": "2.14.0", 637 | "source": { 638 | "type": "git", 639 | "url": "https://github.com/phingofficial/phing.git", 640 | "reference": "7dd73c83c377623def54b58121f46b4dcb35dd61" 641 | }, 642 | "dist": { 643 | "type": "zip", 644 | "url": "https://api.github.com/repos/phingofficial/phing/zipball/7dd73c83c377623def54b58121f46b4dcb35dd61", 645 | "reference": "7dd73c83c377623def54b58121f46b4dcb35dd61", 646 | "shasum": "" 647 | }, 648 | "require": { 649 | "php": ">=5.2.0" 650 | }, 651 | "require-dev": { 652 | "ext-pdo_sqlite": "*", 653 | "lastcraft/simpletest": "@dev", 654 | "mikey179/vfsstream": "^1.6", 655 | "pdepend/pdepend": "2.x", 656 | "pear/archive_tar": "1.4.x", 657 | "pear/http_request2": "dev-trunk", 658 | "pear/net_growl": "dev-trunk", 659 | "pear/pear-core-minimal": "1.10.1", 660 | "pear/versioncontrol_git": "@dev", 661 | "pear/versioncontrol_svn": "~0.5", 662 | "phpdocumentor/phpdocumentor": "2.x", 663 | "phploc/phploc": "~2.0.6", 664 | "phpmd/phpmd": "~2.2", 665 | "phpunit/phpunit": ">=3.7", 666 | "sebastian/git": "~1.0", 667 | "sebastian/phpcpd": "2.x", 668 | "squizlabs/php_codesniffer": "~2.2", 669 | "symfony/yaml": "~2.7" 670 | }, 671 | "suggest": { 672 | "pdepend/pdepend": "PHP version of JDepend", 673 | "pear/archive_tar": "Tar file management class", 674 | "pear/versioncontrol_git": "A library that provides OO interface to handle Git repository", 675 | "pear/versioncontrol_svn": "A simple OO-style interface for Subversion, the free/open-source version control system", 676 | "phpdocumentor/phpdocumentor": "Documentation Generator for PHP", 677 | "phploc/phploc": "A tool for quickly measuring the size of a PHP project", 678 | "phpmd/phpmd": "PHP version of PMD tool", 679 | "phpunit/php-code-coverage": "Library that provides collection, processing, and rendering functionality for PHP code coverage information", 680 | "phpunit/phpunit": "The PHP Unit Testing Framework", 681 | "sebastian/phpcpd": "Copy/Paste Detector (CPD) for PHP code", 682 | "tedivm/jshrink": "Javascript Minifier built in PHP" 683 | }, 684 | "bin": [ 685 | "bin/phing" 686 | ], 687 | "type": "library", 688 | "extra": { 689 | "branch-alias": { 690 | "dev-master": "2.14.x-dev" 691 | } 692 | }, 693 | "autoload": { 694 | "classmap": [ 695 | "classes/phing/" 696 | ] 697 | }, 698 | "notification-url": "https://packagist.org/downloads/", 699 | "include-path": [ 700 | "classes" 701 | ], 702 | "license": [ 703 | "LGPL-3.0" 704 | ], 705 | "authors": [ 706 | { 707 | "name": "Michiel Rook", 708 | "email": "mrook@php.net" 709 | }, 710 | { 711 | "name": "Phing Community", 712 | "homepage": "https://www.phing.info/trac/wiki/Development/Contributors" 713 | } 714 | ], 715 | "description": "PHing Is Not GNU make; it's a PHP project build system or build tool based on Apache Ant.", 716 | "homepage": "https://www.phing.info/", 717 | "keywords": [ 718 | "build", 719 | "phing", 720 | "task", 721 | "tool" 722 | ], 723 | "time": "2016-03-10 21:39:23" 724 | }, 725 | { 726 | "name": "phpcollection/phpcollection", 727 | "version": "0.4.0", 728 | "source": { 729 | "type": "git", 730 | "url": "https://github.com/schmittjoh/php-collection.git", 731 | "reference": "b8bf55a0a929ca43b01232b36719f176f86c7e83" 732 | }, 733 | "dist": { 734 | "type": "zip", 735 | "url": "https://api.github.com/repos/schmittjoh/php-collection/zipball/b8bf55a0a929ca43b01232b36719f176f86c7e83", 736 | "reference": "b8bf55a0a929ca43b01232b36719f176f86c7e83", 737 | "shasum": "" 738 | }, 739 | "require": { 740 | "phpoption/phpoption": "1.*" 741 | }, 742 | "type": "library", 743 | "extra": { 744 | "branch-alias": { 745 | "dev-master": "0.3-dev" 746 | } 747 | }, 748 | "autoload": { 749 | "psr-0": { 750 | "PhpCollection": "src/" 751 | } 752 | }, 753 | "notification-url": "https://packagist.org/downloads/", 754 | "license": [ 755 | "Apache2" 756 | ], 757 | "authors": [ 758 | { 759 | "name": "Johannes Schmitt", 760 | "email": "schmittjoh@gmail.com", 761 | "homepage": "https://github.com/schmittjoh", 762 | "role": "Developer of wrapped JMSSerializerBundle" 763 | } 764 | ], 765 | "description": "General-Purpose Collection Library for PHP", 766 | "keywords": [ 767 | "collection", 768 | "list", 769 | "map", 770 | "sequence", 771 | "set" 772 | ], 773 | "time": "2014-03-11 13:46:42" 774 | }, 775 | { 776 | "name": "phpdocumentor/reflection-docblock", 777 | "version": "2.0.4", 778 | "source": { 779 | "type": "git", 780 | "url": "https://github.com/phpDocumentor/ReflectionDocBlock.git", 781 | "reference": "d68dbdc53dc358a816f00b300704702b2eaff7b8" 782 | }, 783 | "dist": { 784 | "type": "zip", 785 | "url": "https://api.github.com/repos/phpDocumentor/ReflectionDocBlock/zipball/d68dbdc53dc358a816f00b300704702b2eaff7b8", 786 | "reference": "d68dbdc53dc358a816f00b300704702b2eaff7b8", 787 | "shasum": "" 788 | }, 789 | "require": { 790 | "php": ">=5.3.3" 791 | }, 792 | "require-dev": { 793 | "phpunit/phpunit": "~4.0" 794 | }, 795 | "suggest": { 796 | "dflydev/markdown": "~1.0", 797 | "erusev/parsedown": "~1.0" 798 | }, 799 | "type": "library", 800 | "extra": { 801 | "branch-alias": { 802 | "dev-master": "2.0.x-dev" 803 | } 804 | }, 805 | "autoload": { 806 | "psr-0": { 807 | "phpDocumentor": [ 808 | "src/" 809 | ] 810 | } 811 | }, 812 | "notification-url": "https://packagist.org/downloads/", 813 | "license": [ 814 | "MIT" 815 | ], 816 | "authors": [ 817 | { 818 | "name": "Mike van Riel", 819 | "email": "mike.vanriel@naenius.com" 820 | } 821 | ], 822 | "time": "2015-02-03 12:10:50" 823 | }, 824 | { 825 | "name": "phpoption/phpoption", 826 | "version": "1.5.0", 827 | "source": { 828 | "type": "git", 829 | "url": "https://github.com/schmittjoh/php-option.git", 830 | "reference": "94e644f7d2051a5f0fcf77d81605f152eecff0ed" 831 | }, 832 | "dist": { 833 | "type": "zip", 834 | "url": "https://api.github.com/repos/schmittjoh/php-option/zipball/94e644f7d2051a5f0fcf77d81605f152eecff0ed", 835 | "reference": "94e644f7d2051a5f0fcf77d81605f152eecff0ed", 836 | "shasum": "" 837 | }, 838 | "require": { 839 | "php": ">=5.3.0" 840 | }, 841 | "require-dev": { 842 | "phpunit/phpunit": "4.7.*" 843 | }, 844 | "type": "library", 845 | "extra": { 846 | "branch-alias": { 847 | "dev-master": "1.3-dev" 848 | } 849 | }, 850 | "autoload": { 851 | "psr-0": { 852 | "PhpOption\\": "src/" 853 | } 854 | }, 855 | "notification-url": "https://packagist.org/downloads/", 856 | "license": [ 857 | "Apache2" 858 | ], 859 | "authors": [ 860 | { 861 | "name": "Johannes M. Schmitt", 862 | "email": "schmittjoh@gmail.com" 863 | } 864 | ], 865 | "description": "Option Type for PHP", 866 | "keywords": [ 867 | "language", 868 | "option", 869 | "php", 870 | "type" 871 | ], 872 | "time": "2015-07-25 16:39:46" 873 | }, 874 | { 875 | "name": "phpspec/prophecy", 876 | "version": "v1.6.0", 877 | "source": { 878 | "type": "git", 879 | "url": "https://github.com/phpspec/prophecy.git", 880 | "reference": "3c91bdf81797d725b14cb62906f9a4ce44235972" 881 | }, 882 | "dist": { 883 | "type": "zip", 884 | "url": "https://api.github.com/repos/phpspec/prophecy/zipball/3c91bdf81797d725b14cb62906f9a4ce44235972", 885 | "reference": "3c91bdf81797d725b14cb62906f9a4ce44235972", 886 | "shasum": "" 887 | }, 888 | "require": { 889 | "doctrine/instantiator": "^1.0.2", 890 | "php": "^5.3|^7.0", 891 | "phpdocumentor/reflection-docblock": "~2.0", 892 | "sebastian/comparator": "~1.1", 893 | "sebastian/recursion-context": "~1.0" 894 | }, 895 | "require-dev": { 896 | "phpspec/phpspec": "~2.0" 897 | }, 898 | "type": "library", 899 | "extra": { 900 | "branch-alias": { 901 | "dev-master": "1.5.x-dev" 902 | } 903 | }, 904 | "autoload": { 905 | "psr-0": { 906 | "Prophecy\\": "src/" 907 | } 908 | }, 909 | "notification-url": "https://packagist.org/downloads/", 910 | "license": [ 911 | "MIT" 912 | ], 913 | "authors": [ 914 | { 915 | "name": "Konstantin Kudryashov", 916 | "email": "ever.zet@gmail.com", 917 | "homepage": "http://everzet.com" 918 | }, 919 | { 920 | "name": "Marcello Duarte", 921 | "email": "marcello.duarte@gmail.com" 922 | } 923 | ], 924 | "description": "Highly opinionated mocking framework for PHP 5.3+", 925 | "homepage": "https://github.com/phpspec/prophecy", 926 | "keywords": [ 927 | "Double", 928 | "Dummy", 929 | "fake", 930 | "mock", 931 | "spy", 932 | "stub" 933 | ], 934 | "time": "2016-02-15 07:46:21" 935 | }, 936 | { 937 | "name": "phpunit/php-code-coverage", 938 | "version": "3.3.1", 939 | "source": { 940 | "type": "git", 941 | "url": "https://github.com/sebastianbergmann/php-code-coverage.git", 942 | "reference": "2431befdd451fac43fbcde94d1a92fb3b8b68f86" 943 | }, 944 | "dist": { 945 | "type": "zip", 946 | "url": "https://api.github.com/repos/sebastianbergmann/php-code-coverage/zipball/2431befdd451fac43fbcde94d1a92fb3b8b68f86", 947 | "reference": "2431befdd451fac43fbcde94d1a92fb3b8b68f86", 948 | "shasum": "" 949 | }, 950 | "require": { 951 | "php": "^5.6 || ^7.0", 952 | "phpunit/php-file-iterator": "~1.3", 953 | "phpunit/php-text-template": "~1.2", 954 | "phpunit/php-token-stream": "^1.4.2", 955 | "sebastian/code-unit-reverse-lookup": "~1.0", 956 | "sebastian/environment": "^1.3.2", 957 | "sebastian/version": "~1.0|~2.0" 958 | }, 959 | "require-dev": { 960 | "ext-xdebug": ">=2.1.4", 961 | "phpunit/phpunit": "~5" 962 | }, 963 | "suggest": { 964 | "ext-dom": "*", 965 | "ext-xdebug": ">=2.4.0", 966 | "ext-xmlwriter": "*" 967 | }, 968 | "type": "library", 969 | "extra": { 970 | "branch-alias": { 971 | "dev-master": "3.3.x-dev" 972 | } 973 | }, 974 | "autoload": { 975 | "classmap": [ 976 | "src/" 977 | ] 978 | }, 979 | "notification-url": "https://packagist.org/downloads/", 980 | "license": [ 981 | "BSD-3-Clause" 982 | ], 983 | "authors": [ 984 | { 985 | "name": "Sebastian Bergmann", 986 | "email": "sb@sebastian-bergmann.de", 987 | "role": "lead" 988 | } 989 | ], 990 | "description": "Library that provides collection, processing, and rendering functionality for PHP code coverage information.", 991 | "homepage": "https://github.com/sebastianbergmann/php-code-coverage", 992 | "keywords": [ 993 | "coverage", 994 | "testing", 995 | "xunit" 996 | ], 997 | "time": "2016-04-08 08:14:53" 998 | }, 999 | { 1000 | "name": "phpunit/php-file-iterator", 1001 | "version": "1.4.1", 1002 | "source": { 1003 | "type": "git", 1004 | "url": "https://github.com/sebastianbergmann/php-file-iterator.git", 1005 | "reference": "6150bf2c35d3fc379e50c7602b75caceaa39dbf0" 1006 | }, 1007 | "dist": { 1008 | "type": "zip", 1009 | "url": "https://api.github.com/repos/sebastianbergmann/php-file-iterator/zipball/6150bf2c35d3fc379e50c7602b75caceaa39dbf0", 1010 | "reference": "6150bf2c35d3fc379e50c7602b75caceaa39dbf0", 1011 | "shasum": "" 1012 | }, 1013 | "require": { 1014 | "php": ">=5.3.3" 1015 | }, 1016 | "type": "library", 1017 | "extra": { 1018 | "branch-alias": { 1019 | "dev-master": "1.4.x-dev" 1020 | } 1021 | }, 1022 | "autoload": { 1023 | "classmap": [ 1024 | "src/" 1025 | ] 1026 | }, 1027 | "notification-url": "https://packagist.org/downloads/", 1028 | "license": [ 1029 | "BSD-3-Clause" 1030 | ], 1031 | "authors": [ 1032 | { 1033 | "name": "Sebastian Bergmann", 1034 | "email": "sb@sebastian-bergmann.de", 1035 | "role": "lead" 1036 | } 1037 | ], 1038 | "description": "FilterIterator implementation that filters files based on a list of suffixes.", 1039 | "homepage": "https://github.com/sebastianbergmann/php-file-iterator/", 1040 | "keywords": [ 1041 | "filesystem", 1042 | "iterator" 1043 | ], 1044 | "time": "2015-06-21 13:08:43" 1045 | }, 1046 | { 1047 | "name": "phpunit/php-text-template", 1048 | "version": "1.2.1", 1049 | "source": { 1050 | "type": "git", 1051 | "url": "https://github.com/sebastianbergmann/php-text-template.git", 1052 | "reference": "31f8b717e51d9a2afca6c9f046f5d69fc27c8686" 1053 | }, 1054 | "dist": { 1055 | "type": "zip", 1056 | "url": "https://api.github.com/repos/sebastianbergmann/php-text-template/zipball/31f8b717e51d9a2afca6c9f046f5d69fc27c8686", 1057 | "reference": "31f8b717e51d9a2afca6c9f046f5d69fc27c8686", 1058 | "shasum": "" 1059 | }, 1060 | "require": { 1061 | "php": ">=5.3.3" 1062 | }, 1063 | "type": "library", 1064 | "autoload": { 1065 | "classmap": [ 1066 | "src/" 1067 | ] 1068 | }, 1069 | "notification-url": "https://packagist.org/downloads/", 1070 | "license": [ 1071 | "BSD-3-Clause" 1072 | ], 1073 | "authors": [ 1074 | { 1075 | "name": "Sebastian Bergmann", 1076 | "email": "sebastian@phpunit.de", 1077 | "role": "lead" 1078 | } 1079 | ], 1080 | "description": "Simple template engine.", 1081 | "homepage": "https://github.com/sebastianbergmann/php-text-template/", 1082 | "keywords": [ 1083 | "template" 1084 | ], 1085 | "time": "2015-06-21 13:50:34" 1086 | }, 1087 | { 1088 | "name": "phpunit/php-timer", 1089 | "version": "1.0.7", 1090 | "source": { 1091 | "type": "git", 1092 | "url": "https://github.com/sebastianbergmann/php-timer.git", 1093 | "reference": "3e82f4e9fc92665fafd9157568e4dcb01d014e5b" 1094 | }, 1095 | "dist": { 1096 | "type": "zip", 1097 | "url": "https://api.github.com/repos/sebastianbergmann/php-timer/zipball/3e82f4e9fc92665fafd9157568e4dcb01d014e5b", 1098 | "reference": "3e82f4e9fc92665fafd9157568e4dcb01d014e5b", 1099 | "shasum": "" 1100 | }, 1101 | "require": { 1102 | "php": ">=5.3.3" 1103 | }, 1104 | "type": "library", 1105 | "autoload": { 1106 | "classmap": [ 1107 | "src/" 1108 | ] 1109 | }, 1110 | "notification-url": "https://packagist.org/downloads/", 1111 | "license": [ 1112 | "BSD-3-Clause" 1113 | ], 1114 | "authors": [ 1115 | { 1116 | "name": "Sebastian Bergmann", 1117 | "email": "sb@sebastian-bergmann.de", 1118 | "role": "lead" 1119 | } 1120 | ], 1121 | "description": "Utility class for timing", 1122 | "homepage": "https://github.com/sebastianbergmann/php-timer/", 1123 | "keywords": [ 1124 | "timer" 1125 | ], 1126 | "time": "2015-06-21 08:01:12" 1127 | }, 1128 | { 1129 | "name": "phpunit/php-token-stream", 1130 | "version": "1.4.8", 1131 | "source": { 1132 | "type": "git", 1133 | "url": "https://github.com/sebastianbergmann/php-token-stream.git", 1134 | "reference": "3144ae21711fb6cac0b1ab4cbe63b75ce3d4e8da" 1135 | }, 1136 | "dist": { 1137 | "type": "zip", 1138 | "url": "https://api.github.com/repos/sebastianbergmann/php-token-stream/zipball/3144ae21711fb6cac0b1ab4cbe63b75ce3d4e8da", 1139 | "reference": "3144ae21711fb6cac0b1ab4cbe63b75ce3d4e8da", 1140 | "shasum": "" 1141 | }, 1142 | "require": { 1143 | "ext-tokenizer": "*", 1144 | "php": ">=5.3.3" 1145 | }, 1146 | "require-dev": { 1147 | "phpunit/phpunit": "~4.2" 1148 | }, 1149 | "type": "library", 1150 | "extra": { 1151 | "branch-alias": { 1152 | "dev-master": "1.4-dev" 1153 | } 1154 | }, 1155 | "autoload": { 1156 | "classmap": [ 1157 | "src/" 1158 | ] 1159 | }, 1160 | "notification-url": "https://packagist.org/downloads/", 1161 | "license": [ 1162 | "BSD-3-Clause" 1163 | ], 1164 | "authors": [ 1165 | { 1166 | "name": "Sebastian Bergmann", 1167 | "email": "sebastian@phpunit.de" 1168 | } 1169 | ], 1170 | "description": "Wrapper around PHP's tokenizer extension.", 1171 | "homepage": "https://github.com/sebastianbergmann/php-token-stream/", 1172 | "keywords": [ 1173 | "tokenizer" 1174 | ], 1175 | "time": "2015-09-15 10:49:45" 1176 | }, 1177 | { 1178 | "name": "phpunit/phpunit", 1179 | "version": "5.3.2", 1180 | "source": { 1181 | "type": "git", 1182 | "url": "https://github.com/sebastianbergmann/phpunit.git", 1183 | "reference": "2c6da3536035617bae3fe3db37283c9e0eb63ab3" 1184 | }, 1185 | "dist": { 1186 | "type": "zip", 1187 | "url": "https://api.github.com/repos/sebastianbergmann/phpunit/zipball/2c6da3536035617bae3fe3db37283c9e0eb63ab3", 1188 | "reference": "2c6da3536035617bae3fe3db37283c9e0eb63ab3", 1189 | "shasum": "" 1190 | }, 1191 | "require": { 1192 | "ext-dom": "*", 1193 | "ext-json": "*", 1194 | "ext-pcre": "*", 1195 | "ext-reflection": "*", 1196 | "ext-spl": "*", 1197 | "myclabs/deep-copy": "~1.3", 1198 | "php": "^5.6 || ^7.0", 1199 | "phpspec/prophecy": "^1.3.1", 1200 | "phpunit/php-code-coverage": "^3.3.0", 1201 | "phpunit/php-file-iterator": "~1.4", 1202 | "phpunit/php-text-template": "~1.2", 1203 | "phpunit/php-timer": "^1.0.6", 1204 | "phpunit/phpunit-mock-objects": "^3.1", 1205 | "sebastian/comparator": "~1.1", 1206 | "sebastian/diff": "~1.2", 1207 | "sebastian/environment": "~1.3", 1208 | "sebastian/exporter": "~1.2", 1209 | "sebastian/global-state": "~1.0", 1210 | "sebastian/object-enumerator": "~1.0", 1211 | "sebastian/resource-operations": "~1.0", 1212 | "sebastian/version": "~1.0|~2.0", 1213 | "symfony/yaml": "~2.1|~3.0" 1214 | }, 1215 | "suggest": { 1216 | "phpunit/php-invoker": "~1.1" 1217 | }, 1218 | "bin": [ 1219 | "phpunit" 1220 | ], 1221 | "type": "library", 1222 | "extra": { 1223 | "branch-alias": { 1224 | "dev-master": "5.3.x-dev" 1225 | } 1226 | }, 1227 | "autoload": { 1228 | "classmap": [ 1229 | "src/" 1230 | ] 1231 | }, 1232 | "notification-url": "https://packagist.org/downloads/", 1233 | "license": [ 1234 | "BSD-3-Clause" 1235 | ], 1236 | "authors": [ 1237 | { 1238 | "name": "Sebastian Bergmann", 1239 | "email": "sebastian@phpunit.de", 1240 | "role": "lead" 1241 | } 1242 | ], 1243 | "description": "The PHP Unit Testing framework.", 1244 | "homepage": "https://phpunit.de/", 1245 | "keywords": [ 1246 | "phpunit", 1247 | "testing", 1248 | "xunit" 1249 | ], 1250 | "time": "2016-04-12 16:20:08" 1251 | }, 1252 | { 1253 | "name": "phpunit/phpunit-mock-objects", 1254 | "version": "3.1.3", 1255 | "source": { 1256 | "type": "git", 1257 | "url": "https://github.com/sebastianbergmann/phpunit-mock-objects.git", 1258 | "reference": "151c96874bff6fe61a25039df60e776613a61489" 1259 | }, 1260 | "dist": { 1261 | "type": "zip", 1262 | "url": "https://api.github.com/repos/sebastianbergmann/phpunit-mock-objects/zipball/151c96874bff6fe61a25039df60e776613a61489", 1263 | "reference": "151c96874bff6fe61a25039df60e776613a61489", 1264 | "shasum": "" 1265 | }, 1266 | "require": { 1267 | "doctrine/instantiator": "^1.0.2", 1268 | "php": ">=5.6", 1269 | "phpunit/php-text-template": "~1.2", 1270 | "sebastian/exporter": "~1.2" 1271 | }, 1272 | "require-dev": { 1273 | "phpunit/phpunit": "~5" 1274 | }, 1275 | "suggest": { 1276 | "ext-soap": "*" 1277 | }, 1278 | "type": "library", 1279 | "extra": { 1280 | "branch-alias": { 1281 | "dev-master": "3.1.x-dev" 1282 | } 1283 | }, 1284 | "autoload": { 1285 | "classmap": [ 1286 | "src/" 1287 | ] 1288 | }, 1289 | "notification-url": "https://packagist.org/downloads/", 1290 | "license": [ 1291 | "BSD-3-Clause" 1292 | ], 1293 | "authors": [ 1294 | { 1295 | "name": "Sebastian Bergmann", 1296 | "email": "sb@sebastian-bergmann.de", 1297 | "role": "lead" 1298 | } 1299 | ], 1300 | "description": "Mock Object library for PHPUnit", 1301 | "homepage": "https://github.com/sebastianbergmann/phpunit-mock-objects/", 1302 | "keywords": [ 1303 | "mock", 1304 | "xunit" 1305 | ], 1306 | "time": "2016-04-20 14:39:26" 1307 | }, 1308 | { 1309 | "name": "pimple/pimple", 1310 | "version": "v3.0.2", 1311 | "source": { 1312 | "type": "git", 1313 | "url": "https://github.com/silexphp/Pimple.git", 1314 | "reference": "a30f7d6e57565a2e1a316e1baf2a483f788b258a" 1315 | }, 1316 | "dist": { 1317 | "type": "zip", 1318 | "url": "https://api.github.com/repos/silexphp/Pimple/zipball/a30f7d6e57565a2e1a316e1baf2a483f788b258a", 1319 | "reference": "a30f7d6e57565a2e1a316e1baf2a483f788b258a", 1320 | "shasum": "" 1321 | }, 1322 | "require": { 1323 | "php": ">=5.3.0" 1324 | }, 1325 | "type": "library", 1326 | "extra": { 1327 | "branch-alias": { 1328 | "dev-master": "3.0.x-dev" 1329 | } 1330 | }, 1331 | "autoload": { 1332 | "psr-0": { 1333 | "Pimple": "src/" 1334 | } 1335 | }, 1336 | "notification-url": "https://packagist.org/downloads/", 1337 | "license": [ 1338 | "MIT" 1339 | ], 1340 | "authors": [ 1341 | { 1342 | "name": "Fabien Potencier", 1343 | "email": "fabien@symfony.com" 1344 | } 1345 | ], 1346 | "description": "Pimple, a simple Dependency Injection Container", 1347 | "homepage": "http://pimple.sensiolabs.org", 1348 | "keywords": [ 1349 | "container", 1350 | "dependency injection" 1351 | ], 1352 | "time": "2015-09-11 15:10:35" 1353 | }, 1354 | { 1355 | "name": "sami/sami", 1356 | "version": "v3.2.1", 1357 | "source": { 1358 | "type": "git", 1359 | "url": "https://github.com/FriendsOfPHP/Sami.git", 1360 | "reference": "3a46b98e2fa4d4819018e3767ba6346bfed92957" 1361 | }, 1362 | "dist": { 1363 | "type": "zip", 1364 | "url": "https://api.github.com/repos/FriendsOfPHP/Sami/zipball/3a46b98e2fa4d4819018e3767ba6346bfed92957", 1365 | "reference": "3a46b98e2fa4d4819018e3767ba6346bfed92957", 1366 | "shasum": "" 1367 | }, 1368 | "require": { 1369 | "blackfire/php-sdk": "^1.5.6", 1370 | "michelf/php-markdown": "~1.3", 1371 | "nikic/php-parser": "~1.0", 1372 | "php": ">=5.3.9", 1373 | "phpdocumentor/reflection-docblock": "~2.0", 1374 | "pimple/pimple": "~3.0", 1375 | "symfony/console": "~2.1", 1376 | "symfony/filesystem": "~2.1", 1377 | "symfony/finder": "~2.1", 1378 | "symfony/process": "~2.1", 1379 | "symfony/yaml": "~2.1", 1380 | "twig/twig": "~1.20|~2.0" 1381 | }, 1382 | "bin": [ 1383 | "sami.php" 1384 | ], 1385 | "type": "application", 1386 | "extra": { 1387 | "branch-alias": { 1388 | "dev-master": "3.1-dev" 1389 | } 1390 | }, 1391 | "autoload": { 1392 | "psr-4": { 1393 | "Sami\\": "Sami/" 1394 | } 1395 | }, 1396 | "notification-url": "https://packagist.org/downloads/", 1397 | "license": [ 1398 | "MIT" 1399 | ], 1400 | "authors": [ 1401 | { 1402 | "name": "Fabien Potencier", 1403 | "email": "fabien@symfony.com" 1404 | } 1405 | ], 1406 | "description": "Sami, an API documentation generator", 1407 | "homepage": "http://sami.sensiolabs.org", 1408 | "keywords": [ 1409 | "phpdoc" 1410 | ], 1411 | "time": "2016-01-22 07:52:40" 1412 | }, 1413 | { 1414 | "name": "scrutinizer/ocular", 1415 | "version": "1.3.0", 1416 | "source": { 1417 | "type": "git", 1418 | "url": "https://github.com/scrutinizer-ci/ocular.git", 1419 | "reference": "72dcffcd4fbafeff41bf51da349df33170f487e5" 1420 | }, 1421 | "dist": { 1422 | "type": "zip", 1423 | "url": "https://api.github.com/repos/scrutinizer-ci/ocular/zipball/72dcffcd4fbafeff41bf51da349df33170f487e5", 1424 | "reference": "72dcffcd4fbafeff41bf51da349df33170f487e5", 1425 | "shasum": "" 1426 | }, 1427 | "require": { 1428 | "guzzle/guzzle": "~3.0", 1429 | "jms/serializer": "^1.0.0", 1430 | "phpoption/phpoption": "~1.0", 1431 | "symfony/console": "~2.0|~3.0", 1432 | "symfony/process": "~2.3|~3.0" 1433 | }, 1434 | "require-dev": { 1435 | "phpunit/phpunit": "^4.8.0", 1436 | "symfony/filesystem": "~2.0|~3.0" 1437 | }, 1438 | "bin": [ 1439 | "bin/ocular" 1440 | ], 1441 | "type": "library", 1442 | "autoload": { 1443 | "psr-4": { 1444 | "Scrutinizer\\Ocular\\": "src/Scrutinizer/Ocular" 1445 | } 1446 | }, 1447 | "notification-url": "https://packagist.org/downloads/", 1448 | "time": "2015-12-16 14:33:15" 1449 | }, 1450 | { 1451 | "name": "sebastian/code-unit-reverse-lookup", 1452 | "version": "1.0.0", 1453 | "source": { 1454 | "type": "git", 1455 | "url": "https://github.com/sebastianbergmann/code-unit-reverse-lookup.git", 1456 | "reference": "c36f5e7cfce482fde5bf8d10d41a53591e0198fe" 1457 | }, 1458 | "dist": { 1459 | "type": "zip", 1460 | "url": "https://api.github.com/repos/sebastianbergmann/code-unit-reverse-lookup/zipball/c36f5e7cfce482fde5bf8d10d41a53591e0198fe", 1461 | "reference": "c36f5e7cfce482fde5bf8d10d41a53591e0198fe", 1462 | "shasum": "" 1463 | }, 1464 | "require": { 1465 | "php": ">=5.6" 1466 | }, 1467 | "require-dev": { 1468 | "phpunit/phpunit": "~5" 1469 | }, 1470 | "type": "library", 1471 | "extra": { 1472 | "branch-alias": { 1473 | "dev-master": "1.0.x-dev" 1474 | } 1475 | }, 1476 | "autoload": { 1477 | "classmap": [ 1478 | "src/" 1479 | ] 1480 | }, 1481 | "notification-url": "https://packagist.org/downloads/", 1482 | "license": [ 1483 | "BSD-3-Clause" 1484 | ], 1485 | "authors": [ 1486 | { 1487 | "name": "Sebastian Bergmann", 1488 | "email": "sebastian@phpunit.de" 1489 | } 1490 | ], 1491 | "description": "Looks up which function or method a line of code belongs to", 1492 | "homepage": "https://github.com/sebastianbergmann/code-unit-reverse-lookup/", 1493 | "time": "2016-02-13 06:45:14" 1494 | }, 1495 | { 1496 | "name": "sebastian/comparator", 1497 | "version": "1.2.0", 1498 | "source": { 1499 | "type": "git", 1500 | "url": "https://github.com/sebastianbergmann/comparator.git", 1501 | "reference": "937efb279bd37a375bcadf584dec0726f84dbf22" 1502 | }, 1503 | "dist": { 1504 | "type": "zip", 1505 | "url": "https://api.github.com/repos/sebastianbergmann/comparator/zipball/937efb279bd37a375bcadf584dec0726f84dbf22", 1506 | "reference": "937efb279bd37a375bcadf584dec0726f84dbf22", 1507 | "shasum": "" 1508 | }, 1509 | "require": { 1510 | "php": ">=5.3.3", 1511 | "sebastian/diff": "~1.2", 1512 | "sebastian/exporter": "~1.2" 1513 | }, 1514 | "require-dev": { 1515 | "phpunit/phpunit": "~4.4" 1516 | }, 1517 | "type": "library", 1518 | "extra": { 1519 | "branch-alias": { 1520 | "dev-master": "1.2.x-dev" 1521 | } 1522 | }, 1523 | "autoload": { 1524 | "classmap": [ 1525 | "src/" 1526 | ] 1527 | }, 1528 | "notification-url": "https://packagist.org/downloads/", 1529 | "license": [ 1530 | "BSD-3-Clause" 1531 | ], 1532 | "authors": [ 1533 | { 1534 | "name": "Jeff Welch", 1535 | "email": "whatthejeff@gmail.com" 1536 | }, 1537 | { 1538 | "name": "Volker Dusch", 1539 | "email": "github@wallbash.com" 1540 | }, 1541 | { 1542 | "name": "Bernhard Schussek", 1543 | "email": "bschussek@2bepublished.at" 1544 | }, 1545 | { 1546 | "name": "Sebastian Bergmann", 1547 | "email": "sebastian@phpunit.de" 1548 | } 1549 | ], 1550 | "description": "Provides the functionality to compare PHP values for equality", 1551 | "homepage": "http://www.github.com/sebastianbergmann/comparator", 1552 | "keywords": [ 1553 | "comparator", 1554 | "compare", 1555 | "equality" 1556 | ], 1557 | "time": "2015-07-26 15:48:44" 1558 | }, 1559 | { 1560 | "name": "sebastian/diff", 1561 | "version": "1.4.1", 1562 | "source": { 1563 | "type": "git", 1564 | "url": "https://github.com/sebastianbergmann/diff.git", 1565 | "reference": "13edfd8706462032c2f52b4b862974dd46b71c9e" 1566 | }, 1567 | "dist": { 1568 | "type": "zip", 1569 | "url": "https://api.github.com/repos/sebastianbergmann/diff/zipball/13edfd8706462032c2f52b4b862974dd46b71c9e", 1570 | "reference": "13edfd8706462032c2f52b4b862974dd46b71c9e", 1571 | "shasum": "" 1572 | }, 1573 | "require": { 1574 | "php": ">=5.3.3" 1575 | }, 1576 | "require-dev": { 1577 | "phpunit/phpunit": "~4.8" 1578 | }, 1579 | "type": "library", 1580 | "extra": { 1581 | "branch-alias": { 1582 | "dev-master": "1.4-dev" 1583 | } 1584 | }, 1585 | "autoload": { 1586 | "classmap": [ 1587 | "src/" 1588 | ] 1589 | }, 1590 | "notification-url": "https://packagist.org/downloads/", 1591 | "license": [ 1592 | "BSD-3-Clause" 1593 | ], 1594 | "authors": [ 1595 | { 1596 | "name": "Kore Nordmann", 1597 | "email": "mail@kore-nordmann.de" 1598 | }, 1599 | { 1600 | "name": "Sebastian Bergmann", 1601 | "email": "sebastian@phpunit.de" 1602 | } 1603 | ], 1604 | "description": "Diff implementation", 1605 | "homepage": "https://github.com/sebastianbergmann/diff", 1606 | "keywords": [ 1607 | "diff" 1608 | ], 1609 | "time": "2015-12-08 07:14:41" 1610 | }, 1611 | { 1612 | "name": "sebastian/environment", 1613 | "version": "1.3.6", 1614 | "source": { 1615 | "type": "git", 1616 | "url": "https://github.com/sebastianbergmann/environment.git", 1617 | "reference": "2292b116f43c272ff4328083096114f84ea46a56" 1618 | }, 1619 | "dist": { 1620 | "type": "zip", 1621 | "url": "https://api.github.com/repos/sebastianbergmann/environment/zipball/2292b116f43c272ff4328083096114f84ea46a56", 1622 | "reference": "2292b116f43c272ff4328083096114f84ea46a56", 1623 | "shasum": "" 1624 | }, 1625 | "require": { 1626 | "php": ">=5.3.3" 1627 | }, 1628 | "require-dev": { 1629 | "phpunit/phpunit": "~4.4" 1630 | }, 1631 | "type": "library", 1632 | "extra": { 1633 | "branch-alias": { 1634 | "dev-master": "1.3.x-dev" 1635 | } 1636 | }, 1637 | "autoload": { 1638 | "classmap": [ 1639 | "src/" 1640 | ] 1641 | }, 1642 | "notification-url": "https://packagist.org/downloads/", 1643 | "license": [ 1644 | "BSD-3-Clause" 1645 | ], 1646 | "authors": [ 1647 | { 1648 | "name": "Sebastian Bergmann", 1649 | "email": "sebastian@phpunit.de" 1650 | } 1651 | ], 1652 | "description": "Provides functionality to handle HHVM/PHP environments", 1653 | "homepage": "http://www.github.com/sebastianbergmann/environment", 1654 | "keywords": [ 1655 | "Xdebug", 1656 | "environment", 1657 | "hhvm" 1658 | ], 1659 | "time": "2016-05-04 07:59:13" 1660 | }, 1661 | { 1662 | "name": "sebastian/exporter", 1663 | "version": "1.2.1", 1664 | "source": { 1665 | "type": "git", 1666 | "url": "https://github.com/sebastianbergmann/exporter.git", 1667 | "reference": "7ae5513327cb536431847bcc0c10edba2701064e" 1668 | }, 1669 | "dist": { 1670 | "type": "zip", 1671 | "url": "https://api.github.com/repos/sebastianbergmann/exporter/zipball/7ae5513327cb536431847bcc0c10edba2701064e", 1672 | "reference": "7ae5513327cb536431847bcc0c10edba2701064e", 1673 | "shasum": "" 1674 | }, 1675 | "require": { 1676 | "php": ">=5.3.3", 1677 | "sebastian/recursion-context": "~1.0" 1678 | }, 1679 | "require-dev": { 1680 | "phpunit/phpunit": "~4.4" 1681 | }, 1682 | "type": "library", 1683 | "extra": { 1684 | "branch-alias": { 1685 | "dev-master": "1.2.x-dev" 1686 | } 1687 | }, 1688 | "autoload": { 1689 | "classmap": [ 1690 | "src/" 1691 | ] 1692 | }, 1693 | "notification-url": "https://packagist.org/downloads/", 1694 | "license": [ 1695 | "BSD-3-Clause" 1696 | ], 1697 | "authors": [ 1698 | { 1699 | "name": "Jeff Welch", 1700 | "email": "whatthejeff@gmail.com" 1701 | }, 1702 | { 1703 | "name": "Volker Dusch", 1704 | "email": "github@wallbash.com" 1705 | }, 1706 | { 1707 | "name": "Bernhard Schussek", 1708 | "email": "bschussek@2bepublished.at" 1709 | }, 1710 | { 1711 | "name": "Sebastian Bergmann", 1712 | "email": "sebastian@phpunit.de" 1713 | }, 1714 | { 1715 | "name": "Adam Harvey", 1716 | "email": "aharvey@php.net" 1717 | } 1718 | ], 1719 | "description": "Provides the functionality to export PHP variables for visualization", 1720 | "homepage": "http://www.github.com/sebastianbergmann/exporter", 1721 | "keywords": [ 1722 | "export", 1723 | "exporter" 1724 | ], 1725 | "time": "2015-06-21 07:55:53" 1726 | }, 1727 | { 1728 | "name": "sebastian/global-state", 1729 | "version": "1.1.1", 1730 | "source": { 1731 | "type": "git", 1732 | "url": "https://github.com/sebastianbergmann/global-state.git", 1733 | "reference": "bc37d50fea7d017d3d340f230811c9f1d7280af4" 1734 | }, 1735 | "dist": { 1736 | "type": "zip", 1737 | "url": "https://api.github.com/repos/sebastianbergmann/global-state/zipball/bc37d50fea7d017d3d340f230811c9f1d7280af4", 1738 | "reference": "bc37d50fea7d017d3d340f230811c9f1d7280af4", 1739 | "shasum": "" 1740 | }, 1741 | "require": { 1742 | "php": ">=5.3.3" 1743 | }, 1744 | "require-dev": { 1745 | "phpunit/phpunit": "~4.2" 1746 | }, 1747 | "suggest": { 1748 | "ext-uopz": "*" 1749 | }, 1750 | "type": "library", 1751 | "extra": { 1752 | "branch-alias": { 1753 | "dev-master": "1.0-dev" 1754 | } 1755 | }, 1756 | "autoload": { 1757 | "classmap": [ 1758 | "src/" 1759 | ] 1760 | }, 1761 | "notification-url": "https://packagist.org/downloads/", 1762 | "license": [ 1763 | "BSD-3-Clause" 1764 | ], 1765 | "authors": [ 1766 | { 1767 | "name": "Sebastian Bergmann", 1768 | "email": "sebastian@phpunit.de" 1769 | } 1770 | ], 1771 | "description": "Snapshotting of global state", 1772 | "homepage": "http://www.github.com/sebastianbergmann/global-state", 1773 | "keywords": [ 1774 | "global state" 1775 | ], 1776 | "time": "2015-10-12 03:26:01" 1777 | }, 1778 | { 1779 | "name": "sebastian/object-enumerator", 1780 | "version": "1.0.0", 1781 | "source": { 1782 | "type": "git", 1783 | "url": "https://github.com/sebastianbergmann/object-enumerator.git", 1784 | "reference": "d4ca2fb70344987502567bc50081c03e6192fb26" 1785 | }, 1786 | "dist": { 1787 | "type": "zip", 1788 | "url": "https://api.github.com/repos/sebastianbergmann/object-enumerator/zipball/d4ca2fb70344987502567bc50081c03e6192fb26", 1789 | "reference": "d4ca2fb70344987502567bc50081c03e6192fb26", 1790 | "shasum": "" 1791 | }, 1792 | "require": { 1793 | "php": ">=5.6", 1794 | "sebastian/recursion-context": "~1.0" 1795 | }, 1796 | "require-dev": { 1797 | "phpunit/phpunit": "~5" 1798 | }, 1799 | "type": "library", 1800 | "extra": { 1801 | "branch-alias": { 1802 | "dev-master": "1.0.x-dev" 1803 | } 1804 | }, 1805 | "autoload": { 1806 | "classmap": [ 1807 | "src/" 1808 | ] 1809 | }, 1810 | "notification-url": "https://packagist.org/downloads/", 1811 | "license": [ 1812 | "BSD-3-Clause" 1813 | ], 1814 | "authors": [ 1815 | { 1816 | "name": "Sebastian Bergmann", 1817 | "email": "sebastian@phpunit.de" 1818 | } 1819 | ], 1820 | "description": "Traverses array structures and object graphs to enumerate all referenced objects", 1821 | "homepage": "https://github.com/sebastianbergmann/object-enumerator/", 1822 | "time": "2016-01-28 13:25:10" 1823 | }, 1824 | { 1825 | "name": "sebastian/recursion-context", 1826 | "version": "1.0.2", 1827 | "source": { 1828 | "type": "git", 1829 | "url": "https://github.com/sebastianbergmann/recursion-context.git", 1830 | "reference": "913401df809e99e4f47b27cdd781f4a258d58791" 1831 | }, 1832 | "dist": { 1833 | "type": "zip", 1834 | "url": "https://api.github.com/repos/sebastianbergmann/recursion-context/zipball/913401df809e99e4f47b27cdd781f4a258d58791", 1835 | "reference": "913401df809e99e4f47b27cdd781f4a258d58791", 1836 | "shasum": "" 1837 | }, 1838 | "require": { 1839 | "php": ">=5.3.3" 1840 | }, 1841 | "require-dev": { 1842 | "phpunit/phpunit": "~4.4" 1843 | }, 1844 | "type": "library", 1845 | "extra": { 1846 | "branch-alias": { 1847 | "dev-master": "1.0.x-dev" 1848 | } 1849 | }, 1850 | "autoload": { 1851 | "classmap": [ 1852 | "src/" 1853 | ] 1854 | }, 1855 | "notification-url": "https://packagist.org/downloads/", 1856 | "license": [ 1857 | "BSD-3-Clause" 1858 | ], 1859 | "authors": [ 1860 | { 1861 | "name": "Jeff Welch", 1862 | "email": "whatthejeff@gmail.com" 1863 | }, 1864 | { 1865 | "name": "Sebastian Bergmann", 1866 | "email": "sebastian@phpunit.de" 1867 | }, 1868 | { 1869 | "name": "Adam Harvey", 1870 | "email": "aharvey@php.net" 1871 | } 1872 | ], 1873 | "description": "Provides functionality to recursively process PHP variables", 1874 | "homepage": "http://www.github.com/sebastianbergmann/recursion-context", 1875 | "time": "2015-11-11 19:50:13" 1876 | }, 1877 | { 1878 | "name": "sebastian/resource-operations", 1879 | "version": "1.0.0", 1880 | "source": { 1881 | "type": "git", 1882 | "url": "https://github.com/sebastianbergmann/resource-operations.git", 1883 | "reference": "ce990bb21759f94aeafd30209e8cfcdfa8bc3f52" 1884 | }, 1885 | "dist": { 1886 | "type": "zip", 1887 | "url": "https://api.github.com/repos/sebastianbergmann/resource-operations/zipball/ce990bb21759f94aeafd30209e8cfcdfa8bc3f52", 1888 | "reference": "ce990bb21759f94aeafd30209e8cfcdfa8bc3f52", 1889 | "shasum": "" 1890 | }, 1891 | "require": { 1892 | "php": ">=5.6.0" 1893 | }, 1894 | "type": "library", 1895 | "extra": { 1896 | "branch-alias": { 1897 | "dev-master": "1.0.x-dev" 1898 | } 1899 | }, 1900 | "autoload": { 1901 | "classmap": [ 1902 | "src/" 1903 | ] 1904 | }, 1905 | "notification-url": "https://packagist.org/downloads/", 1906 | "license": [ 1907 | "BSD-3-Clause" 1908 | ], 1909 | "authors": [ 1910 | { 1911 | "name": "Sebastian Bergmann", 1912 | "email": "sebastian@phpunit.de" 1913 | } 1914 | ], 1915 | "description": "Provides a list of PHP built-in functions that operate on resources", 1916 | "homepage": "https://www.github.com/sebastianbergmann/resource-operations", 1917 | "time": "2015-07-28 20:34:47" 1918 | }, 1919 | { 1920 | "name": "sebastian/version", 1921 | "version": "2.0.0", 1922 | "source": { 1923 | "type": "git", 1924 | "url": "https://github.com/sebastianbergmann/version.git", 1925 | "reference": "c829badbd8fdf16a0bad8aa7fa7971c029f1b9c5" 1926 | }, 1927 | "dist": { 1928 | "type": "zip", 1929 | "url": "https://api.github.com/repos/sebastianbergmann/version/zipball/c829badbd8fdf16a0bad8aa7fa7971c029f1b9c5", 1930 | "reference": "c829badbd8fdf16a0bad8aa7fa7971c029f1b9c5", 1931 | "shasum": "" 1932 | }, 1933 | "require": { 1934 | "php": ">=5.6" 1935 | }, 1936 | "type": "library", 1937 | "extra": { 1938 | "branch-alias": { 1939 | "dev-master": "2.0.x-dev" 1940 | } 1941 | }, 1942 | "autoload": { 1943 | "classmap": [ 1944 | "src/" 1945 | ] 1946 | }, 1947 | "notification-url": "https://packagist.org/downloads/", 1948 | "license": [ 1949 | "BSD-3-Clause" 1950 | ], 1951 | "authors": [ 1952 | { 1953 | "name": "Sebastian Bergmann", 1954 | "email": "sebastian@phpunit.de", 1955 | "role": "lead" 1956 | } 1957 | ], 1958 | "description": "Library that helps with managing the version number of Git-hosted PHP projects", 1959 | "homepage": "https://github.com/sebastianbergmann/version", 1960 | "time": "2016-02-04 12:56:52" 1961 | }, 1962 | { 1963 | "name": "symfony/console", 1964 | "version": "v2.8.6", 1965 | "source": { 1966 | "type": "git", 1967 | "url": "https://github.com/symfony/console.git", 1968 | "reference": "48221d3de4dc22d2cd57c97e8b9361821da86609" 1969 | }, 1970 | "dist": { 1971 | "type": "zip", 1972 | "url": "https://api.github.com/repos/symfony/console/zipball/48221d3de4dc22d2cd57c97e8b9361821da86609", 1973 | "reference": "48221d3de4dc22d2cd57c97e8b9361821da86609", 1974 | "shasum": "" 1975 | }, 1976 | "require": { 1977 | "php": ">=5.3.9", 1978 | "symfony/polyfill-mbstring": "~1.0" 1979 | }, 1980 | "require-dev": { 1981 | "psr/log": "~1.0", 1982 | "symfony/event-dispatcher": "~2.1|~3.0.0", 1983 | "symfony/process": "~2.1|~3.0.0" 1984 | }, 1985 | "suggest": { 1986 | "psr/log": "For using the console logger", 1987 | "symfony/event-dispatcher": "", 1988 | "symfony/process": "" 1989 | }, 1990 | "type": "library", 1991 | "extra": { 1992 | "branch-alias": { 1993 | "dev-master": "2.8-dev" 1994 | } 1995 | }, 1996 | "autoload": { 1997 | "psr-4": { 1998 | "Symfony\\Component\\Console\\": "" 1999 | }, 2000 | "exclude-from-classmap": [ 2001 | "/Tests/" 2002 | ] 2003 | }, 2004 | "notification-url": "https://packagist.org/downloads/", 2005 | "license": [ 2006 | "MIT" 2007 | ], 2008 | "authors": [ 2009 | { 2010 | "name": "Fabien Potencier", 2011 | "email": "fabien@symfony.com" 2012 | }, 2013 | { 2014 | "name": "Symfony Community", 2015 | "homepage": "https://symfony.com/contributors" 2016 | } 2017 | ], 2018 | "description": "Symfony Console Component", 2019 | "homepage": "https://symfony.com", 2020 | "time": "2016-04-26 12:00:47" 2021 | }, 2022 | { 2023 | "name": "symfony/event-dispatcher", 2024 | "version": "v2.8.6", 2025 | "source": { 2026 | "type": "git", 2027 | "url": "https://github.com/symfony/event-dispatcher.git", 2028 | "reference": "a158f13992a3147d466af7a23b564ac719a4ddd8" 2029 | }, 2030 | "dist": { 2031 | "type": "zip", 2032 | "url": "https://api.github.com/repos/symfony/event-dispatcher/zipball/a158f13992a3147d466af7a23b564ac719a4ddd8", 2033 | "reference": "a158f13992a3147d466af7a23b564ac719a4ddd8", 2034 | "shasum": "" 2035 | }, 2036 | "require": { 2037 | "php": ">=5.3.9" 2038 | }, 2039 | "require-dev": { 2040 | "psr/log": "~1.0", 2041 | "symfony/config": "~2.0,>=2.0.5|~3.0.0", 2042 | "symfony/dependency-injection": "~2.6|~3.0.0", 2043 | "symfony/expression-language": "~2.6|~3.0.0", 2044 | "symfony/stopwatch": "~2.3|~3.0.0" 2045 | }, 2046 | "suggest": { 2047 | "symfony/dependency-injection": "", 2048 | "symfony/http-kernel": "" 2049 | }, 2050 | "type": "library", 2051 | "extra": { 2052 | "branch-alias": { 2053 | "dev-master": "2.8-dev" 2054 | } 2055 | }, 2056 | "autoload": { 2057 | "psr-4": { 2058 | "Symfony\\Component\\EventDispatcher\\": "" 2059 | }, 2060 | "exclude-from-classmap": [ 2061 | "/Tests/" 2062 | ] 2063 | }, 2064 | "notification-url": "https://packagist.org/downloads/", 2065 | "license": [ 2066 | "MIT" 2067 | ], 2068 | "authors": [ 2069 | { 2070 | "name": "Fabien Potencier", 2071 | "email": "fabien@symfony.com" 2072 | }, 2073 | { 2074 | "name": "Symfony Community", 2075 | "homepage": "https://symfony.com/contributors" 2076 | } 2077 | ], 2078 | "description": "Symfony EventDispatcher Component", 2079 | "homepage": "https://symfony.com", 2080 | "time": "2016-05-03 18:59:18" 2081 | }, 2082 | { 2083 | "name": "symfony/filesystem", 2084 | "version": "v2.8.6", 2085 | "source": { 2086 | "type": "git", 2087 | "url": "https://github.com/symfony/filesystem.git", 2088 | "reference": "dee379131dceed90a429e951546b33edfe7dccbb" 2089 | }, 2090 | "dist": { 2091 | "type": "zip", 2092 | "url": "https://api.github.com/repos/symfony/filesystem/zipball/dee379131dceed90a429e951546b33edfe7dccbb", 2093 | "reference": "dee379131dceed90a429e951546b33edfe7dccbb", 2094 | "shasum": "" 2095 | }, 2096 | "require": { 2097 | "php": ">=5.3.9" 2098 | }, 2099 | "type": "library", 2100 | "extra": { 2101 | "branch-alias": { 2102 | "dev-master": "2.8-dev" 2103 | } 2104 | }, 2105 | "autoload": { 2106 | "psr-4": { 2107 | "Symfony\\Component\\Filesystem\\": "" 2108 | }, 2109 | "exclude-from-classmap": [ 2110 | "/Tests/" 2111 | ] 2112 | }, 2113 | "notification-url": "https://packagist.org/downloads/", 2114 | "license": [ 2115 | "MIT" 2116 | ], 2117 | "authors": [ 2118 | { 2119 | "name": "Fabien Potencier", 2120 | "email": "fabien@symfony.com" 2121 | }, 2122 | { 2123 | "name": "Symfony Community", 2124 | "homepage": "https://symfony.com/contributors" 2125 | } 2126 | ], 2127 | "description": "Symfony Filesystem Component", 2128 | "homepage": "https://symfony.com", 2129 | "time": "2016-04-12 18:01:21" 2130 | }, 2131 | { 2132 | "name": "symfony/finder", 2133 | "version": "v2.8.6", 2134 | "source": { 2135 | "type": "git", 2136 | "url": "https://github.com/symfony/finder.git", 2137 | "reference": "ca24cf2cd4e3826f571e0067e535758e73807aa1" 2138 | }, 2139 | "dist": { 2140 | "type": "zip", 2141 | "url": "https://api.github.com/repos/symfony/finder/zipball/ca24cf2cd4e3826f571e0067e535758e73807aa1", 2142 | "reference": "ca24cf2cd4e3826f571e0067e535758e73807aa1", 2143 | "shasum": "" 2144 | }, 2145 | "require": { 2146 | "php": ">=5.3.9" 2147 | }, 2148 | "type": "library", 2149 | "extra": { 2150 | "branch-alias": { 2151 | "dev-master": "2.8-dev" 2152 | } 2153 | }, 2154 | "autoload": { 2155 | "psr-4": { 2156 | "Symfony\\Component\\Finder\\": "" 2157 | }, 2158 | "exclude-from-classmap": [ 2159 | "/Tests/" 2160 | ] 2161 | }, 2162 | "notification-url": "https://packagist.org/downloads/", 2163 | "license": [ 2164 | "MIT" 2165 | ], 2166 | "authors": [ 2167 | { 2168 | "name": "Fabien Potencier", 2169 | "email": "fabien@symfony.com" 2170 | }, 2171 | { 2172 | "name": "Symfony Community", 2173 | "homepage": "https://symfony.com/contributors" 2174 | } 2175 | ], 2176 | "description": "Symfony Finder Component", 2177 | "homepage": "https://symfony.com", 2178 | "time": "2016-03-10 10:53:53" 2179 | }, 2180 | { 2181 | "name": "symfony/polyfill-mbstring", 2182 | "version": "v1.1.1", 2183 | "source": { 2184 | "type": "git", 2185 | "url": "https://github.com/symfony/polyfill-mbstring.git", 2186 | "reference": "1289d16209491b584839022f29257ad859b8532d" 2187 | }, 2188 | "dist": { 2189 | "type": "zip", 2190 | "url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/1289d16209491b584839022f29257ad859b8532d", 2191 | "reference": "1289d16209491b584839022f29257ad859b8532d", 2192 | "shasum": "" 2193 | }, 2194 | "require": { 2195 | "php": ">=5.3.3" 2196 | }, 2197 | "suggest": { 2198 | "ext-mbstring": "For best performance" 2199 | }, 2200 | "type": "library", 2201 | "extra": { 2202 | "branch-alias": { 2203 | "dev-master": "1.1-dev" 2204 | } 2205 | }, 2206 | "autoload": { 2207 | "psr-4": { 2208 | "Symfony\\Polyfill\\Mbstring\\": "" 2209 | }, 2210 | "files": [ 2211 | "bootstrap.php" 2212 | ] 2213 | }, 2214 | "notification-url": "https://packagist.org/downloads/", 2215 | "license": [ 2216 | "MIT" 2217 | ], 2218 | "authors": [ 2219 | { 2220 | "name": "Nicolas Grekas", 2221 | "email": "p@tchwork.com" 2222 | }, 2223 | { 2224 | "name": "Symfony Community", 2225 | "homepage": "https://symfony.com/contributors" 2226 | } 2227 | ], 2228 | "description": "Symfony polyfill for the Mbstring extension", 2229 | "homepage": "https://symfony.com", 2230 | "keywords": [ 2231 | "compatibility", 2232 | "mbstring", 2233 | "polyfill", 2234 | "portable", 2235 | "shim" 2236 | ], 2237 | "time": "2016-01-20 09:13:37" 2238 | }, 2239 | { 2240 | "name": "symfony/process", 2241 | "version": "v2.8.6", 2242 | "source": { 2243 | "type": "git", 2244 | "url": "https://github.com/symfony/process.git", 2245 | "reference": "1276bd9be89be039748cf753a2137f4ef149cd74" 2246 | }, 2247 | "dist": { 2248 | "type": "zip", 2249 | "url": "https://api.github.com/repos/symfony/process/zipball/1276bd9be89be039748cf753a2137f4ef149cd74", 2250 | "reference": "1276bd9be89be039748cf753a2137f4ef149cd74", 2251 | "shasum": "" 2252 | }, 2253 | "require": { 2254 | "php": ">=5.3.9" 2255 | }, 2256 | "type": "library", 2257 | "extra": { 2258 | "branch-alias": { 2259 | "dev-master": "2.8-dev" 2260 | } 2261 | }, 2262 | "autoload": { 2263 | "psr-4": { 2264 | "Symfony\\Component\\Process\\": "" 2265 | }, 2266 | "exclude-from-classmap": [ 2267 | "/Tests/" 2268 | ] 2269 | }, 2270 | "notification-url": "https://packagist.org/downloads/", 2271 | "license": [ 2272 | "MIT" 2273 | ], 2274 | "authors": [ 2275 | { 2276 | "name": "Fabien Potencier", 2277 | "email": "fabien@symfony.com" 2278 | }, 2279 | { 2280 | "name": "Symfony Community", 2281 | "homepage": "https://symfony.com/contributors" 2282 | } 2283 | ], 2284 | "description": "Symfony Process Component", 2285 | "homepage": "https://symfony.com", 2286 | "time": "2016-04-14 15:22:22" 2287 | }, 2288 | { 2289 | "name": "symfony/yaml", 2290 | "version": "v2.8.6", 2291 | "source": { 2292 | "type": "git", 2293 | "url": "https://github.com/symfony/yaml.git", 2294 | "reference": "e4fbcc65f90909c999ac3b4dfa699ee6563a9940" 2295 | }, 2296 | "dist": { 2297 | "type": "zip", 2298 | "url": "https://api.github.com/repos/symfony/yaml/zipball/e4fbcc65f90909c999ac3b4dfa699ee6563a9940", 2299 | "reference": "e4fbcc65f90909c999ac3b4dfa699ee6563a9940", 2300 | "shasum": "" 2301 | }, 2302 | "require": { 2303 | "php": ">=5.3.9" 2304 | }, 2305 | "type": "library", 2306 | "extra": { 2307 | "branch-alias": { 2308 | "dev-master": "2.8-dev" 2309 | } 2310 | }, 2311 | "autoload": { 2312 | "psr-4": { 2313 | "Symfony\\Component\\Yaml\\": "" 2314 | }, 2315 | "exclude-from-classmap": [ 2316 | "/Tests/" 2317 | ] 2318 | }, 2319 | "notification-url": "https://packagist.org/downloads/", 2320 | "license": [ 2321 | "MIT" 2322 | ], 2323 | "authors": [ 2324 | { 2325 | "name": "Fabien Potencier", 2326 | "email": "fabien@symfony.com" 2327 | }, 2328 | { 2329 | "name": "Symfony Community", 2330 | "homepage": "https://symfony.com/contributors" 2331 | } 2332 | ], 2333 | "description": "Symfony Yaml Component", 2334 | "homepage": "https://symfony.com", 2335 | "time": "2016-03-29 19:00:15" 2336 | }, 2337 | { 2338 | "name": "twig/twig", 2339 | "version": "v1.24.0", 2340 | "source": { 2341 | "type": "git", 2342 | "url": "https://github.com/twigphp/Twig.git", 2343 | "reference": "3e5aa30ebfbafd5951fb1b01e338e1800ce7e0e8" 2344 | }, 2345 | "dist": { 2346 | "type": "zip", 2347 | "url": "https://api.github.com/repos/twigphp/Twig/zipball/3e5aa30ebfbafd5951fb1b01e338e1800ce7e0e8", 2348 | "reference": "3e5aa30ebfbafd5951fb1b01e338e1800ce7e0e8", 2349 | "shasum": "" 2350 | }, 2351 | "require": { 2352 | "php": ">=5.2.7" 2353 | }, 2354 | "require-dev": { 2355 | "symfony/debug": "~2.7", 2356 | "symfony/phpunit-bridge": "~2.7" 2357 | }, 2358 | "type": "library", 2359 | "extra": { 2360 | "branch-alias": { 2361 | "dev-master": "1.24-dev" 2362 | } 2363 | }, 2364 | "autoload": { 2365 | "psr-0": { 2366 | "Twig_": "lib/" 2367 | } 2368 | }, 2369 | "notification-url": "https://packagist.org/downloads/", 2370 | "license": [ 2371 | "BSD-3-Clause" 2372 | ], 2373 | "authors": [ 2374 | { 2375 | "name": "Fabien Potencier", 2376 | "email": "fabien@symfony.com", 2377 | "homepage": "http://fabien.potencier.org", 2378 | "role": "Lead Developer" 2379 | }, 2380 | { 2381 | "name": "Armin Ronacher", 2382 | "email": "armin.ronacher@active-4.com", 2383 | "role": "Project Founder" 2384 | }, 2385 | { 2386 | "name": "Twig Team", 2387 | "homepage": "http://twig.sensiolabs.org/contributors", 2388 | "role": "Contributors" 2389 | } 2390 | ], 2391 | "description": "Twig, the flexible, fast, and secure template language for PHP", 2392 | "homepage": "http://twig.sensiolabs.org", 2393 | "keywords": [ 2394 | "templating" 2395 | ], 2396 | "time": "2016-01-25 21:22:18" 2397 | } 2398 | ], 2399 | "aliases": [], 2400 | "minimum-stability": "stable", 2401 | "stability-flags": [], 2402 | "prefer-stable": false, 2403 | "prefer-lowest": false, 2404 | "platform": { 2405 | "php": "^5.6 || ^7.0" 2406 | }, 2407 | "platform-dev": [] 2408 | } 2409 | -------------------------------------------------------------------------------- /phpunit.xml.dist: -------------------------------------------------------------------------------- 1 | 2 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | tests/src 41 | 42 | 43 | 44 | 45 | src 46 | 47 | 48 | 49 | -------------------------------------------------------------------------------- /sami-config.php: -------------------------------------------------------------------------------- 1 | 6 | */ 7 | 8 | /** 9 | * Initialize autoloader 10 | */ 11 | require_once __DIR__ . '/vendor/autoload.php'; 12 | 13 | /** 14 | * Import classes 15 | */ 16 | use Sami\Sami; 17 | use Symfony\Component\Finder\Finder; 18 | 19 | /** 20 | * Return sami object 21 | */ 22 | return new Sami( 23 | Finder::create()->files()->name('*.php')->in(__DIR__ . '/src'), 24 | [ 25 | 'title' => 'Stream API', 26 | 'build_dir' => __DIR__ . '/build/docs', 27 | 'cache_dir' => __DIR__ . '/cache/sami', 28 | 'default_opened_level' => 2, 29 | ] 30 | ); 31 | -------------------------------------------------------------------------------- /src/ByteOrder.php: -------------------------------------------------------------------------------- 1 | 6 | */ 7 | 8 | namespace GravityMedia\Stream; 9 | 10 | /** 11 | * Byte order class. 12 | * 13 | * @package GravityMedia\Stream 14 | */ 15 | class ByteOrder 16 | { 17 | /** 18 | * Machine endian 19 | */ 20 | const MACHINE_ENDIAN = 0; 21 | 22 | /** 23 | * Big endian 24 | */ 25 | const BIG_ENDIAN = 1; 26 | 27 | /** 28 | * Little endian 29 | */ 30 | const LITTLE_ENDIAN = 2; 31 | 32 | /** 33 | * Valid values 34 | * 35 | * @var int[] 36 | */ 37 | protected static $values = [ 38 | self::MACHINE_ENDIAN, 39 | self::BIG_ENDIAN, 40 | self::LITTLE_ENDIAN 41 | ]; 42 | 43 | /** 44 | * Return valid values 45 | * 46 | * @return int[] 47 | */ 48 | public static function values() 49 | { 50 | return static::$values; 51 | } 52 | } 53 | -------------------------------------------------------------------------------- /src/Exception/BadMethodCallException.php: -------------------------------------------------------------------------------- 1 | 6 | */ 7 | 8 | namespace GravityMedia\Stream\Exception; 9 | 10 | /** 11 | * Bad method call exception class. 12 | * 13 | * @package GravityMedia\Stream\Exception 14 | */ 15 | class BadMethodCallException extends \BadMethodCallException implements ExceptionInterface 16 | { 17 | } 18 | -------------------------------------------------------------------------------- /src/Exception/ExceptionInterface.php: -------------------------------------------------------------------------------- 1 | 6 | */ 7 | 8 | namespace GravityMedia\Stream\Exception; 9 | 10 | /** 11 | * Exception interface. 12 | * 13 | * @package GravityMedia\Stream\Exception 14 | */ 15 | interface ExceptionInterface 16 | { 17 | } 18 | -------------------------------------------------------------------------------- /src/Exception/IOException.php: -------------------------------------------------------------------------------- 1 | 6 | */ 7 | 8 | namespace GravityMedia\Stream\Exception; 9 | 10 | /** 11 | * IO exception class. 12 | * 13 | * @package GravityMedia\Stream\Exception 14 | */ 15 | class IOException extends \RuntimeException implements ExceptionInterface 16 | { 17 | } 18 | -------------------------------------------------------------------------------- /src/Exception/InvalidArgumentException.php: -------------------------------------------------------------------------------- 1 | 6 | */ 7 | 8 | namespace GravityMedia\Stream\Exception; 9 | 10 | /** 11 | * Invalid argument exception class. 12 | * 13 | * @package GravityMedia\Stream\Exception 14 | */ 15 | class InvalidArgumentException extends \InvalidArgumentException implements ExceptionInterface 16 | { 17 | } 18 | -------------------------------------------------------------------------------- /src/Stream.php: -------------------------------------------------------------------------------- 1 | 6 | */ 7 | 8 | namespace GravityMedia\Stream; 9 | 10 | use GravityMedia\Stream\Exception; 11 | 12 | /** 13 | * Stream class. 14 | * 15 | * @package GravityMedia\Stream 16 | */ 17 | class Stream 18 | { 19 | /** 20 | * @var string[] 21 | */ 22 | private static $readModes = ['r', 'w+', 'r+', 'x+', 'c+', 'rb', 'w+b', 'r+b', 'x+b', 'c+b', 'rt', 'w+t', 23 | 'r+t', 'x+t', 'c+t', 'a+']; 24 | 25 | /** 26 | * @var string[] 27 | */ 28 | private static $writeModes = ['w', 'w+', 'rw', 'r+', 'x+', 'c+', 'wb', 'w+b', 'r+b', 'x+b', 'c+b', 'w+t', 29 | 'r+t', 'x+t', 'c+t', 'a', 'a+']; 30 | 31 | /** 32 | * @var resource 33 | */ 34 | protected $resource; 35 | 36 | /** 37 | * @var bool 38 | */ 39 | protected $local; 40 | 41 | /** 42 | * @var bool 43 | */ 44 | protected $readable; 45 | 46 | /** 47 | * @var bool 48 | */ 49 | protected $writable; 50 | 51 | /** 52 | * @var bool 53 | */ 54 | protected $seekable; 55 | 56 | /** 57 | * @var string 58 | */ 59 | protected $uri; 60 | 61 | /** 62 | * @var int 63 | */ 64 | protected $byteOrder; 65 | 66 | /** 67 | * @var int 68 | */ 69 | protected static $machineByteOrder; 70 | 71 | /** 72 | * Create stream object from resource. 73 | * 74 | * @param resource $resource 75 | * 76 | * @throws Exception\InvalidArgumentException An exception will be thrown for invalid resource arguments. 77 | * 78 | * @return static 79 | */ 80 | public static function fromResource($resource) 81 | { 82 | if (!is_resource($resource)) { 83 | throw new Exception\InvalidArgumentException('Invalid resource'); 84 | } 85 | 86 | $stream = new static(); 87 | 88 | return $stream->bindResource($resource); 89 | } 90 | 91 | /** 92 | * Bind resource to stream and gather meta data. 93 | * 94 | * @param resource $resource The resource to bind to the stream. 95 | * 96 | * @throws Exception\InvalidArgumentException An exception will be thrown for invalid resource arguments. 97 | * 98 | * @return $this 99 | */ 100 | public function bindResource($resource) 101 | { 102 | if (!is_resource($resource)) { 103 | throw new Exception\InvalidArgumentException('Invalid resource'); 104 | } 105 | 106 | $metaData = stream_get_meta_data($resource); 107 | 108 | $this->resource = $resource; 109 | $this->local = stream_is_local($resource); 110 | $this->readable = in_array($metaData['mode'], self::$readModes); 111 | $this->writable = in_array($metaData['mode'], self::$writeModes); 112 | $this->seekable = $metaData['seekable']; 113 | $this->uri = $metaData['uri']; 114 | 115 | return $this; 116 | } 117 | 118 | /** 119 | * Return whether the stream is local. 120 | * 121 | * @return bool 122 | */ 123 | public function isLocal() 124 | { 125 | return $this->local; 126 | } 127 | 128 | /** 129 | * Return whether read access on the stream will be granted. 130 | * 131 | * @return bool 132 | */ 133 | public function isReadable() 134 | { 135 | return $this->readable; 136 | } 137 | 138 | /** 139 | * Return whether write access on the stream will be granted. 140 | * 141 | * @return bool 142 | */ 143 | public function isWritable() 144 | { 145 | return $this->writable; 146 | } 147 | 148 | /** 149 | * Return whether the stream can be sought. 150 | * 151 | * @return bool 152 | */ 153 | public function isSeekable() 154 | { 155 | return $this->seekable; 156 | } 157 | 158 | /** 159 | * Get the URI or filename associated with the stream. 160 | * 161 | * @return string 162 | */ 163 | public function getUri() 164 | { 165 | return $this->uri; 166 | } 167 | 168 | /** 169 | * Get the byte order for integer handling. 170 | * 171 | * @return int 172 | */ 173 | public function getByteOrder() 174 | { 175 | if (null === $this->byteOrder) { 176 | return ByteOrder::MACHINE_ENDIAN; 177 | } 178 | 179 | return $this->byteOrder; 180 | } 181 | 182 | /** 183 | * Set the byte order for integer handling. 184 | * 185 | * @param int $byteOrder The byte order to set. Must be one of the constants defined by the byte order enum. 186 | * 187 | * @throws Exception\InvalidArgumentException An exception will be thrown for invalid byte order arguments. 188 | * 189 | * @return $this 190 | */ 191 | public function setByteOrder($byteOrder) 192 | { 193 | if (!in_array($byteOrder, ByteOrder::values(), true)) { 194 | throw new Exception\InvalidArgumentException('Invalid byte order'); 195 | } 196 | 197 | $this->byteOrder = $byteOrder; 198 | 199 | return $this; 200 | } 201 | 202 | /** 203 | * Get the machine byte order. 204 | * 205 | * @return int 206 | */ 207 | public function getMachineByteOrder() 208 | { 209 | if (null === static::$machineByteOrder) { 210 | static::$machineByteOrder = ByteOrder::BIG_ENDIAN; 211 | 212 | list(, $value) = @unpack('s', "\x01\x00"); 213 | if (1 === $value) { 214 | static::$machineByteOrder = ByteOrder::LITTLE_ENDIAN; 215 | } 216 | } 217 | 218 | return static::$machineByteOrder; 219 | } 220 | 221 | /** 222 | * Get information about the stream. 223 | * 224 | * @param string $info The information to retrieve. 225 | * 226 | * @throws Exception\IOException An exception will be thrown for invalid stream resources. 227 | * 228 | * @return int 229 | */ 230 | protected function getStat($info) 231 | { 232 | if (!is_resource($this->resource)) { 233 | throw new Exception\IOException('Invalid stream resource'); 234 | } 235 | 236 | $uri = $this->getUri(); 237 | if (is_string($uri)) { 238 | clearstatcache(true, $uri); 239 | } 240 | 241 | $stat = fstat($this->resource); 242 | 243 | return $stat[$info]; 244 | } 245 | 246 | /** 247 | * Get size of the stream in bytes 248 | * 249 | * @throws Exception\BadMethodCallException An exception will be thrown for non-local streams. 250 | * @throws Exception\IOException An exception will be thrown for invalid stream resources. 251 | * 252 | * @return int 253 | */ 254 | public function getSize() 255 | { 256 | if (!$this->isLocal()) { 257 | throw new Exception\BadMethodCallException('Stream not local'); 258 | } 259 | 260 | return $this->getStat('size'); 261 | } 262 | 263 | /** 264 | * Return whether the end of the stream was reached. 265 | * 266 | * @throws Exception\IOException An exception will be thrown for invalid stream resources. 267 | * 268 | * @return bool 269 | * @link http://www.php.net/manual/en/function.feof.php 270 | */ 271 | public function eof() 272 | { 273 | if (!is_resource($this->resource)) { 274 | throw new Exception\IOException('Invalid stream resource'); 275 | } 276 | 277 | return feof($this->resource); 278 | } 279 | 280 | /** 281 | * Return the current position of the stream. 282 | * 283 | * @throws Exception\IOException An exception will be thrown for invalid stream resources. 284 | * 285 | * @return int 286 | * @link http://www.php.net/manual/en/function.ftell.php 287 | */ 288 | public function tell() 289 | { 290 | if (!is_resource($this->resource)) { 291 | throw new Exception\IOException('Invalid stream resource'); 292 | } 293 | 294 | return ftell($this->resource); 295 | } 296 | 297 | /** 298 | * Seek and return the position of the stream. 299 | * 300 | * @param int $offset The offset. 301 | * @param int $whence Either SEEK_SET (which is default), SEEK_CUR or SEEK_END. 302 | * 303 | * @throws Exception\BadMethodCallException An exception will be thrown for non-seekable streams. 304 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 305 | * position could not be set. 306 | * 307 | * @return int 308 | * @link http://www.php.net/manual/en/function.fseek.php 309 | */ 310 | public function seek($offset, $whence = SEEK_SET) 311 | { 312 | if (!$this->isSeekable()) { 313 | throw new Exception\BadMethodCallException('Stream not seekable'); 314 | } 315 | 316 | if (!is_resource($this->resource)) { 317 | throw new Exception\IOException('Invalid stream resource'); 318 | } 319 | 320 | if (fseek($this->resource, $offset, $whence) < 0) { 321 | throw new Exception\IOException('Unexpected result of operation'); 322 | } 323 | 324 | return $this->tell(); 325 | } 326 | 327 | /** 328 | * Rewind the position of the stream. 329 | * 330 | * @throws Exception\BadMethodCallException An exception will be thrown for non-seekable streams. 331 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 332 | * position could not be set. 333 | * 334 | * @return int 335 | */ 336 | public function rewind() 337 | { 338 | return $this->seek(0); 339 | } 340 | 341 | /** 342 | * Align the data in relation to the byte order. 343 | * 344 | * @param string $data 345 | * 346 | * @return string 347 | */ 348 | protected function alignData($data) 349 | { 350 | if ($this->getByteOrder() !== ByteOrder::MACHINE_ENDIAN 351 | && $this->getByteOrder() !== $this->getMachineByteOrder() 352 | ) { 353 | return strrev($data); 354 | } 355 | 356 | return $data; 357 | } 358 | 359 | /** 360 | * Read up to $length number of bytes of data from the stream. 361 | * 362 | * @param int $length The maximum number of bytes to read. 363 | * 364 | * @throws Exception\BadMethodCallException An exception will be thrown for non-readable streams. 365 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 366 | * data could not be read. 367 | * 368 | * @return string 369 | * @link http://www.php.net/manual/en/function.fread.php 370 | */ 371 | public function read($length) 372 | { 373 | if (!$this->isReadable()) { 374 | throw new Exception\BadMethodCallException('Stream not readable'); 375 | } 376 | 377 | if (!is_resource($this->resource)) { 378 | throw new Exception\IOException('Invalid stream resource'); 379 | } 380 | 381 | $data = @fread($this->resource, $length); 382 | if (false === $data) { 383 | throw new Exception\IOException('Unexpected result of operation'); 384 | } 385 | 386 | return $data; 387 | } 388 | 389 | /** 390 | * Read signed 8-bit integer (char) data from the stream. 391 | * 392 | * @throws Exception\BadMethodCallException An exception will be thrown for non-readable streams. 393 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 394 | * data could not be read. 395 | * 396 | * @return int 397 | */ 398 | public function readInt8() 399 | { 400 | list(, $value) = @unpack('c', $this->read(1)); 401 | return $value; 402 | } 403 | 404 | /** 405 | * Read unsigned 8-bit integer (char) data from the stream. 406 | * 407 | * @throws Exception\BadMethodCallException An exception will be thrown for non-readable streams. 408 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 409 | * data could not be read. 410 | * 411 | * @return int 412 | */ 413 | public function readUInt8() 414 | { 415 | list(, $value) = @unpack('C', $this->read(1)); 416 | return $value; 417 | } 418 | 419 | /** 420 | * Read signed 16-bit integer (short) data from the stream. 421 | * 422 | * @throws Exception\BadMethodCallException An exception will be thrown for non-readable streams. 423 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 424 | * data could not be read. 425 | * 426 | * @return int 427 | */ 428 | public function readInt16() 429 | { 430 | list(, $value) = @unpack('s', $this->alignData($this->read(2))); 431 | return $value; 432 | } 433 | 434 | /** 435 | * Read unsigned 16-bit integer (short) data from the stream. 436 | * 437 | * @throws Exception\BadMethodCallException An exception will be thrown for non-readable streams. 438 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 439 | * data could not be read. 440 | * 441 | * @return int 442 | */ 443 | public function readUInt16() 444 | { 445 | switch ($this->getByteOrder()) { 446 | case ByteOrder::BIG_ENDIAN: 447 | $format = 'n'; 448 | break; 449 | case ByteOrder::LITTLE_ENDIAN: 450 | $format = 'v'; 451 | break; 452 | default: 453 | $format = 'S'; 454 | } 455 | 456 | list(, $value) = @unpack($format, $this->read(2)); 457 | return $value; 458 | } 459 | 460 | /** 461 | * Read signed 24-bit integer data from the stream. 462 | * 463 | * @throws Exception\BadMethodCallException An exception will be thrown for non-readable streams. 464 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 465 | * data could not be read. 466 | * 467 | * @return int 468 | */ 469 | public function readInt24() 470 | { 471 | $value = $this->readUInt24(); 472 | 473 | if ($value & 0x800000) { 474 | $value -= 0x1000000; 475 | } 476 | 477 | return $value; 478 | } 479 | 480 | /** 481 | * Read unsigned 24-bit integer data from the stream. 482 | * 483 | * @throws Exception\BadMethodCallException An exception will be thrown for non-readable streams. 484 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 485 | * data could not be read. 486 | * 487 | * @return int 488 | */ 489 | public function readUInt24() 490 | { 491 | $values = @unpack('C3', $this->alignData($this->read(3))); 492 | return $values[1] | $values[2] << 8 | $values[3] << 16; 493 | } 494 | 495 | /** 496 | * Read signed 32-bit integer (long) data from the stream. 497 | * 498 | * @throws Exception\BadMethodCallException An exception will be thrown for non-readable streams. 499 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 500 | * data could not be read. 501 | * 502 | * @return int 503 | */ 504 | public function readInt32() 505 | { 506 | list(, $value) = @unpack('l', $this->alignData($this->read(4))); 507 | return $value; 508 | } 509 | 510 | /** 511 | * Read unsigned 32-bit integer (long) data from the stream. 512 | * 513 | * @throws Exception\BadMethodCallException An exception will be thrown for non-readable streams. 514 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 515 | * data could not be read. 516 | * 517 | * @return int 518 | */ 519 | public function readUInt32() 520 | { 521 | switch ($this->getByteOrder()) { 522 | case ByteOrder::BIG_ENDIAN: 523 | $format = 'N'; 524 | break; 525 | case ByteOrder::LITTLE_ENDIAN: 526 | $format = 'V'; 527 | break; 528 | default: 529 | $format = 'L'; 530 | } 531 | 532 | list(, $value) = @unpack($format, $this->read(4)); 533 | return $value; 534 | } 535 | 536 | /** 537 | * Read signed 48-bit integer data from the stream. 538 | * 539 | * @throws Exception\BadMethodCallException An exception will be thrown for non-readable streams. 540 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 541 | * data could not be read. 542 | * 543 | * @return int 544 | */ 545 | public function readInt48() 546 | { 547 | $value = $this->readUInt48(); 548 | 549 | if ($value & 0x800000000000) { 550 | $value -= 0x1000000000000; 551 | } 552 | 553 | return $value; 554 | } 555 | 556 | /** 557 | * Read unsigned 48-bit integer data from the stream. 558 | * 559 | * @throws Exception\BadMethodCallException An exception will be thrown for non-readable streams. 560 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 561 | * data could not be read. 562 | * 563 | * @return int 564 | */ 565 | public function readUInt48() 566 | { 567 | $values = @unpack('C6', $this->alignData($this->read(6))); 568 | return $values[1] | $values[2] << 8 | $values[3] << 16 | $values[4] << 24 | $values[5] << 32 | $values[6] << 40; 569 | } 570 | 571 | /** 572 | * Read signed 64-bit integer (long long) data from the stream. 573 | * 574 | * @throws Exception\BadMethodCallException An exception will be thrown for non-readable streams. 575 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 576 | * data could not be read. 577 | * 578 | * @return int 579 | */ 580 | public function readInt64() 581 | { 582 | list(, $value) = @unpack('q', $this->alignData($this->read(8))); 583 | return $value; 584 | } 585 | 586 | /** 587 | * Read unsigned 64-bit integer (long long) data from the stream. 588 | * 589 | * @throws Exception\BadMethodCallException An exception will be thrown for non-readable streams. 590 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 591 | * data could not be read. 592 | * 593 | * @return int 594 | */ 595 | public function readUInt64() 596 | { 597 | switch ($this->getByteOrder()) { 598 | case ByteOrder::BIG_ENDIAN: 599 | $format = 'J'; 600 | break; 601 | case ByteOrder::LITTLE_ENDIAN: 602 | $format = 'P'; 603 | break; 604 | default: 605 | $format = 'Q'; 606 | } 607 | 608 | list(, $value) = @unpack($format, $this->read(8)); 609 | return $value; 610 | } 611 | 612 | /** 613 | * Write data to the stream and return the number of bytes written. 614 | * 615 | * @param string $data The data 616 | * 617 | * @throws Exception\BadMethodCallException An exception will be thrown for non-writable streams. 618 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 619 | * data could not be written. 620 | * 621 | * @return int 622 | * @link http://www.php.net/manual/en/function.fwrite.php 623 | */ 624 | public function write($data) 625 | { 626 | if (!$this->isWritable()) { 627 | throw new Exception\BadMethodCallException('Stream not writable'); 628 | } 629 | 630 | if (!is_resource($this->resource)) { 631 | throw new Exception\IOException('Invalid stream resource'); 632 | } 633 | 634 | $length = @fwrite($this->resource, $data); 635 | if (false === $length) { 636 | throw new Exception\IOException('Unexpected result of operation'); 637 | } 638 | 639 | return $length; 640 | } 641 | 642 | /** 643 | * Write signed 8-bit integer (char) data to the stream 644 | * 645 | * @param int $value The value 646 | * 647 | * @return int 648 | */ 649 | public function writeInt8($value) 650 | { 651 | return $this->write(pack('c', $value)); 652 | } 653 | 654 | /** 655 | * Write unsigned 8-bit integer (char) data to the stream 656 | * 657 | * @param int $value The value 658 | * 659 | * @return int 660 | */ 661 | public function writeUInt8($value) 662 | { 663 | return $this->write(pack('C', $value)); 664 | } 665 | 666 | /** 667 | * Write signed 16-bit integer (short) data to the stream 668 | * 669 | * @param int $value The value 670 | * 671 | * @return int 672 | */ 673 | public function writeInt16($value) 674 | { 675 | return $this->write($this->alignData(pack('s', $value))); 676 | } 677 | 678 | /** 679 | * Write unsigned 16-bit integer (short) data to the stream 680 | * 681 | * @param int $value The value 682 | * 683 | * @return int 684 | */ 685 | public function writeUInt16($value) 686 | { 687 | switch ($this->getByteOrder()) { 688 | case ByteOrder::BIG_ENDIAN: 689 | $format = 'n'; 690 | break; 691 | case ByteOrder::LITTLE_ENDIAN: 692 | $format = 'v'; 693 | break; 694 | default: 695 | $format = 'S'; 696 | } 697 | 698 | return $this->write(pack($format, $value)); 699 | } 700 | 701 | /** 702 | * Write signed 24-bit integer data to the stream 703 | * 704 | * @param int $value The value 705 | * 706 | * @return int 707 | */ 708 | public function writeInt24($value) 709 | { 710 | if ($value & 0x7fffff) { 711 | $value += 0x1000000; 712 | } 713 | 714 | return $this->writeUInt24($value); 715 | } 716 | 717 | /** 718 | * Write unsigned 24-bit integer data to the stream 719 | * 720 | * @param int $value The value 721 | * 722 | * @return int 723 | */ 724 | public function writeUInt24($value) 725 | { 726 | return $this->write($this->alignData(pack('C3', $value, $value >> 8, $value >> 16))); 727 | } 728 | 729 | /** 730 | * Write signed 32-bit integer (long) data to the stream 731 | * 732 | * @param int $value The value 733 | * 734 | * @return int 735 | */ 736 | public function writeInt32($value) 737 | { 738 | return $this->write($this->alignData(pack('l', $value))); 739 | } 740 | 741 | /** 742 | * Write unsigned 32-bit integer (long) data to the stream 743 | * 744 | * @param int $value The value 745 | * 746 | * @return int 747 | */ 748 | public function writeUInt32($value) 749 | { 750 | switch ($this->getByteOrder()) { 751 | case ByteOrder::BIG_ENDIAN: 752 | $format = 'N'; 753 | break; 754 | case ByteOrder::LITTLE_ENDIAN: 755 | $format = 'V'; 756 | break; 757 | default: 758 | $format = 'L'; 759 | } 760 | 761 | return $this->write(pack($format, $value)); 762 | } 763 | 764 | /** 765 | * Write signed 48-bit integer data to the stream 766 | * 767 | * @param int $value The value 768 | * 769 | * @return int 770 | */ 771 | public function writeInt48($value) 772 | { 773 | if ($value & 0x7fffffffffff) { 774 | $value += 0x1000000000000; 775 | } 776 | 777 | return $this->writeUInt48($value); 778 | } 779 | 780 | /** 781 | * Write unsigned 48-bit integer data to the stream 782 | * 783 | * @param int $value The value 784 | * 785 | * @return int 786 | */ 787 | public function writeUInt48($value) 788 | { 789 | return $this->write($this->alignData( 790 | pack('C6', $value, $value >> 8, $value >> 16, $value >> 24, $value >> 32, $value >> 40) 791 | )); 792 | } 793 | 794 | /** 795 | * Write signed 64-bit integer (long long) data to the stream 796 | * 797 | * @param int $value The value 798 | * 799 | * @return int 800 | */ 801 | public function writeInt64($value) 802 | { 803 | return $this->write($this->alignData(pack('q', $value))); 804 | } 805 | 806 | /** 807 | * Write unsigned 64-bit integer (long long) data to the stream 808 | * 809 | * @param int $value The value 810 | * 811 | * @return int 812 | */ 813 | public function writeUInt64($value) 814 | { 815 | switch ($this->getByteOrder()) { 816 | case ByteOrder::BIG_ENDIAN: 817 | $format = 'J'; 818 | break; 819 | case ByteOrder::LITTLE_ENDIAN: 820 | $format = 'P'; 821 | break; 822 | default: 823 | $format = 'Q'; 824 | } 825 | 826 | return $this->write(pack($format, $value)); 827 | } 828 | 829 | /** 830 | * Truncate the stream to a given length. 831 | * 832 | * @param int $size The size to truncate to. 833 | * 834 | * @throws Exception\BadMethodCallException An exception will be thrown for non-writable streams. 835 | * @throws Exception\IOException An exception will be thrown for invalid stream resources or when the 836 | * stream could not be truncated. 837 | * 838 | * @return bool 839 | * @link http://www.php.net/manual/en/function.ftruncate.php 840 | */ 841 | public function truncate($size) 842 | { 843 | if (!$this->isWritable()) { 844 | throw new Exception\BadMethodCallException('Stream not writable'); 845 | } 846 | 847 | if (!is_resource($this->resource)) { 848 | throw new Exception\IOException('Invalid stream resource'); 849 | } 850 | 851 | return @ftruncate($this->resource, $size); 852 | } 853 | 854 | /** 855 | * Close the stream. 856 | * 857 | * @return bool 858 | * @link http://www.php.net/manual/en/function.fclose.php 859 | */ 860 | public function close() 861 | { 862 | return @fclose($this->resource); 863 | } 864 | } 865 | -------------------------------------------------------------------------------- /tests/src/ByteOrderTest.php: -------------------------------------------------------------------------------- 1 | 6 | */ 7 | 8 | namespace GravityMedia\StreamTest; 9 | 10 | use GravityMedia\Stream\ByteOrder; 11 | 12 | /** 13 | * Stream test 14 | * 15 | * @package GravityMedia\StreamTest 16 | * 17 | * @covers GravityMedia\Stream\ByteOrder 18 | */ 19 | class ByteOrderTest extends \PHPUnit_Framework_TestCase 20 | { 21 | /** 22 | * Test that the byte order enum returns all possible values 23 | */ 24 | public function testByteOrderValues() 25 | { 26 | $this->assertSame( 27 | [ByteOrder::MACHINE_ENDIAN, ByteOrder::BIG_ENDIAN, ByteOrder::LITTLE_ENDIAN], 28 | ByteOrder::values() 29 | ); 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /tests/src/Helper/ByteOrderHelper.php: -------------------------------------------------------------------------------- 1 | 6 | */ 7 | 8 | namespace GravityMedia\StreamTest\Helper; 9 | 10 | use GravityMedia\Stream\ByteOrder; 11 | 12 | /** 13 | * Byte order helper class 14 | * 15 | * @package GravityMedia\StreamTest\Helper 16 | */ 17 | class ByteOrderHelper 18 | { 19 | /** 20 | * @var int 21 | */ 22 | protected static $machineByteOrder; 23 | 24 | /** 25 | * Get machine byte order 26 | * 27 | * @return int 28 | */ 29 | public static function getMachineByteOrder() 30 | { 31 | if (null === static::$machineByteOrder) { 32 | static::$machineByteOrder = ByteOrder::BIG_ENDIAN; 33 | 34 | list(, $value) = unpack('s', "\x01\x00"); 35 | if (1 === $value) { 36 | static::$machineByteOrder = ByteOrder::LITTLE_ENDIAN; 37 | } 38 | } 39 | 40 | return static::$machineByteOrder; 41 | } 42 | } 43 | -------------------------------------------------------------------------------- /tests/src/Helper/ResourceHelper.php: -------------------------------------------------------------------------------- 1 | 6 | */ 7 | 8 | namespace GravityMedia\StreamTest\Helper; 9 | 10 | /** 11 | * Resource helper class 12 | * 13 | * @package GravityMedia\StreamTest\Helper 14 | */ 15 | class ResourceHelper 16 | { 17 | /** 18 | * The URI of the resource 19 | */ 20 | const RESOURCE_URI = 'php://temp'; 21 | 22 | /** 23 | * The read/write-mode of the resource 24 | */ 25 | const RESOURCE_MODE = 'r+'; 26 | 27 | /** 28 | * @var resource 29 | */ 30 | protected $resource; 31 | 32 | /** 33 | * Create resource helper object 34 | * 35 | * @param string $uri 36 | * @param string $mode 37 | */ 38 | public function __construct($uri = self::RESOURCE_URI, $mode = self::RESOURCE_MODE) 39 | { 40 | $this->resource = fopen($uri, $mode); 41 | } 42 | 43 | /** 44 | * Destroy resource helper object 45 | */ 46 | public function __destruct() 47 | { 48 | @fclose($this->resource); 49 | } 50 | 51 | /** 52 | * Get resource 53 | * 54 | * @return resource 55 | */ 56 | public function getResource() 57 | { 58 | return $this->resource; 59 | } 60 | } 61 | -------------------------------------------------------------------------------- /tests/src/StreamTest.php: -------------------------------------------------------------------------------- 1 | 6 | */ 7 | 8 | namespace GravityMedia\StreamTest; 9 | 10 | use GravityMedia\Stream\ByteOrder; 11 | use GravityMedia\Stream\Stream; 12 | use GravityMedia\StreamTest\Helper\ByteOrderHelper; 13 | use GravityMedia\StreamTest\Helper\ResourceHelper; 14 | 15 | /** 16 | * Stream test 17 | * 18 | * @package GravityMedia\StreamTest 19 | * 20 | * @covers GravityMedia\Stream\Stream 21 | * @uses GravityMedia\Stream\ByteOrder 22 | */ 23 | class StreamTest extends \PHPUnit_Framework_TestCase 24 | { 25 | /** 26 | * Provide signed 8-bit characters 27 | * 28 | * @return array 29 | */ 30 | public function provideInt8Values() 31 | { 32 | return [ 33 | ["\x80", -128], 34 | ["\x00", 0], 35 | ["\x7f", 127] 36 | ]; 37 | } 38 | 39 | /** 40 | * Provide unsigned 8-bit characters 41 | * 42 | * @return array 43 | */ 44 | public function provideUInt8Values() 45 | { 46 | return [ 47 | ["\x00", 0], 48 | ["\x7f", 127], 49 | ["\x80", 128], 50 | ["\xff", 255] 51 | ]; 52 | } 53 | 54 | /** 55 | * Provide signed 16-bit integers 56 | * 57 | * @return array 58 | */ 59 | public function provideInt16Values() 60 | { 61 | $values = [ 62 | [ByteOrder::BIG_ENDIAN, "\x80\x00", -32768], 63 | [ByteOrder::BIG_ENDIAN, "\x00\x00", 0], 64 | [ByteOrder::BIG_ENDIAN, "\x7f\xff", 32767], 65 | [ByteOrder::LITTLE_ENDIAN, "\x00\x80", -32768], 66 | [ByteOrder::LITTLE_ENDIAN, "\x00\x00", 0], 67 | [ByteOrder::LITTLE_ENDIAN, "\xff\x7f", 32767] 68 | ]; 69 | 70 | if (ByteOrder::LITTLE_ENDIAN === ByteOrderHelper::getMachineByteOrder()) { 71 | return array_merge($values, [ 72 | [ByteOrder::MACHINE_ENDIAN, "\x00\x80", -32768], 73 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00", 0], 74 | [ByteOrder::MACHINE_ENDIAN, "\xff\x7f", 32767] 75 | ]); 76 | } 77 | 78 | return array_merge($values, [ 79 | [ByteOrder::MACHINE_ENDIAN, "\x80\x00", -32768], 80 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00", 0], 81 | [ByteOrder::MACHINE_ENDIAN, "\x7f\xff", 32767] 82 | ]); 83 | } 84 | 85 | /** 86 | * Provide unsigned 16-bit integers 87 | * 88 | * @return array 89 | */ 90 | public function provideUInt16Values() 91 | { 92 | $values = [ 93 | [ByteOrder::BIG_ENDIAN, "\x00\x00", 0], 94 | [ByteOrder::BIG_ENDIAN, "\x00\x01", 1], 95 | [ByteOrder::BIG_ENDIAN, "\x00\xff", 255], 96 | [ByteOrder::BIG_ENDIAN, "\xff\xfe", 65534], 97 | [ByteOrder::BIG_ENDIAN, "\xff\xff", 65535], 98 | [ByteOrder::LITTLE_ENDIAN, "\x00\x00", 0], 99 | [ByteOrder::LITTLE_ENDIAN, "\x01\x00", 1], 100 | [ByteOrder::LITTLE_ENDIAN, "\xff\x00", 255], 101 | [ByteOrder::LITTLE_ENDIAN, "\xfe\xff", 65534], 102 | [ByteOrder::LITTLE_ENDIAN, "\xff\xff", 65535] 103 | ]; 104 | 105 | if (ByteOrder::LITTLE_ENDIAN === ByteOrderHelper::getMachineByteOrder()) { 106 | return array_merge($values, [ 107 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00", 0], 108 | [ByteOrder::MACHINE_ENDIAN, "\x01\x00", 1], 109 | [ByteOrder::MACHINE_ENDIAN, "\xff\x00", 255], 110 | [ByteOrder::MACHINE_ENDIAN, "\xfe\xff", 65534], 111 | [ByteOrder::MACHINE_ENDIAN, "\xff\xff", 65535] 112 | ]); 113 | } 114 | 115 | return array_merge($values, [ 116 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00", 0], 117 | [ByteOrder::MACHINE_ENDIAN, "\x00\x01", 1], 118 | [ByteOrder::MACHINE_ENDIAN, "\x00\xff", 255], 119 | [ByteOrder::MACHINE_ENDIAN, "\xff\xfe", 65534], 120 | [ByteOrder::MACHINE_ENDIAN, "\xff\xff", 65535] 121 | ]); 122 | } 123 | 124 | /** 125 | * Provide signed 24-bit integers 126 | * 127 | * @return array 128 | */ 129 | public function provideInt24Values() 130 | { 131 | $values = [ 132 | [ByteOrder::BIG_ENDIAN, "\x80\x00\x00", -8388608], 133 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x00", 0], 134 | [ByteOrder::BIG_ENDIAN, "\x7f\xff\xff", 8388607], 135 | [ByteOrder::LITTLE_ENDIAN, "\x00\x00\x80", -8388608], 136 | [ByteOrder::LITTLE_ENDIAN, "\x00\x00\x00", 0], 137 | [ByteOrder::LITTLE_ENDIAN, "\xff\xff\x7f", 8388607] 138 | ]; 139 | 140 | if (ByteOrder::LITTLE_ENDIAN === ByteOrderHelper::getMachineByteOrder()) { 141 | return array_merge($values, [ 142 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x80", -8388608], 143 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00", 0], 144 | [ByteOrder::MACHINE_ENDIAN, "\xff\xff\x7f", 8388607] 145 | ]); 146 | } 147 | 148 | return array_merge($values, [ 149 | [ByteOrder::MACHINE_ENDIAN, "\x80\x00\x00", -8388608], 150 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00", 0], 151 | [ByteOrder::MACHINE_ENDIAN, "\x7f\xff\xff", 8388607] 152 | ]); 153 | } 154 | 155 | /** 156 | * Provide unsigned 24-bit integers 157 | * 158 | * @return array 159 | */ 160 | public function provideUInt24Values() 161 | { 162 | $values = [ 163 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x00", 0], 164 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x01", 1], 165 | [ByteOrder::BIG_ENDIAN, "\x00\x00\xff", 255], 166 | [ByteOrder::BIG_ENDIAN, "\xff\xff\xff", 16777215], 167 | [ByteOrder::LITTLE_ENDIAN, "\x00\x00\x00", 0], 168 | [ByteOrder::LITTLE_ENDIAN, "\x01\x00\x00", 1], 169 | [ByteOrder::LITTLE_ENDIAN, "\xff\x00\x00", 255], 170 | [ByteOrder::LITTLE_ENDIAN, "\xff\xff\xff", 16777215] 171 | ]; 172 | 173 | if (ByteOrder::LITTLE_ENDIAN === ByteOrderHelper::getMachineByteOrder()) { 174 | return array_merge($values, [ 175 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00", 0], 176 | [ByteOrder::MACHINE_ENDIAN, "\x01\x00\x00", 1], 177 | [ByteOrder::MACHINE_ENDIAN, "\xff\x00\x00", 255], 178 | [ByteOrder::MACHINE_ENDIAN, "\xff\xff\xff", 16777215] 179 | ]); 180 | } 181 | 182 | return array_merge($values, [ 183 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00", 0], 184 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x01", 1], 185 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\xff", 255], 186 | [ByteOrder::MACHINE_ENDIAN, "\xff\xff\xff", 16777215] 187 | ]); 188 | } 189 | 190 | /** 191 | * Provide signed 32-bit integers 192 | * 193 | * @return array 194 | */ 195 | public function provideInt32Values() 196 | { 197 | $values = [ 198 | [ByteOrder::BIG_ENDIAN, "\x80\x00\x00\x00", -2147483648], 199 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x00\x00", 0], 200 | [ByteOrder::BIG_ENDIAN, "\x7f\xff\xff\xff", 2147483647], 201 | [ByteOrder::LITTLE_ENDIAN, "\x00\x00\x00\x80", -2147483648], 202 | [ByteOrder::LITTLE_ENDIAN, "\x00\x00\x00\x00", 0], 203 | [ByteOrder::LITTLE_ENDIAN, "\xff\xff\xff\x7f", 2147483647] 204 | ]; 205 | 206 | if (ByteOrder::LITTLE_ENDIAN === ByteOrderHelper::getMachineByteOrder()) { 207 | return array_merge($values, [ 208 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x80", -2147483648], 209 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00", 0], 210 | [ByteOrder::MACHINE_ENDIAN, "\xff\xff\xff\x7f", 2147483647] 211 | ]); 212 | } 213 | 214 | return array_merge($values, [ 215 | [ByteOrder::MACHINE_ENDIAN, "\x80\x00\x00\x00", -2147483648], 216 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00", 0], 217 | [ByteOrder::MACHINE_ENDIAN, "\x7f\xff\xff\xff", 2147483647] 218 | ]); 219 | } 220 | 221 | /** 222 | * Provide unsigned 32-bit integers 223 | * 224 | * @return array 225 | */ 226 | public function provideUInt32Values() 227 | { 228 | $values = [ 229 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x00\x00", 0], 230 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x00\x01", 1], 231 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x00\xff", 255], 232 | [ByteOrder::BIG_ENDIAN, "\xff\xff\xff\xff", 4294967295], 233 | [ByteOrder::LITTLE_ENDIAN, "\x00\x00\x00\x00", 0], 234 | [ByteOrder::LITTLE_ENDIAN, "\x01\x00\x00\x00", 1], 235 | [ByteOrder::LITTLE_ENDIAN, "\xff\x00\x00\x00", 255], 236 | [ByteOrder::LITTLE_ENDIAN, "\xff\xff\xff\xff", 4294967295] 237 | ]; 238 | 239 | if (ByteOrder::LITTLE_ENDIAN === ByteOrderHelper::getMachineByteOrder()) { 240 | return array_merge($values, [ 241 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00", 0], 242 | [ByteOrder::MACHINE_ENDIAN, "\x01\x00\x00\x00", 1], 243 | [ByteOrder::MACHINE_ENDIAN, "\xff\x00\x00\x00", 255], 244 | [ByteOrder::MACHINE_ENDIAN, "\xff\xff\xff\xff", 4294967295] 245 | ]); 246 | } 247 | 248 | return array_merge($values, [ 249 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00", 0], 250 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x01", 1], 251 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\xff", 255], 252 | [ByteOrder::MACHINE_ENDIAN, "\xff\xff\xff\xff", 4294967295] 253 | ]); 254 | } 255 | 256 | /** 257 | * Provide signed 48-bit integers 258 | * 259 | * @return array 260 | */ 261 | public function provideInt48Values() 262 | { 263 | $values = [ 264 | [ByteOrder::BIG_ENDIAN, "\x80\x00\x00\x00\x00\x00", -140737488355328], 265 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x00\x00\x00\x00", 0], 266 | [ByteOrder::BIG_ENDIAN, "\x7f\xff\xff\xff\xff\xff", 140737488355327], 267 | [ByteOrder::LITTLE_ENDIAN, "\x00\x00\x00\x00\x00\x80", -140737488355328], 268 | [ByteOrder::LITTLE_ENDIAN, "\x00\x00\x00\x00\x00\x00", 0], 269 | [ByteOrder::LITTLE_ENDIAN, "\xff\xff\xff\xff\xff\x7f", 140737488355327] 270 | ]; 271 | 272 | if (ByteOrder::LITTLE_ENDIAN === ByteOrderHelper::getMachineByteOrder()) { 273 | return array_merge($values, [ 274 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00\x00\x80", -140737488355328], 275 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00\x00\x00", 0], 276 | [ByteOrder::MACHINE_ENDIAN, "\xff\xff\xff\xff\xff\x7f", 140737488355327] 277 | ]); 278 | } 279 | 280 | return array_merge($values, [ 281 | [ByteOrder::MACHINE_ENDIAN, "\x80\x00\x00\x00\x00\x00", -140737488355328], 282 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00\x00\x00", 0], 283 | [ByteOrder::MACHINE_ENDIAN, "\x7f\xff\xff\xff\xff\xff", 140737488355327] 284 | ]); 285 | } 286 | 287 | /** 288 | * Provide unsigned 48-bit integers 289 | * 290 | * @return array 291 | */ 292 | public function provideUInt48Values() 293 | { 294 | $values = [ 295 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x00\x00\x00\x00", 0], 296 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x00\x00\x00\x01", 1], 297 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x00\x00\x00\xff", 255], 298 | [ByteOrder::BIG_ENDIAN, "\xff\xff\xff\xff\xff\xff", 281474976710655], 299 | [ByteOrder::LITTLE_ENDIAN, "\x00\x00\x00\x00\x00\x00", 0], 300 | [ByteOrder::LITTLE_ENDIAN, "\x01\x00\x00\x00\x00\x00", 1], 301 | [ByteOrder::LITTLE_ENDIAN, "\xff\x00\x00\x00\x00\x00", 255], 302 | [ByteOrder::LITTLE_ENDIAN, "\xff\xff\xff\xff\xff\xff", 281474976710655] 303 | ]; 304 | 305 | if (ByteOrder::LITTLE_ENDIAN === ByteOrderHelper::getMachineByteOrder()) { 306 | return array_merge($values, [ 307 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00\x00\x00", 0], 308 | [ByteOrder::MACHINE_ENDIAN, "\x01\x00\x00\x00\x00\x00", 1], 309 | [ByteOrder::MACHINE_ENDIAN, "\xff\x00\x00\x00\x00\x00", 255], 310 | [ByteOrder::MACHINE_ENDIAN, "\xff\xff\xff\xff\xff\xff", 281474976710655] 311 | ]); 312 | } 313 | 314 | return array_merge($values, [ 315 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00\x00\x00", 0], 316 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00\x00\x01", 1], 317 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00\x00\xff", 255], 318 | [ByteOrder::MACHINE_ENDIAN, "\xff\xff\xff\xff\xff\xff", 281474976710655] 319 | ]); 320 | } 321 | 322 | /** 323 | * Provide signed 64-bit integers 324 | * 325 | * @return array 326 | */ 327 | public function provideInt64Values() 328 | { 329 | $values = [ 330 | [ByteOrder::BIG_ENDIAN, "\x80\x00\x00\x00\x00\x00\x00\x01", -9223372036854775807], 331 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x00\x00\x00\x00\x00\x00", 0], 332 | [ByteOrder::BIG_ENDIAN, "\x7f\xff\xff\xff\xff\xff\xff\xff", 9223372036854775807], 333 | [ByteOrder::LITTLE_ENDIAN, "\x01\x00\x00\x00\x00\x00\x00\x80", -9223372036854775807], 334 | [ByteOrder::LITTLE_ENDIAN, "\x00\x00\x00\x00\x00\x00\x00\x00", 0], 335 | [ByteOrder::LITTLE_ENDIAN, "\xff\xff\xff\xff\xff\xff\xff\x7f", 9223372036854775807] 336 | ]; 337 | 338 | if (ByteOrder::LITTLE_ENDIAN === ByteOrderHelper::getMachineByteOrder()) { 339 | return array_merge($values, [ 340 | [ByteOrder::MACHINE_ENDIAN, "\x01\x00\x00\x00\x00\x00\x00\x80", -9223372036854775807], 341 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00\x00\x00\x00\x00", 0], 342 | [ByteOrder::MACHINE_ENDIAN, "\xff\xff\xff\xff\xff\xff\xff\x7f", 9223372036854775807] 343 | ]); 344 | } 345 | 346 | return array_merge($values, [ 347 | [ByteOrder::MACHINE_ENDIAN, "\x80\x00\x00\x00\x00\x00\x00\x01", -9223372036854775807], 348 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00\x00\x00\x00\x00", 0], 349 | [ByteOrder::MACHINE_ENDIAN, "\x7f\xff\xff\xff\xff\xff\xff\xff", 9223372036854775807] 350 | ]); 351 | } 352 | 353 | /** 354 | * Provide unsigned 64-bit integers 355 | * 356 | * @return array 357 | */ 358 | public function provideUInt64Values() 359 | { 360 | $values = [ 361 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x00\x00\x00\x00\x00\x00", 0], 362 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x00\x00\x00\x00\x00\x01", 1], 363 | [ByteOrder::BIG_ENDIAN, "\x00\x00\x00\x00\x00\x00\x00\xff", 255], 364 | [ByteOrder::BIG_ENDIAN, "\x7f\xff\xff\xff\xff\xff\xff\xff", 9223372036854775807], 365 | [ByteOrder::LITTLE_ENDIAN, "\x00\x00\x00\x00\x00\x00\x00\x00", 0], 366 | [ByteOrder::LITTLE_ENDIAN, "\x01\x00\x00\x00\x00\x00\x00\x00", 1], 367 | [ByteOrder::LITTLE_ENDIAN, "\xff\x00\x00\x00\x00\x00\x00\x00", 255], 368 | [ByteOrder::LITTLE_ENDIAN, "\xff\xff\xff\xff\xff\xff\xff\x7f", 9223372036854775807] 369 | ]; 370 | 371 | if (ByteOrder::LITTLE_ENDIAN === ByteOrderHelper::getMachineByteOrder()) { 372 | return array_merge($values, [ 373 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00\x00\x00\x00\x00", 0], 374 | [ByteOrder::MACHINE_ENDIAN, "\x01\x00\x00\x00\x00\x00\x00\x00", 1], 375 | [ByteOrder::MACHINE_ENDIAN, "\xff\x00\x00\x00\x00\x00\x00\x00", 255], 376 | [ByteOrder::MACHINE_ENDIAN, "\xff\xff\xff\xff\xff\xff\xff\x7f", 9223372036854775807] 377 | ]); 378 | } 379 | 380 | return array_merge($values, [ 381 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00\x00\x00\x00\x00", 0], 382 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00\x00\x00\x00\x01", 1], 383 | [ByteOrder::MACHINE_ENDIAN, "\x00\x00\x00\x00\x00\x00\x00\xff", 255], 384 | [ByteOrder::MACHINE_ENDIAN, "\x7f\xff\xff\xff\xff\xff\xff\xff", 9223372036854775807] 385 | ]); 386 | } 387 | 388 | /** 389 | * Test that the stream creation throws an exception on invalid resource argument 390 | * 391 | * @expectedException \GravityMedia\Stream\Exception\InvalidArgumentException 392 | * @expectedExceptionMessage Invalid resource 393 | */ 394 | public function testStreamCreationThrowsExceptionOnInvalidResourceArgument() 395 | { 396 | Stream::fromResource(null); 397 | } 398 | 399 | /** 400 | * Test that the an exception is thrown when trying to bind an invalid resources 401 | * 402 | * @expectedException \GravityMedia\Stream\Exception\InvalidArgumentException 403 | * @expectedExceptionMessage Invalid resource 404 | */ 405 | public function testBindingInvalidResourceThrowsException() 406 | { 407 | $resourceHelper = new ResourceHelper(); 408 | $resource = $resourceHelper->getResource(); 409 | 410 | $stream = Stream::fromResource($resource); 411 | 412 | $stream->bindResource(null); 413 | } 414 | 415 | /** 416 | * Test that the resource setter initializes the meta data 417 | */ 418 | public function testStreamCreationInitializesMetaData() 419 | { 420 | $resourceHelper = new ResourceHelper(); 421 | $resource = $resourceHelper->getResource(); 422 | 423 | $stream = Stream::fromResource($resource); 424 | 425 | $this->assertTrue($stream->isLocal()); 426 | $this->assertTrue($stream->isReadable()); 427 | $this->assertTrue($stream->isWritable()); 428 | $this->assertTrue($stream->isSeekable()); 429 | $this->assertEquals(ResourceHelper::RESOURCE_URI, $stream->getUri()); 430 | } 431 | 432 | /** 433 | * Test that the stream returns the default byte order 434 | */ 435 | public function testStreamReturnsDefaultByteOrder() 436 | { 437 | $resourceHelper = new ResourceHelper(); 438 | $resource = $resourceHelper->getResource(); 439 | 440 | $stream = Stream::fromResource($resource); 441 | 442 | $this->assertSame(ByteOrder::MACHINE_ENDIAN, $stream->getByteOrder()); 443 | } 444 | 445 | /** 446 | * Test that setting an invalid byte order throws an exception 447 | * 448 | * @expectedException \GravityMedia\Stream\Exception\InvalidArgumentException 449 | * @expectedExceptionMessage Invalid byte order 450 | */ 451 | public function testSettingInvalidByteOrderThrowsExceptions() 452 | { 453 | $resourceHelper = new ResourceHelper(); 454 | $resource = $resourceHelper->getResource(); 455 | 456 | $stream = Stream::fromResource($resource); 457 | $stream->setByteOrder(null); 458 | } 459 | 460 | /** 461 | * Thest that the byte order which was set is being returned 462 | */ 463 | public function testStreamReturnsByteOrderPreviouslySet() 464 | { 465 | $resourceHelper = new ResourceHelper(); 466 | $resource = $resourceHelper->getResource(); 467 | 468 | $stream = Stream::fromResource($resource); 469 | $stream->setByteOrder(ByteOrder::LITTLE_ENDIAN); 470 | 471 | $this->assertSame(ByteOrder::LITTLE_ENDIAN, $stream->getByteOrder()); 472 | } 473 | 474 | /** 475 | * Test that getting the size from a non-local stream throws an exception 476 | * 477 | * @expectedException \GravityMedia\Stream\Exception\BadMethodCallException 478 | * @expectedExceptionMessage Stream not local 479 | */ 480 | public function testGettingSizeThrowsExceptionOnNonLocalStream() 481 | { 482 | $streamMock = $this->getMockBuilder(Stream::class) 483 | ->setMethods(['isLocal']) 484 | ->getMock(); 485 | 486 | $streamMock->expects($this->once()) 487 | ->method('isLocal') 488 | ->will($this->returnValue(false)); 489 | 490 | /** @var \GravityMedia\Stream\Stream $streamMock */ 491 | $streamMock->getSize(); 492 | } 493 | 494 | /** 495 | * Test that getting the size from a closed stream throws an exception 496 | * 497 | * @expectedException \GravityMedia\Stream\Exception\IOException 498 | * @expectedExceptionMessage Invalid stream resource 499 | */ 500 | public function testGettingSizeThrowsExceptionOnClosedStream() 501 | { 502 | $resourceHelper = new ResourceHelper(); 503 | $resource = $resourceHelper->getResource(); 504 | 505 | $stream = Stream::fromResource($resource); 506 | $stream->close(); 507 | $stream->getSize(); 508 | } 509 | 510 | /** 511 | * Test that a stream returns the correct size 512 | */ 513 | public function testGettingSize() 514 | { 515 | $resourceHelper = new ResourceHelper(); 516 | $resource = $resourceHelper->getResource(); 517 | fwrite($resource, 'contents'); 518 | 519 | $stream = Stream::fromResource($resource); 520 | 521 | $this->assertEquals(8, $stream->getSize()); 522 | } 523 | 524 | /** 525 | * Test that checking for the end of stream throws an exception on closed stream 526 | * 527 | * @expectedException \GravityMedia\Stream\Exception\IOException 528 | * @expectedExceptionMessage Invalid stream resource 529 | */ 530 | public function testEndOfStreamThrowsExceptionOnClosedStream() 531 | { 532 | $resourceHelper = new ResourceHelper(); 533 | $resource = $resourceHelper->getResource(); 534 | 535 | $stream = Stream::fromResource($resource); 536 | $stream->close(); 537 | $stream->eof(); 538 | } 539 | 540 | /** 541 | * Test that the end of stream was reached 542 | */ 543 | public function testEndOfStream() 544 | { 545 | $resourceHelper = new ResourceHelper(); 546 | $resource = $resourceHelper->getResource(); 547 | fread($resource, 1); 548 | 549 | $stream = Stream::fromResource($resource); 550 | 551 | $this->assertTrue($stream->eof()); 552 | } 553 | 554 | /** 555 | * Test that locating the position on a closed stream throws an exception 556 | * 557 | * @expectedException \GravityMedia\Stream\Exception\IOException 558 | * @expectedExceptionMessage Invalid stream resource 559 | */ 560 | public function testLocatingPositionThrowsExceptionOnClosedStream() 561 | { 562 | $resourceHelper = new ResourceHelper(); 563 | $resource = $resourceHelper->getResource(); 564 | 565 | $stream = Stream::fromResource($resource); 566 | $stream->close(); 567 | $stream->tell(); 568 | } 569 | 570 | /** 571 | * Test that the position of the stream can be located 572 | */ 573 | public function testLocatingPosition() 574 | { 575 | $resourceHelper = new ResourceHelper(); 576 | $resource = $resourceHelper->getResource(); 577 | fwrite($resource, 'contents'); 578 | 579 | $stream = Stream::fromResource($resource); 580 | $stream->seek(4); 581 | 582 | $this->assertEquals(4, $stream->tell()); 583 | } 584 | 585 | /** 586 | * Test that seeking on a non-seekable stream throws an exception 587 | * 588 | * @expectedException \GravityMedia\Stream\Exception\BadMethodCallException 589 | * @expectedExceptionMessage Stream not seekable 590 | */ 591 | public function testSeekingPositionThrowsExceptionOnNonSeekableStream() 592 | { 593 | $streamMock = $this->getMockBuilder(Stream::class) 594 | ->setMethods(['isSeekable']) 595 | ->getMock(); 596 | 597 | $streamMock->expects($this->once()) 598 | ->method('isSeekable') 599 | ->will($this->returnValue(false)); 600 | 601 | /** @var \GravityMedia\Stream\Stream $streamMock */ 602 | $streamMock->seek(0); 603 | } 604 | 605 | /** 606 | * Test that seeking on a closed stream throws an exception 607 | * 608 | * @expectedException \GravityMedia\Stream\Exception\IOException 609 | * @expectedExceptionMessage Invalid stream resource 610 | */ 611 | public function testSeekingPositionThrowsExceptionOnClosedStream() 612 | { 613 | $resourceHelper = new ResourceHelper(); 614 | $resource = $resourceHelper->getResource(); 615 | 616 | $stream = Stream::fromResource($resource); 617 | $stream->close(); 618 | $stream->seek(0); 619 | } 620 | 621 | /** 622 | * Test that seeking on a stream throws an exception when trying to seek with an invalid offset 623 | * 624 | * @expectedException \GravityMedia\Stream\Exception\IOException 625 | * @expectedExceptionMessage Unexpected result of operation 626 | */ 627 | public function testSeekingPositionThrowsExceptionOnInvalidOffset() 628 | { 629 | $resourceHelper = new ResourceHelper(); 630 | $resource = $resourceHelper->getResource(); 631 | 632 | $stream = Stream::fromResource($resource); 633 | $stream->seek(-1); 634 | } 635 | 636 | /** 637 | * Test that seeking the stream returns correct position 638 | */ 639 | public function testSeekingPosition() 640 | { 641 | $resourceHelper = new ResourceHelper(); 642 | $resource = $resourceHelper->getResource(); 643 | fwrite($resource, 'contents'); 644 | 645 | $stream = Stream::fromResource($resource); 646 | 647 | $this->assertEquals(0, $stream->seek(-8, SEEK_END)); 648 | } 649 | 650 | /** 651 | * Test that rewinding the stream returns correct position 652 | */ 653 | public function testRewindPosition() 654 | { 655 | $resourceHelper = new ResourceHelper(); 656 | $resource = $resourceHelper->getResource(); 657 | fwrite($resource, 'contents'); 658 | 659 | $stream = Stream::fromResource($resource); 660 | 661 | $this->assertEquals(0, $stream->rewind()); 662 | } 663 | 664 | /** 665 | * Test that reading data from a closed stream throws an exception 666 | * 667 | * @expectedException \GravityMedia\Stream\Exception\IOException 668 | * @expectedExceptionMessage Invalid stream resource 669 | */ 670 | public function testReadingDataThrowsExceptionOnClosedStream() 671 | { 672 | $resourceHelper = new ResourceHelper(); 673 | $resource = $resourceHelper->getResource(); 674 | 675 | $stream = Stream::fromResource($resource); 676 | $stream->close(); 677 | $stream->read(1); 678 | } 679 | 680 | /** 681 | * Test that reading data from a non-readable stream throws an exception 682 | * 683 | * @expectedException \GravityMedia\Stream\Exception\BadMethodCallException 684 | * @expectedExceptionMessage Stream not readable 685 | */ 686 | public function testReadingDataThrowsExceptionOnNonReadableStream() 687 | { 688 | $streamMock = $this->getMockBuilder(Stream::class) 689 | ->setMethods(['isReadable']) 690 | ->getMock(); 691 | 692 | $streamMock->expects($this->once()) 693 | ->method('isReadable') 694 | ->will($this->returnValue(false)); 695 | 696 | /** @var \GravityMedia\Stream\Stream $streamMock */ 697 | $streamMock->read(1); 698 | } 699 | 700 | /** 701 | * Test that reading data from an empty stream throws an exception 702 | * 703 | * @expectedException \GravityMedia\Stream\Exception\IOException 704 | * @expectedExceptionMessage Unexpected result of operation 705 | */ 706 | public function testReadingDataThrowsExceptionOnInvalidLength() 707 | { 708 | $resourceHelper = new ResourceHelper(); 709 | $resource = $resourceHelper->getResource(); 710 | 711 | $stream = Stream::fromResource($resource); 712 | $stream->read(0); 713 | } 714 | 715 | /** 716 | * Test that the data can be read 717 | */ 718 | public function testReadingData() 719 | { 720 | $resourceHelper = new ResourceHelper(); 721 | $resource = $resourceHelper->getResource(); 722 | fwrite($resource, 'contents'); 723 | fseek($resource, 0); 724 | 725 | $stream = Stream::fromResource($resource); 726 | 727 | $this->assertSame('contents', $stream->read(8)); 728 | } 729 | 730 | /** 731 | * Test reading signed 8-bit character 732 | * 733 | * @dataProvider provideInt8Values() 734 | * 735 | * @param string $data 736 | * @param int $value 737 | */ 738 | public function testReadingInt8($data, $value) 739 | { 740 | $streamMock = $this->getMockBuilder(Stream::class) 741 | ->disableOriginalConstructor() 742 | ->setMethods(['read']) 743 | ->getMock(); 744 | 745 | $streamMock->expects($this->once()) 746 | ->method('read') 747 | ->with(1) 748 | ->will($this->returnValue($data)); 749 | 750 | /** @var \GravityMedia\Stream\Stream $streamMock */ 751 | $this->assertSame($value, $streamMock->readInt8()); 752 | } 753 | 754 | /** 755 | * Test reading unsigned 8-bit character 756 | * 757 | * @dataProvider provideUInt8Values() 758 | * 759 | * @param string $data 760 | * @param int $value 761 | */ 762 | public function testReadingUInt8($data, $value) 763 | { 764 | $streamMock = $this->getMockBuilder(Stream::class) 765 | ->disableOriginalConstructor() 766 | ->setMethods(['read']) 767 | ->getMock(); 768 | 769 | $streamMock->expects($this->once()) 770 | ->method('read') 771 | ->with(1) 772 | ->will($this->returnValue($data)); 773 | 774 | /** @var \GravityMedia\Stream\Stream $streamMock */ 775 | $this->assertSame($value, $streamMock->readUInt8()); 776 | } 777 | 778 | /** 779 | * Test reading signed 16-bit integer 780 | * 781 | * @dataProvider provideInt16Values() 782 | * 783 | * @param int $byteOrder 784 | * @param string $data 785 | * @param int $value 786 | */ 787 | public function testReadingInt16($byteOrder, $data, $value) 788 | { 789 | $readerMock = $this->getMockBuilder(Stream::class) 790 | ->disableOriginalConstructor() 791 | ->setMethods(['getByteOrder', 'read']) 792 | ->getMock(); 793 | 794 | $readerMock->expects($this->atLeast(1)) 795 | ->method('getByteOrder') 796 | ->will($this->returnValue($byteOrder)); 797 | 798 | $readerMock->expects($this->once()) 799 | ->method('read') 800 | ->with(2) 801 | ->will($this->returnValue($data)); 802 | 803 | /** @var \GravityMedia\Stream\Stream $readerMock */ 804 | $this->assertSame($value, $readerMock->readInt16()); 805 | } 806 | 807 | /** 808 | * Test reading unsigned 16-bit integer 809 | * 810 | * @dataProvider provideUInt16Values() 811 | * 812 | * @param int $byteOrder 813 | * @param string $data 814 | * @param int $value 815 | */ 816 | public function testReadingUInt16($byteOrder, $data, $value) 817 | { 818 | $readerMock = $this->getMockBuilder(Stream::class) 819 | ->disableOriginalConstructor() 820 | ->setMethods(['getByteOrder', 'read']) 821 | ->getMock(); 822 | 823 | $readerMock->expects($this->atLeast(1)) 824 | ->method('getByteOrder') 825 | ->will($this->returnValue($byteOrder)); 826 | 827 | $readerMock->expects($this->once()) 828 | ->method('read') 829 | ->with(2) 830 | ->will($this->returnValue($data)); 831 | 832 | /** @var \GravityMedia\Stream\Stream $readerMock */ 833 | $this->assertSame($value, $readerMock->readUInt16()); 834 | } 835 | 836 | /** 837 | * Test reading signed 24-bit integer 838 | * 839 | * @dataProvider provideInt24Values() 840 | * 841 | * @param int $byteOrder 842 | * @param string $data 843 | * @param int $value 844 | */ 845 | public function testReadingInt24($byteOrder, $data, $value) 846 | { 847 | $readerMock = $this->getMockBuilder(Stream::class) 848 | ->disableOriginalConstructor() 849 | ->setMethods(['getByteOrder', 'read']) 850 | ->getMock(); 851 | 852 | $readerMock->expects($this->atLeast(1)) 853 | ->method('getByteOrder') 854 | ->will($this->returnValue($byteOrder)); 855 | 856 | $readerMock->expects($this->once()) 857 | ->method('read') 858 | ->with(3) 859 | ->will($this->returnValue($data)); 860 | 861 | /** @var \GravityMedia\Stream\Stream $readerMock */ 862 | $this->assertSame($value, $readerMock->readInt24()); 863 | } 864 | 865 | /** 866 | * Test reading unsigned 24-bit integer 867 | * 868 | * @dataProvider provideUInt24Values() 869 | * 870 | * @param int $byteOrder 871 | * @param string $data 872 | * @param int $value 873 | */ 874 | public function testReadingUInt24($byteOrder, $data, $value) 875 | { 876 | $readerMock = $this->getMockBuilder(Stream::class) 877 | ->disableOriginalConstructor() 878 | ->setMethods(['getByteOrder', 'read']) 879 | ->getMock(); 880 | 881 | $readerMock->expects($this->atLeast(1)) 882 | ->method('getByteOrder') 883 | ->will($this->returnValue($byteOrder)); 884 | 885 | $readerMock->expects($this->once()) 886 | ->method('read') 887 | ->with(3) 888 | ->will($this->returnValue($data)); 889 | 890 | /** @var \GravityMedia\Stream\Stream $readerMock */ 891 | $this->assertSame($value, $readerMock->readUInt24()); 892 | } 893 | 894 | /** 895 | * Test reading signed 32-bit integer 896 | * 897 | * @dataProvider provideInt32Values() 898 | * 899 | * @param int $byteOrder 900 | * @param string $data 901 | * @param int $value 902 | */ 903 | public function testReadingInt32($byteOrder, $data, $value) 904 | { 905 | $readerMock = $this->getMockBuilder(Stream::class) 906 | ->disableOriginalConstructor() 907 | ->setMethods(['getByteOrder', 'read']) 908 | ->getMock(); 909 | 910 | $readerMock->expects($this->atLeast(1)) 911 | ->method('getByteOrder') 912 | ->will($this->returnValue($byteOrder)); 913 | 914 | $readerMock->expects($this->once()) 915 | ->method('read') 916 | ->with(4) 917 | ->will($this->returnValue($data)); 918 | 919 | /** @var \GravityMedia\Stream\Stream $readerMock */ 920 | $this->assertSame($value, $readerMock->readInt32()); 921 | } 922 | 923 | /** 924 | * Test reading unsigned 32-bit integer 925 | * 926 | * @dataProvider provideUInt32Values() 927 | * 928 | * @param int $byteOrder 929 | * @param string $data 930 | * @param int $value 931 | */ 932 | public function testReadingUInt32($byteOrder, $data, $value) 933 | { 934 | $readerMock = $this->getMockBuilder(Stream::class) 935 | ->disableOriginalConstructor() 936 | ->setMethods(['getByteOrder', 'read']) 937 | ->getMock(); 938 | 939 | $readerMock->expects($this->atLeast(1)) 940 | ->method('getByteOrder') 941 | ->will($this->returnValue($byteOrder)); 942 | 943 | $readerMock->expects($this->once()) 944 | ->method('read') 945 | ->with(4) 946 | ->will($this->returnValue($data)); 947 | 948 | /** @var \GravityMedia\Stream\Stream $readerMock */ 949 | $this->assertSame($value, $readerMock->readUInt32()); 950 | } 951 | 952 | /** 953 | * Test reading signed 48-bit integer 954 | * 955 | * @dataProvider provideInt48Values() 956 | * 957 | * @param int $byteOrder 958 | * @param string $data 959 | * @param int $value 960 | */ 961 | public function testReadingInt48($byteOrder, $data, $value) 962 | { 963 | $readerMock = $this->getMockBuilder(Stream::class) 964 | ->disableOriginalConstructor() 965 | ->setMethods(['getByteOrder', 'read']) 966 | ->getMock(); 967 | 968 | $readerMock->expects($this->atLeast(1)) 969 | ->method('getByteOrder') 970 | ->will($this->returnValue($byteOrder)); 971 | 972 | $readerMock->expects($this->once()) 973 | ->method('read') 974 | ->with(6) 975 | ->will($this->returnValue($data)); 976 | 977 | /** @var \GravityMedia\Stream\Stream $readerMock */ 978 | $this->assertSame($value, $readerMock->readInt48()); 979 | } 980 | 981 | /** 982 | * Test reading unsigned 48-bit integer 983 | * 984 | * @dataProvider provideUInt48Values() 985 | * 986 | * @param int $byteOrder 987 | * @param string $data 988 | * @param int $value 989 | */ 990 | public function testReadingUInt48($byteOrder, $data, $value) 991 | { 992 | $readerMock = $this->getMockBuilder(Stream::class) 993 | ->disableOriginalConstructor() 994 | ->setMethods(['getByteOrder', 'read']) 995 | ->getMock(); 996 | 997 | $readerMock->expects($this->atLeast(1)) 998 | ->method('getByteOrder') 999 | ->will($this->returnValue($byteOrder)); 1000 | 1001 | $readerMock->expects($this->once()) 1002 | ->method('read') 1003 | ->with(6) 1004 | ->will($this->returnValue($data)); 1005 | 1006 | /** @var \GravityMedia\Stream\Stream $readerMock */ 1007 | $this->assertSame($value, $readerMock->readUInt48()); 1008 | } 1009 | 1010 | /** 1011 | * Test reading signed 64-bit integer 1012 | * 1013 | * @dataProvider provideInt64Values() 1014 | * 1015 | * @param int $byteOrder 1016 | * @param string $data 1017 | * @param int $value 1018 | */ 1019 | public function testReadingInt64($byteOrder, $data, $value) 1020 | { 1021 | $readerMock = $this->getMockBuilder(Stream::class) 1022 | ->disableOriginalConstructor() 1023 | ->setMethods(['getByteOrder', 'read']) 1024 | ->getMock(); 1025 | 1026 | $readerMock->expects($this->atLeast(1)) 1027 | ->method('getByteOrder') 1028 | ->will($this->returnValue($byteOrder)); 1029 | 1030 | $readerMock->expects($this->once()) 1031 | ->method('read') 1032 | ->with(8) 1033 | ->will($this->returnValue($data)); 1034 | 1035 | /** @var \GravityMedia\Stream\Stream $readerMock */ 1036 | $this->assertSame($value, $readerMock->readInt64()); 1037 | } 1038 | 1039 | /** 1040 | * Test reading unsigned 64-bit integer 1041 | * 1042 | * @dataProvider provideUInt64Values() 1043 | * 1044 | * @param int $byteOrder 1045 | * @param string $data 1046 | * @param int $value 1047 | */ 1048 | public function testReadingUInt64($byteOrder, $data, $value) 1049 | { 1050 | $readerMock = $this->getMockBuilder(Stream::class) 1051 | ->disableOriginalConstructor() 1052 | ->setMethods(['getByteOrder', 'read']) 1053 | ->getMock(); 1054 | 1055 | $readerMock->expects($this->atLeast(1)) 1056 | ->method('getByteOrder') 1057 | ->will($this->returnValue($byteOrder)); 1058 | 1059 | $readerMock->expects($this->once()) 1060 | ->method('read') 1061 | ->with(8) 1062 | ->will($this->returnValue($data)); 1063 | 1064 | /** @var \GravityMedia\Stream\Stream $readerMock */ 1065 | $this->assertSame($value, $readerMock->readUInt64()); 1066 | } 1067 | 1068 | /** 1069 | * Test that writing data to a closed stream throws an exception 1070 | * 1071 | * @expectedException \GravityMedia\Stream\Exception\IOException 1072 | * @expectedExceptionMessage Invalid stream resource 1073 | */ 1074 | public function testWritingDataThrowsExceptionOnClosedStream() 1075 | { 1076 | $resourceHelper = new ResourceHelper(); 1077 | $resource = $resourceHelper->getResource(); 1078 | 1079 | $stream = Stream::fromResource($resource); 1080 | $stream->close(); 1081 | $stream->write('contents'); 1082 | } 1083 | 1084 | /** 1085 | * Test that writing data to a non-writable stream throws an exception 1086 | * 1087 | * @expectedException \GravityMedia\Stream\Exception\BadMethodCallException 1088 | * @expectedExceptionMessage Stream not writable 1089 | */ 1090 | public function testWritingDataThrowsExceptionOnNonWritableStream() 1091 | { 1092 | $streamMock = $this->getMockBuilder(Stream::class) 1093 | ->setMethods(['isWritable']) 1094 | ->getMock(); 1095 | 1096 | $streamMock->expects($this->once()) 1097 | ->method('isWritable') 1098 | ->will($this->returnValue(false)); 1099 | 1100 | /** @var \GravityMedia\Stream\Stream $streamMock */ 1101 | $streamMock->write('contents'); 1102 | } 1103 | 1104 | /** 1105 | * Test that writing invalid data to a stream throws an exception 1106 | * 1107 | * @expectedException \GravityMedia\Stream\Exception\IOException 1108 | * @expectedExceptionMessage Unexpected result of operation 1109 | */ 1110 | public function testWritingDataThrowsExceptionOnInvalidData() 1111 | { 1112 | $resourceHelper = new ResourceHelper(); 1113 | $resource = $resourceHelper->getResource(); 1114 | 1115 | $stream = Stream::fromResource($resource); 1116 | $stream->write(new \stdClass()); 1117 | } 1118 | 1119 | /** 1120 | * Test that the data can be written and the length is returned 1121 | */ 1122 | public function testWritingData() 1123 | { 1124 | $resourceHelper = new ResourceHelper(); 1125 | $resource = $resourceHelper->getResource(); 1126 | 1127 | $stream = Stream::fromResource($resource); 1128 | 1129 | $this->assertEquals(8, $stream->write('contents')); 1130 | } 1131 | 1132 | /** 1133 | * Test writing signed 8-bit character 1134 | * 1135 | * @dataProvider provideInt8Values() 1136 | * 1137 | * @param string $data 1138 | * @param int $value 1139 | */ 1140 | public function testWritingInt8($data, $value) 1141 | { 1142 | $streamMock = $this->getMockBuilder(Stream::class) 1143 | ->disableOriginalConstructor() 1144 | ->setMethods(['write']) 1145 | ->getMock(); 1146 | 1147 | $streamMock->expects($this->once()) 1148 | ->method('write') 1149 | ->with($data) 1150 | ->will($this->returnValue(1)); 1151 | 1152 | /** @var \GravityMedia\Stream\Stream $streamMock */ 1153 | $this->assertSame(1, $streamMock->writeInt8($value)); 1154 | } 1155 | 1156 | /** 1157 | * Test writing unsigned 8-bit character 1158 | * 1159 | * @dataProvider provideUInt8Values() 1160 | * 1161 | * @param string $data 1162 | * @param int $value 1163 | */ 1164 | public function testWritingUInt8($data, $value) 1165 | { 1166 | $streamMock = $this->getMockBuilder(Stream::class) 1167 | ->disableOriginalConstructor() 1168 | ->setMethods(['write']) 1169 | ->getMock(); 1170 | 1171 | $streamMock->expects($this->once()) 1172 | ->method('write') 1173 | ->with($data) 1174 | ->will($this->returnValue(1)); 1175 | 1176 | /** @var \GravityMedia\Stream\Stream $streamMock */ 1177 | $this->assertSame(1, $streamMock->writeUInt8($value)); 1178 | } 1179 | 1180 | /** 1181 | * Test writing signed 16-bit integer 1182 | * 1183 | * @dataProvider provideInt16Values() 1184 | * 1185 | * @param int $byteOrder 1186 | * @param string $data 1187 | * @param int $value 1188 | */ 1189 | public function testWritingInt16($byteOrder, $data, $value) 1190 | { 1191 | $streamMock = $this->getMockBuilder(Stream::class) 1192 | ->disableOriginalConstructor() 1193 | ->setMethods(['getByteOrder', 'write']) 1194 | ->getMock(); 1195 | 1196 | $streamMock->expects($this->atLeast(1)) 1197 | ->method('getByteOrder') 1198 | ->will($this->returnValue($byteOrder)); 1199 | 1200 | $streamMock->expects($this->once()) 1201 | ->method('write') 1202 | ->with($data) 1203 | ->will($this->returnValue(2)); 1204 | 1205 | /** @var \GravityMedia\Stream\Stream $streamMock */ 1206 | $this->assertSame(2, $streamMock->writeInt16($value)); 1207 | } 1208 | 1209 | /** 1210 | * Test writing unsigned 16-bit integer 1211 | * 1212 | * @dataProvider provideUInt16Values() 1213 | * 1214 | * @param int $byteOrder 1215 | * @param string $data 1216 | * @param int $value 1217 | */ 1218 | public function testWritingUInt16($byteOrder, $data, $value) 1219 | { 1220 | $streamMock = $this->getMockBuilder(Stream::class) 1221 | ->disableOriginalConstructor() 1222 | ->setMethods(['getByteOrder', 'write']) 1223 | ->getMock(); 1224 | 1225 | $streamMock->expects($this->atLeast(1)) 1226 | ->method('getByteOrder') 1227 | ->will($this->returnValue($byteOrder)); 1228 | 1229 | $streamMock->expects($this->once()) 1230 | ->method('write') 1231 | ->with($data) 1232 | ->will($this->returnValue(2)); 1233 | 1234 | /** @var \GravityMedia\Stream\Stream $streamMock */ 1235 | $this->assertSame(2, $streamMock->writeUInt16($value)); 1236 | } 1237 | 1238 | /** 1239 | * Test writing signed 24-bit integer 1240 | * 1241 | * @dataProvider provideInt24Values() 1242 | * 1243 | * @param int $byteOrder 1244 | * @param string $data 1245 | * @param int $value 1246 | */ 1247 | public function testWritingInt24($byteOrder, $data, $value) 1248 | { 1249 | $streamMock = $this->getMockBuilder(Stream::class) 1250 | ->disableOriginalConstructor() 1251 | ->setMethods(['getByteOrder', 'write']) 1252 | ->getMock(); 1253 | 1254 | $streamMock->expects($this->atLeast(1)) 1255 | ->method('getByteOrder') 1256 | ->will($this->returnValue($byteOrder)); 1257 | 1258 | $streamMock->expects($this->once()) 1259 | ->method('write') 1260 | ->with($data) 1261 | ->will($this->returnValue(3)); 1262 | 1263 | /** @var \GravityMedia\Stream\Stream $streamMock */ 1264 | $this->assertSame(3, $streamMock->writeInt24($value)); 1265 | } 1266 | 1267 | /** 1268 | * Test writing unsigned 24-bit integer 1269 | * 1270 | * @dataProvider provideUInt24Values() 1271 | * 1272 | * @param int $byteOrder 1273 | * @param string $data 1274 | * @param int $value 1275 | */ 1276 | public function testWritingUInt24($byteOrder, $data, $value) 1277 | { 1278 | $streamMock = $this->getMockBuilder(Stream::class) 1279 | ->disableOriginalConstructor() 1280 | ->setMethods(['getByteOrder', 'write']) 1281 | ->getMock(); 1282 | 1283 | $streamMock->expects($this->atLeast(1)) 1284 | ->method('getByteOrder') 1285 | ->will($this->returnValue($byteOrder)); 1286 | 1287 | $streamMock->expects($this->once()) 1288 | ->method('write') 1289 | ->with($data) 1290 | ->will($this->returnValue(3)); 1291 | 1292 | /** @var \GravityMedia\Stream\Stream $streamMock */ 1293 | $this->assertSame(3, $streamMock->writeUInt24($value)); 1294 | } 1295 | 1296 | /** 1297 | * Test writing signed 32-bit integer 1298 | * 1299 | * @dataProvider provideInt32Values() 1300 | * 1301 | * @param int $byteOrder 1302 | * @param string $data 1303 | * @param int $value 1304 | */ 1305 | public function testWritingInt32($byteOrder, $data, $value) 1306 | { 1307 | $streamMock = $this->getMockBuilder(Stream::class) 1308 | ->disableOriginalConstructor() 1309 | ->setMethods(['getByteOrder', 'write']) 1310 | ->getMock(); 1311 | 1312 | $streamMock->expects($this->atLeast(1)) 1313 | ->method('getByteOrder') 1314 | ->will($this->returnValue($byteOrder)); 1315 | 1316 | $streamMock->expects($this->once()) 1317 | ->method('write') 1318 | ->with($data) 1319 | ->will($this->returnValue(4)); 1320 | 1321 | /** @var \GravityMedia\Stream\Stream $streamMock */ 1322 | $this->assertSame(4, $streamMock->writeInt32($value)); 1323 | } 1324 | 1325 | /** 1326 | * Test writing unsigned 32-bit integer 1327 | * 1328 | * @dataProvider provideUInt32Values() 1329 | * 1330 | * @param int $byteOrder 1331 | * @param string $data 1332 | * @param int $value 1333 | */ 1334 | public function testWritingUInt32($byteOrder, $data, $value) 1335 | { 1336 | $streamMock = $this->getMockBuilder(Stream::class) 1337 | ->disableOriginalConstructor() 1338 | ->setMethods(['getByteOrder', 'write']) 1339 | ->getMock(); 1340 | 1341 | $streamMock->expects($this->atLeast(1)) 1342 | ->method('getByteOrder') 1343 | ->will($this->returnValue($byteOrder)); 1344 | 1345 | $streamMock->expects($this->once()) 1346 | ->method('write') 1347 | ->with($data) 1348 | ->will($this->returnValue(4)); 1349 | 1350 | /** @var \GravityMedia\Stream\Stream $streamMock */ 1351 | $this->assertSame(4, $streamMock->writeUInt32($value)); 1352 | } 1353 | 1354 | /** 1355 | * Test writing signed 48-bit integer 1356 | * 1357 | * @dataProvider provideInt48Values() 1358 | * 1359 | * @param int $byteOrder 1360 | * @param string $data 1361 | * @param int $value 1362 | */ 1363 | public function testWritingInt48($byteOrder, $data, $value) 1364 | { 1365 | $streamMock = $this->getMockBuilder(Stream::class) 1366 | ->disableOriginalConstructor() 1367 | ->setMethods(['getByteOrder', 'write']) 1368 | ->getMock(); 1369 | 1370 | $streamMock->expects($this->atLeast(1)) 1371 | ->method('getByteOrder') 1372 | ->will($this->returnValue($byteOrder)); 1373 | 1374 | $streamMock->expects($this->once()) 1375 | ->method('write') 1376 | ->with($data) 1377 | ->will($this->returnValue(6)); 1378 | 1379 | /** @var \GravityMedia\Stream\Stream $streamMock */ 1380 | $this->assertSame(6, $streamMock->writeInt48($value)); 1381 | } 1382 | 1383 | /** 1384 | * Test writing unsigned 48-bit integer 1385 | * 1386 | * @dataProvider provideUInt48Values() 1387 | * 1388 | * @param int $byteOrder 1389 | * @param string $data 1390 | * @param int $value 1391 | */ 1392 | public function testWritingUInt48($byteOrder, $data, $value) 1393 | { 1394 | $streamMock = $this->getMockBuilder(Stream::class) 1395 | ->disableOriginalConstructor() 1396 | ->setMethods(['getByteOrder', 'write']) 1397 | ->getMock(); 1398 | 1399 | $streamMock->expects($this->atLeast(1)) 1400 | ->method('getByteOrder') 1401 | ->will($this->returnValue($byteOrder)); 1402 | 1403 | $streamMock->expects($this->once()) 1404 | ->method('write') 1405 | ->with($data) 1406 | ->will($this->returnValue(6)); 1407 | 1408 | /** @var \GravityMedia\Stream\Stream $streamMock */ 1409 | $this->assertSame(6, $streamMock->writeUInt48($value)); 1410 | } 1411 | 1412 | /** 1413 | * Test writing signed 64-bit integer 1414 | * 1415 | * @dataProvider provideInt64Values() 1416 | * 1417 | * @param int $byteOrder 1418 | * @param string $data 1419 | * @param int $value 1420 | */ 1421 | public function testWritingInt64($byteOrder, $data, $value) 1422 | { 1423 | $streamMock = $this->getMockBuilder(Stream::class) 1424 | ->disableOriginalConstructor() 1425 | ->setMethods(['getByteOrder', 'write']) 1426 | ->getMock(); 1427 | 1428 | $streamMock->expects($this->atLeast(1)) 1429 | ->method('getByteOrder') 1430 | ->will($this->returnValue($byteOrder)); 1431 | 1432 | $streamMock->expects($this->once()) 1433 | ->method('write') 1434 | ->with($data) 1435 | ->will($this->returnValue(8)); 1436 | 1437 | /** @var \GravityMedia\Stream\Stream $streamMock */ 1438 | $this->assertSame(8, $streamMock->writeInt64($value)); 1439 | } 1440 | 1441 | /** 1442 | * Test writing unsigned 64-bit integer 1443 | * 1444 | * @dataProvider provideUInt64Values() 1445 | * 1446 | * @param int $byteOrder 1447 | * @param string $data 1448 | * @param int $value 1449 | */ 1450 | public function testWritingUInt64($byteOrder, $data, $value) 1451 | { 1452 | $streamMock = $this->getMockBuilder(Stream::class) 1453 | ->disableOriginalConstructor() 1454 | ->setMethods(['getByteOrder', 'write']) 1455 | ->getMock(); 1456 | 1457 | $streamMock->expects($this->atLeast(1)) 1458 | ->method('getByteOrder') 1459 | ->will($this->returnValue($byteOrder)); 1460 | 1461 | $streamMock->expects($this->once()) 1462 | ->method('write') 1463 | ->with($data) 1464 | ->will($this->returnValue(8)); 1465 | 1466 | /** @var \GravityMedia\Stream\Stream $streamMock */ 1467 | $this->assertSame(8, $streamMock->writeUInt64($value)); 1468 | } 1469 | 1470 | /** 1471 | * Test that truncating a closed stream throws an exception 1472 | * 1473 | * @expectedException \GravityMedia\Stream\Exception\IOException 1474 | * @expectedExceptionMessage Invalid stream resource 1475 | */ 1476 | public function testTruncatingThrowsExceptionOnClosedStream() 1477 | { 1478 | $resourceHelper = new ResourceHelper(); 1479 | $resource = $resourceHelper->getResource(); 1480 | 1481 | $stream = Stream::fromResource($resource); 1482 | $stream->close(); 1483 | $stream->truncate(0); 1484 | } 1485 | 1486 | /** 1487 | * Test that truncating a non-writable stream throws an exception 1488 | * 1489 | * @expectedException \GravityMedia\Stream\Exception\BadMethodCallException 1490 | * @expectedExceptionMessage Stream not writable 1491 | */ 1492 | public function testTruncatingThrowsExceptionOnNonWritableStream() 1493 | { 1494 | $streamMock = $this->getMockBuilder(Stream::class) 1495 | ->setMethods(['isWritable']) 1496 | ->getMock(); 1497 | 1498 | $streamMock->expects($this->once()) 1499 | ->method('isWritable') 1500 | ->will($this->returnValue(false)); 1501 | 1502 | /** @var \GravityMedia\Stream\Stream $streamMock */ 1503 | $streamMock->truncate(0); 1504 | } 1505 | 1506 | /** 1507 | * Test that the stream can be truncated 1508 | */ 1509 | public function testTruncating() 1510 | { 1511 | $resourceHelper = new ResourceHelper(); 1512 | $resource = $resourceHelper->getResource(); 1513 | 1514 | $stream = Stream::fromResource($resource); 1515 | 1516 | $this->assertTrue($stream->truncate(8)); 1517 | $this->assertEquals("\x00\x00\x00\x00\x00\x00\x00\x00", stream_get_contents($resource)); 1518 | } 1519 | 1520 | /** 1521 | * Test that closing the stream closes the stream resource 1522 | */ 1523 | public function testCloseStreamResource() 1524 | { 1525 | $resourceHelper = new ResourceHelper(); 1526 | $resource = $resourceHelper->getResource(); 1527 | 1528 | $stream = Stream::fromResource($resource); 1529 | 1530 | $this->assertTrue($stream->close()); 1531 | $this->assertFalse(is_resource($resource)); 1532 | } 1533 | } 1534 | --------------------------------------------------------------------------------