From 9010085c4a03822f5782d633cad471735b67d1e1 Mon Sep 17 00:00:00 2001 From: Jack'lul Date: Wed, 21 Feb 2018 19:55:20 +0100 Subject: [PATCH] Initial commit --- .gitignore | 8 + .travis.yml | 34 + LICENSE | 21 + README.md | 117 +++ composer.json | 44 + composer.lock | 1757 ++++++++++++++++++++++++++++++++ phpcs.xml.dist | 8 + phpunit.xml.dist | 17 + src/E621.php | 899 ++++++++++++++++ src/Entity/Artist.php | 18 + src/Entity/Blip.php | 18 + src/Entity/Comment.php | 18 + src/Entity/Dmail.php | 18 + src/Entity/Entity.php | 60 ++ src/Entity/Forum.php | 18 + src/Entity/Generic.php | 18 + src/Entity/Note.php | 18 + src/Entity/Pool.php | 18 + src/Entity/PoolPost.php | 18 + src/Entity/Post.php | 59 ++ src/Entity/PostFlagHistory.php | 18 + src/Entity/PostMd5.php | 22 + src/Entity/PostTagHistory.php | 18 + src/Entity/Response.php | 74 ++ src/Entity/Set.php | 18 + src/Entity/SetMaintainer.php | 18 + src/Entity/SetPost.php | 18 + src/Entity/Tag.php | 45 + src/Entity/TagAlias.php | 18 + src/Entity/TagImplication.php | 18 + src/Entity/Ticket.php | 18 + src/Entity/User.php | 18 + src/Entity/UserRecord.php | 18 + src/Entity/Wiki.php | 18 + tests/E621Test.php | 74 ++ 35 files changed, 3599 insertions(+) create mode 100644 .gitignore create mode 100644 .travis.yml create mode 100644 LICENSE create mode 100644 README.md create mode 100644 composer.json create mode 100644 composer.lock create mode 100644 phpcs.xml.dist create mode 100644 phpunit.xml.dist create mode 100644 src/E621.php create mode 100644 src/Entity/Artist.php create mode 100644 src/Entity/Blip.php create mode 100644 src/Entity/Comment.php create mode 100644 src/Entity/Dmail.php create mode 100644 src/Entity/Entity.php create mode 100644 src/Entity/Forum.php create mode 100644 src/Entity/Generic.php create mode 100644 src/Entity/Note.php create mode 100644 src/Entity/Pool.php create mode 100644 src/Entity/PoolPost.php create mode 100644 src/Entity/Post.php create mode 100644 src/Entity/PostFlagHistory.php create mode 100644 src/Entity/PostMd5.php create mode 100644 src/Entity/PostTagHistory.php create mode 100644 src/Entity/Response.php create mode 100644 src/Entity/Set.php create mode 100644 src/Entity/SetMaintainer.php create mode 100644 src/Entity/SetPost.php create mode 100644 src/Entity/Tag.php create mode 100644 src/Entity/TagAlias.php create mode 100644 src/Entity/TagImplication.php create mode 100644 src/Entity/Ticket.php create mode 100644 src/Entity/User.php create mode 100644 src/Entity/UserRecord.php create mode 100644 src/Entity/Wiki.php create mode 100644 tests/E621Test.php diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..c93e508 --- /dev/null +++ b/.gitignore @@ -0,0 +1,8 @@ +# PHPStorm +.idea + +# Composer +vendor/ + +# Others +.php_cs.cache diff --git a/.travis.yml b/.travis.yml new file mode 100644 index 0000000..074b17e --- /dev/null +++ b/.travis.yml @@ -0,0 +1,34 @@ +language: php + +cache: + directories: + - "$HOME/.composer/cache" + +php: + - 5.5 + - 5.6 + - 7.0 + - 7.1 + - 7.2 + - nightly + - hhvm + +matrix: + allow_failures: + - php: nightly + - php: hhvm + fast_finish: true + +notifications: + on_success: never + on_failure: never + +git: + depth: 1 + +install: + - travis_retry composer install --prefer-dist --no-interaction + +script: + - composer check-code + - composer test diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..665f516 --- /dev/null +++ b/LICENSE @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) 2018 Jack'lul + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. \ No newline at end of file diff --git a/README.md b/README.md new file mode 100644 index 0000000..7e40bfc --- /dev/null +++ b/README.md @@ -0,0 +1,117 @@ +# e621 API + +[![Build Status](https://travis-ci.org/jacklul/e621-api.svg?branch=master)](https://travis-ci.org/jacklul/e621-api) + +Simple PHP API wrapper for e621.net API. + +**This class is currently in development, most of the stuff was not tested and not every method in entities is implemented and documented yet.** + +## Table of Contents +- [Instructions](#instructions) + - [Installation](#installation) + - [Usage](#usage) + +## Instructions +### Installation + +Install this package through [Composer](https://github.com/composer/composer) - `composer require jacklul/e621-api`. + +### Usage + +- Initialize the object with User-Agent "My project": + +```php + require 'vendor/autoload.php'; // don't forget about loading Composer's autloader + + use jacklul\E621API\E621; + + $api = new E621('My project'); +``` + +- Perform request with own parameters: + +```php + $request = $api->postIndex(['tags' => 'falvie cat order:>score', 'limit' => 25]); +``` + +- This will return `Response` object, to get the actual data we make sure the request was successful first before getting result data: + +```php + if ($request->isSuccessful()) { + $results = $request->getResult(); // get the result data + } else { + echo $request->getReason(); // print request failure reason + } +``` + +- In case of `postIndex()` method result will be array of `Post` objects: + +```php + Array + ( + [0] => jacklul\E621API\Entity\Post Object + ( + [id] => 1194987 + [tags] => 2017 anthro armband bandage cat clothed clothing day digitigrade falvie feathers feline foot_wraps fur hair hi_res male mammal melee_weapon outside scabbard + scarf sheathed_weapon short_hair skimpy sky snow snowing solo standing step_pose sword weapon white_fur white_hair wraps + [locked_tags] => + [description] => + [created_at] => Array + ( + [json_class] => Time + [s] => 1492637589 + [n] => 932211000 + ) + + [creator_id] => 169756 + [author] => Millcore + [change] => 11649500 + [source] => https://www.furaffinity.net/view/23264446/ + [score] => 49 + [fav_count] => 104 + [md5] => d9988923347357a24ade031b9997de63 + [file_size] => 1776405 + [file_url] => https://static1.e621.net/data/d9/98/d9988923347357a24ade031b9997de63.png + [file_ext] => png + [preview_url] => https://static1.e621.net/data/preview/d9/98/d9988923347357a24ade031b9997de63.jpg + [preview_width] => 96 + [preview_height] => 150 + [sample_url] => https://static1.e621.net/data/sample/d9/98/d9988923347357a24ade031b9997de63.jpg + [sample_width] => 517 + [sample_height] => 800 + [rating] => s + [status] => active + [width] => 776 + [height] => 1200 + [has_comments] => 1 + [has_notes] => + [has_children] => + [children] => + [parent_id] => + [artist] => Array + ( + [0] => falvie + ) + + [sources] => Array + ( + [0] => https://www.furaffinity.net/view/23264446/ + [1] => http://www.furaffinity.net/user/falvie/ + [2] => https://d.facdn.net/art/falvie/1492632100/1492632100.falvie_kodiakonesm.png + ) + ) + ) +``` + +- You can easily iterate over it using `foreach()` and print every image's URL: + +```php + /** @var \jacklul\E621API\Entity\Post $post */ + foreach ($results as $post) { + echo $post->getFileUrl() . PHP_EOL; + } +``` + +## License + +See [LICENSE](LICENSE). diff --git a/composer.json b/composer.json new file mode 100644 index 0000000..0329c0b --- /dev/null +++ b/composer.json @@ -0,0 +1,44 @@ +{ + "name": "jacklul/e621-api", + "type": "library", + "description": "PHP e621 API Wrapper", + "keywords": ["e621", "api", "wrapper"], + "license": "MIT", + "homepage": "https://github.com/jacklul/e621-API", + "support": { + "issues": "https://github.com/jacklul/e621-API/issues", + "source": "https://github.com/jacklul/e621-API" + }, + "authors": [ + { + "name": "Jack'lul", + "email": "jacklulcat@gmail.com", + "homepage": "https://jacklul.github.io", + "role": "Developer" + } + ], + "require": { + "php": "^5.5|^7.0", + "guzzlehttp/guzzle": "^6.3" + }, + "require-dev": { + "phpunit/phpunit": "^7.0", + "squizlabs/php_codesniffer": "^3.2" + }, + "suggest": { + "ext-curl": "cURL provides better performance and capabilities" + }, + "autoload": { + "psr-4": { + "jacklul\\E621API\\": "src/" + } + }, + "scripts": { + "check-code": [ + "\"vendor/bin/phpcs\" -snp --standard=phpcs.xml.dist --encoding=utf-8 src/ tests/ --report-width=150" + ], + "test": [ + "\"vendor/bin/phpunit\"" + ] + } +} diff --git a/composer.lock b/composer.lock new file mode 100644 index 0000000..0d29596 --- /dev/null +++ b/composer.lock @@ -0,0 +1,1757 @@ +{ + "_readme": [ + "This file locks the dependencies of your project to a known state", + "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#composer-lock-the-lock-file", + "This file is @generated automatically" + ], + "content-hash": "1fe0beffac6f9f693a4a0584b067f091", + "packages": [ + { + "name": "guzzlehttp/guzzle", + "version": "6.3.0", + "source": { + "type": "git", + "url": "https://github.com/guzzle/guzzle.git", + "reference": "f4db5a78a5ea468d4831de7f0bf9d9415e348699" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/guzzle/guzzle/zipball/f4db5a78a5ea468d4831de7f0bf9d9415e348699", + "reference": "f4db5a78a5ea468d4831de7f0bf9d9415e348699", + "shasum": "" + }, + "require": { + "guzzlehttp/promises": "^1.0", + "guzzlehttp/psr7": "^1.4", + "php": ">=5.5" + }, + "require-dev": { + "ext-curl": "*", + "phpunit/phpunit": "^4.0 || ^5.0", + "psr/log": "^1.0" + }, + "suggest": { + "psr/log": "Required for using the Log middleware" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "6.2-dev" + } + }, + "autoload": { + "files": [ + "src/functions_include.php" + ], + "psr-4": { + "GuzzleHttp\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Michael Dowling", + "email": "mtdowling@gmail.com", + "homepage": "https://github.com/mtdowling" + } + ], + "description": "Guzzle is a PHP HTTP client library", + "homepage": "http://guzzlephp.org/", + "keywords": [ + "client", + "curl", + "framework", + "http", + "http client", + "rest", + "web service" + ], + "time": "2017-06-22T18:50:49+00:00" + }, + { + "name": "guzzlehttp/promises", + "version": "v1.3.1", + "source": { + "type": "git", + "url": "https://github.com/guzzle/promises.git", + "reference": "a59da6cf61d80060647ff4d3eb2c03a2bc694646" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/guzzle/promises/zipball/a59da6cf61d80060647ff4d3eb2c03a2bc694646", + "reference": "a59da6cf61d80060647ff4d3eb2c03a2bc694646", + "shasum": "" + }, + "require": { + "php": ">=5.5.0" + }, + "require-dev": { + "phpunit/phpunit": "^4.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.4-dev" + } + }, + "autoload": { + "psr-4": { + "GuzzleHttp\\Promise\\": "src/" + }, + "files": [ + "src/functions_include.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Michael Dowling", + "email": "mtdowling@gmail.com", + "homepage": "https://github.com/mtdowling" + } + ], + "description": "Guzzle promises library", + "keywords": [ + "promise" + ], + "time": "2016-12-20T10:07:11+00:00" + }, + { + "name": "guzzlehttp/psr7", + "version": "1.4.2", + "source": { + "type": "git", + "url": "https://github.com/guzzle/psr7.git", + "reference": "f5b8a8512e2b58b0071a7280e39f14f72e05d87c" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/guzzle/psr7/zipball/f5b8a8512e2b58b0071a7280e39f14f72e05d87c", + "reference": "f5b8a8512e2b58b0071a7280e39f14f72e05d87c", + "shasum": "" + }, + "require": { + "php": ">=5.4.0", + "psr/http-message": "~1.0" + }, + "provide": { + "psr/http-message-implementation": "1.0" + }, + "require-dev": { + "phpunit/phpunit": "~4.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.4-dev" + } + }, + "autoload": { + "psr-4": { + "GuzzleHttp\\Psr7\\": "src/" + }, + "files": [ + "src/functions_include.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Michael Dowling", + "email": "mtdowling@gmail.com", + "homepage": "https://github.com/mtdowling" + }, + { + "name": "Tobias Schultze", + "homepage": "https://github.com/Tobion" + } + ], + "description": "PSR-7 message implementation that also provides common utility methods", + "keywords": [ + "http", + "message", + "request", + "response", + "stream", + "uri", + "url" + ], + "time": "2017-03-20T17:10:46+00:00" + }, + { + "name": "psr/http-message", + "version": "1.0.1", + "source": { + "type": "git", + "url": "https://github.com/php-fig/http-message.git", + "reference": "f6561bf28d520154e4b0ec72be95418abe6d9363" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-fig/http-message/zipball/f6561bf28d520154e4b0ec72be95418abe6d9363", + "reference": "f6561bf28d520154e4b0ec72be95418abe6d9363", + "shasum": "" + }, + "require": { + "php": ">=5.3.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0.x-dev" + } + }, + "autoload": { + "psr-4": { + "Psr\\Http\\Message\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "PHP-FIG", + "homepage": "http://www.php-fig.org/" + } + ], + "description": "Common interface for HTTP messages", + "homepage": "https://github.com/php-fig/http-message", + "keywords": [ + "http", + "http-message", + "psr", + "psr-7", + "request", + "response" + ], + "time": "2016-08-06T14:39:51+00:00" + } + ], + "packages-dev": [ + { + "name": "doctrine/instantiator", + "version": "1.1.0", + "source": { + "type": "git", + "url": "https://github.com/doctrine/instantiator.git", + "reference": "185b8868aa9bf7159f5f953ed5afb2d7fcdc3bda" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/doctrine/instantiator/zipball/185b8868aa9bf7159f5f953ed5afb2d7fcdc3bda", + "reference": "185b8868aa9bf7159f5f953ed5afb2d7fcdc3bda", + "shasum": "" + }, + "require": { + "php": "^7.1" + }, + "require-dev": { + "athletic/athletic": "~0.1.8", + "ext-pdo": "*", + "ext-phar": "*", + "phpunit/phpunit": "^6.2.3", + "squizlabs/php_codesniffer": "^3.0.2" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.2.x-dev" + } + }, + "autoload": { + "psr-4": { + "Doctrine\\Instantiator\\": "src/Doctrine/Instantiator/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Marco Pivetta", + "email": "ocramius@gmail.com", + "homepage": "http://ocramius.github.com/" + } + ], + "description": "A small, lightweight utility to instantiate objects in PHP without invoking their constructors", + "homepage": "https://github.com/doctrine/instantiator", + "keywords": [ + "constructor", + "instantiate" + ], + "time": "2017-07-22T11:58:36+00:00" + }, + { + "name": "myclabs/deep-copy", + "version": "1.7.0", + "source": { + "type": "git", + "url": "https://github.com/myclabs/DeepCopy.git", + "reference": "3b8a3a99ba1f6a3952ac2747d989303cbd6b7a3e" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/myclabs/DeepCopy/zipball/3b8a3a99ba1f6a3952ac2747d989303cbd6b7a3e", + "reference": "3b8a3a99ba1f6a3952ac2747d989303cbd6b7a3e", + "shasum": "" + }, + "require": { + "php": "^5.6 || ^7.0" + }, + "require-dev": { + "doctrine/collections": "^1.0", + "doctrine/common": "^2.6", + "phpunit/phpunit": "^4.1" + }, + "type": "library", + "autoload": { + "psr-4": { + "DeepCopy\\": "src/DeepCopy/" + }, + "files": [ + "src/DeepCopy/deep_copy.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "description": "Create deep copies (clones) of your objects", + "keywords": [ + "clone", + "copy", + "duplicate", + "object", + "object graph" + ], + "time": "2017-10-19T19:58:43+00:00" + }, + { + "name": "phar-io/manifest", + "version": "1.0.1", + "source": { + "type": "git", + "url": "https://github.com/phar-io/manifest.git", + "reference": "2df402786ab5368a0169091f61a7c1e0eb6852d0" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phar-io/manifest/zipball/2df402786ab5368a0169091f61a7c1e0eb6852d0", + "reference": "2df402786ab5368a0169091f61a7c1e0eb6852d0", + "shasum": "" + }, + "require": { + "ext-dom": "*", + "ext-phar": "*", + "phar-io/version": "^1.0.1", + "php": "^5.6 || ^7.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0.x-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Arne Blankerts", + "email": "arne@blankerts.de", + "role": "Developer" + }, + { + "name": "Sebastian Heuer", + "email": "sebastian@phpeople.de", + "role": "Developer" + }, + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "Developer" + } + ], + "description": "Component for reading phar.io manifest information from a PHP Archive (PHAR)", + "time": "2017-03-05T18:14:27+00:00" + }, + { + "name": "phar-io/version", + "version": "1.0.1", + "source": { + "type": "git", + "url": "https://github.com/phar-io/version.git", + "reference": "a70c0ced4be299a63d32fa96d9281d03e94041df" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phar-io/version/zipball/a70c0ced4be299a63d32fa96d9281d03e94041df", + "reference": "a70c0ced4be299a63d32fa96d9281d03e94041df", + "shasum": "" + }, + "require": { + "php": "^5.6 || ^7.0" + }, + "type": "library", + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Arne Blankerts", + "email": "arne@blankerts.de", + "role": "Developer" + }, + { + "name": "Sebastian Heuer", + "email": "sebastian@phpeople.de", + "role": "Developer" + }, + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "Developer" + } + ], + "description": "Library for handling version information and constraints", + "time": "2017-03-05T17:38:23+00:00" + }, + { + "name": "phpdocumentor/reflection-common", + "version": "1.0.1", + "source": { + "type": "git", + "url": "https://github.com/phpDocumentor/ReflectionCommon.git", + "reference": "21bdeb5f65d7ebf9f43b1b25d404f87deab5bfb6" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phpDocumentor/ReflectionCommon/zipball/21bdeb5f65d7ebf9f43b1b25d404f87deab5bfb6", + "reference": "21bdeb5f65d7ebf9f43b1b25d404f87deab5bfb6", + "shasum": "" + }, + "require": { + "php": ">=5.5" + }, + "require-dev": { + "phpunit/phpunit": "^4.6" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0.x-dev" + } + }, + "autoload": { + "psr-4": { + "phpDocumentor\\Reflection\\": [ + "src" + ] + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Jaap van Otterdijk", + "email": "opensource@ijaap.nl" + } + ], + "description": "Common reflection classes used by phpdocumentor to reflect the code structure", + "homepage": "http://www.phpdoc.org", + "keywords": [ + "FQSEN", + "phpDocumentor", + "phpdoc", + "reflection", + "static analysis" + ], + "time": "2017-09-11T18:02:19+00:00" + }, + { + "name": "phpdocumentor/reflection-docblock", + "version": "4.3.0", + "source": { + "type": "git", + "url": "https://github.com/phpDocumentor/ReflectionDocBlock.git", + "reference": "94fd0001232e47129dd3504189fa1c7225010d08" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phpDocumentor/ReflectionDocBlock/zipball/94fd0001232e47129dd3504189fa1c7225010d08", + "reference": "94fd0001232e47129dd3504189fa1c7225010d08", + "shasum": "" + }, + "require": { + "php": "^7.0", + "phpdocumentor/reflection-common": "^1.0.0", + "phpdocumentor/type-resolver": "^0.4.0", + "webmozart/assert": "^1.0" + }, + "require-dev": { + "doctrine/instantiator": "~1.0.5", + "mockery/mockery": "^1.0", + "phpunit/phpunit": "^6.4" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "4.x-dev" + } + }, + "autoload": { + "psr-4": { + "phpDocumentor\\Reflection\\": [ + "src/" + ] + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Mike van Riel", + "email": "me@mikevanriel.com" + } + ], + "description": "With this component, a library can provide support for annotations via DocBlocks or otherwise retrieve information that is embedded in a DocBlock.", + "time": "2017-11-30T07:14:17+00:00" + }, + { + "name": "phpdocumentor/type-resolver", + "version": "0.4.0", + "source": { + "type": "git", + "url": "https://github.com/phpDocumentor/TypeResolver.git", + "reference": "9c977708995954784726e25d0cd1dddf4e65b0f7" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phpDocumentor/TypeResolver/zipball/9c977708995954784726e25d0cd1dddf4e65b0f7", + "reference": "9c977708995954784726e25d0cd1dddf4e65b0f7", + "shasum": "" + }, + "require": { + "php": "^5.5 || ^7.0", + "phpdocumentor/reflection-common": "^1.0" + }, + "require-dev": { + "mockery/mockery": "^0.9.4", + "phpunit/phpunit": "^5.2||^4.8.24" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0.x-dev" + } + }, + "autoload": { + "psr-4": { + "phpDocumentor\\Reflection\\": [ + "src/" + ] + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Mike van Riel", + "email": "me@mikevanriel.com" + } + ], + "time": "2017-07-14T14:27:02+00:00" + }, + { + "name": "phpspec/prophecy", + "version": "1.7.5", + "source": { + "type": "git", + "url": "https://github.com/phpspec/prophecy.git", + "reference": "dfd6be44111a7c41c2e884a336cc4f461b3b2401" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phpspec/prophecy/zipball/dfd6be44111a7c41c2e884a336cc4f461b3b2401", + "reference": "dfd6be44111a7c41c2e884a336cc4f461b3b2401", + "shasum": "" + }, + "require": { + "doctrine/instantiator": "^1.0.2", + "php": "^5.3|^7.0", + "phpdocumentor/reflection-docblock": "^2.0|^3.0.2|^4.0", + "sebastian/comparator": "^1.1|^2.0", + "sebastian/recursion-context": "^1.0|^2.0|^3.0" + }, + "require-dev": { + "phpspec/phpspec": "^2.5|^3.2", + "phpunit/phpunit": "^4.8.35 || ^5.7 || ^6.5" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.7.x-dev" + } + }, + "autoload": { + "psr-0": { + "Prophecy\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Konstantin Kudryashov", + "email": "ever.zet@gmail.com", + "homepage": "http://everzet.com" + }, + { + "name": "Marcello Duarte", + "email": "marcello.duarte@gmail.com" + } + ], + "description": "Highly opinionated mocking framework for PHP 5.3+", + "homepage": "https://github.com/phpspec/prophecy", + "keywords": [ + "Double", + "Dummy", + "fake", + "mock", + "spy", + "stub" + ], + "time": "2018-02-19T10:16:54+00:00" + }, + { + "name": "phpunit/php-code-coverage", + "version": "6.0.1", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/php-code-coverage.git", + "reference": "f8ca4b604baf23dab89d87773c28cc07405189ba" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/php-code-coverage/zipball/f8ca4b604baf23dab89d87773c28cc07405189ba", + "reference": "f8ca4b604baf23dab89d87773c28cc07405189ba", + "shasum": "" + }, + "require": { + "ext-dom": "*", + "ext-xmlwriter": "*", + "php": "^7.1", + "phpunit/php-file-iterator": "^1.4.2", + "phpunit/php-text-template": "^1.2.1", + "phpunit/php-token-stream": "^3.0", + "sebastian/code-unit-reverse-lookup": "^1.0.1", + "sebastian/environment": "^3.0", + "sebastian/version": "^2.0.1", + "theseer/tokenizer": "^1.1" + }, + "require-dev": { + "phpunit/phpunit": "^7.0" + }, + "suggest": { + "ext-xdebug": "^2.6.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "6.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Library that provides collection, processing, and rendering functionality for PHP code coverage information.", + "homepage": "https://github.com/sebastianbergmann/php-code-coverage", + "keywords": [ + "coverage", + "testing", + "xunit" + ], + "time": "2018-02-02T07:01:41+00:00" + }, + { + "name": "phpunit/php-file-iterator", + "version": "1.4.5", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/php-file-iterator.git", + "reference": "730b01bc3e867237eaac355e06a36b85dd93a8b4" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/php-file-iterator/zipball/730b01bc3e867237eaac355e06a36b85dd93a8b4", + "reference": "730b01bc3e867237eaac355e06a36b85dd93a8b4", + "shasum": "" + }, + "require": { + "php": ">=5.3.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.4.x-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sb@sebastian-bergmann.de", + "role": "lead" + } + ], + "description": "FilterIterator implementation that filters files based on a list of suffixes.", + "homepage": "https://github.com/sebastianbergmann/php-file-iterator/", + "keywords": [ + "filesystem", + "iterator" + ], + "time": "2017-11-27T13:52:08+00:00" + }, + { + "name": "phpunit/php-text-template", + "version": "1.2.1", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/php-text-template.git", + "reference": "31f8b717e51d9a2afca6c9f046f5d69fc27c8686" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/php-text-template/zipball/31f8b717e51d9a2afca6c9f046f5d69fc27c8686", + "reference": "31f8b717e51d9a2afca6c9f046f5d69fc27c8686", + "shasum": "" + }, + "require": { + "php": ">=5.3.3" + }, + "type": "library", + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Simple template engine.", + "homepage": "https://github.com/sebastianbergmann/php-text-template/", + "keywords": [ + "template" + ], + "time": "2015-06-21T13:50:34+00:00" + }, + { + "name": "phpunit/php-timer", + "version": "2.0.0", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/php-timer.git", + "reference": "8b8454ea6958c3dee38453d3bd571e023108c91f" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/php-timer/zipball/8b8454ea6958c3dee38453d3bd571e023108c91f", + "reference": "8b8454ea6958c3dee38453d3bd571e023108c91f", + "shasum": "" + }, + "require": { + "php": "^7.1" + }, + "require-dev": { + "phpunit/phpunit": "^7.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Utility class for timing", + "homepage": "https://github.com/sebastianbergmann/php-timer/", + "keywords": [ + "timer" + ], + "time": "2018-02-01T13:07:23+00:00" + }, + { + "name": "phpunit/php-token-stream", + "version": "3.0.0", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/php-token-stream.git", + "reference": "21ad88bbba7c3d93530d93994e0a33cd45f02ace" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/php-token-stream/zipball/21ad88bbba7c3d93530d93994e0a33cd45f02ace", + "reference": "21ad88bbba7c3d93530d93994e0a33cd45f02ace", + "shasum": "" + }, + "require": { + "ext-tokenizer": "*", + "php": "^7.1" + }, + "require-dev": { + "phpunit/phpunit": "^7.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Wrapper around PHP's tokenizer extension.", + "homepage": "https://github.com/sebastianbergmann/php-token-stream/", + "keywords": [ + "tokenizer" + ], + "time": "2018-02-01T13:16:43+00:00" + }, + { + "name": "phpunit/phpunit", + "version": "7.0.1", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/phpunit.git", + "reference": "316555dbd0ed4097bbdd17c65ab416bf27a472e9" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/phpunit/zipball/316555dbd0ed4097bbdd17c65ab416bf27a472e9", + "reference": "316555dbd0ed4097bbdd17c65ab416bf27a472e9", + "shasum": "" + }, + "require": { + "ext-dom": "*", + "ext-json": "*", + "ext-libxml": "*", + "ext-mbstring": "*", + "ext-xml": "*", + "myclabs/deep-copy": "^1.6.1", + "phar-io/manifest": "^1.0.1", + "phar-io/version": "^1.0", + "php": "^7.1", + "phpspec/prophecy": "^1.7", + "phpunit/php-code-coverage": "^6.0", + "phpunit/php-file-iterator": "^1.4.3", + "phpunit/php-text-template": "^1.2.1", + "phpunit/php-timer": "^2.0", + "phpunit/phpunit-mock-objects": "^6.0", + "sebastian/comparator": "^2.1", + "sebastian/diff": "^3.0", + "sebastian/environment": "^3.1", + "sebastian/exporter": "^3.1", + "sebastian/global-state": "^2.0", + "sebastian/object-enumerator": "^3.0.3", + "sebastian/resource-operations": "^1.0", + "sebastian/version": "^2.0.1" + }, + "require-dev": { + "ext-pdo": "*" + }, + "suggest": { + "ext-xdebug": "*", + "phpunit/php-invoker": "^2.0" + }, + "bin": [ + "phpunit" + ], + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "7.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "The PHP Unit Testing framework.", + "homepage": "https://phpunit.de/", + "keywords": [ + "phpunit", + "testing", + "xunit" + ], + "time": "2018-02-13T06:08:08+00:00" + }, + { + "name": "phpunit/phpunit-mock-objects", + "version": "6.0.1", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/phpunit-mock-objects.git", + "reference": "e3249dedc2d99259ccae6affbc2684eac37c2e53" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/phpunit-mock-objects/zipball/e3249dedc2d99259ccae6affbc2684eac37c2e53", + "reference": "e3249dedc2d99259ccae6affbc2684eac37c2e53", + "shasum": "" + }, + "require": { + "doctrine/instantiator": "^1.0.5", + "php": "^7.1", + "phpunit/php-text-template": "^1.2.1", + "sebastian/exporter": "^3.1" + }, + "require-dev": { + "phpunit/phpunit": "^7.0" + }, + "suggest": { + "ext-soap": "*" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "6.0.x-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Mock Object library for PHPUnit", + "homepage": "https://github.com/sebastianbergmann/phpunit-mock-objects/", + "keywords": [ + "mock", + "xunit" + ], + "time": "2018-02-15T05:27:38+00:00" + }, + { + "name": "sebastian/code-unit-reverse-lookup", + "version": "1.0.1", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/code-unit-reverse-lookup.git", + "reference": "4419fcdb5eabb9caa61a27c7a1db532a6b55dd18" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/code-unit-reverse-lookup/zipball/4419fcdb5eabb9caa61a27c7a1db532a6b55dd18", + "reference": "4419fcdb5eabb9caa61a27c7a1db532a6b55dd18", + "shasum": "" + }, + "require": { + "php": "^5.6 || ^7.0" + }, + "require-dev": { + "phpunit/phpunit": "^5.7 || ^6.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0.x-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Looks up which function or method a line of code belongs to", + "homepage": "https://github.com/sebastianbergmann/code-unit-reverse-lookup/", + "time": "2017-03-04T06:30:41+00:00" + }, + { + "name": "sebastian/comparator", + "version": "2.1.3", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/comparator.git", + "reference": "34369daee48eafb2651bea869b4b15d75ccc35f9" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/comparator/zipball/34369daee48eafb2651bea869b4b15d75ccc35f9", + "reference": "34369daee48eafb2651bea869b4b15d75ccc35f9", + "shasum": "" + }, + "require": { + "php": "^7.0", + "sebastian/diff": "^2.0 || ^3.0", + "sebastian/exporter": "^3.1" + }, + "require-dev": { + "phpunit/phpunit": "^6.4" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.1.x-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Jeff Welch", + "email": "whatthejeff@gmail.com" + }, + { + "name": "Volker Dusch", + "email": "github@wallbash.com" + }, + { + "name": "Bernhard Schussek", + "email": "bschussek@2bepublished.at" + }, + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Provides the functionality to compare PHP values for equality", + "homepage": "https://github.com/sebastianbergmann/comparator", + "keywords": [ + "comparator", + "compare", + "equality" + ], + "time": "2018-02-01T13:46:46+00:00" + }, + { + "name": "sebastian/diff", + "version": "3.0.0", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/diff.git", + "reference": "e09160918c66281713f1c324c1f4c4c3037ba1e8" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/diff/zipball/e09160918c66281713f1c324c1f4c4c3037ba1e8", + "reference": "e09160918c66281713f1c324c1f4c4c3037ba1e8", + "shasum": "" + }, + "require": { + "php": "^7.1" + }, + "require-dev": { + "phpunit/phpunit": "^7.0", + "symfony/process": "^2 || ^3.3 || ^4" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Kore Nordmann", + "email": "mail@kore-nordmann.de" + }, + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Diff implementation", + "homepage": "https://github.com/sebastianbergmann/diff", + "keywords": [ + "diff", + "udiff", + "unidiff", + "unified diff" + ], + "time": "2018-02-01T13:45:15+00:00" + }, + { + "name": "sebastian/environment", + "version": "3.1.0", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/environment.git", + "reference": "cd0871b3975fb7fc44d11314fd1ee20925fce4f5" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/environment/zipball/cd0871b3975fb7fc44d11314fd1ee20925fce4f5", + "reference": "cd0871b3975fb7fc44d11314fd1ee20925fce4f5", + "shasum": "" + }, + "require": { + "php": "^7.0" + }, + "require-dev": { + "phpunit/phpunit": "^6.1" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.1.x-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Provides functionality to handle HHVM/PHP environments", + "homepage": "http://www.github.com/sebastianbergmann/environment", + "keywords": [ + "Xdebug", + "environment", + "hhvm" + ], + "time": "2017-07-01T08:51:00+00:00" + }, + { + "name": "sebastian/exporter", + "version": "3.1.0", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/exporter.git", + "reference": "234199f4528de6d12aaa58b612e98f7d36adb937" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/exporter/zipball/234199f4528de6d12aaa58b612e98f7d36adb937", + "reference": "234199f4528de6d12aaa58b612e98f7d36adb937", + "shasum": "" + }, + "require": { + "php": "^7.0", + "sebastian/recursion-context": "^3.0" + }, + "require-dev": { + "ext-mbstring": "*", + "phpunit/phpunit": "^6.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.1.x-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Jeff Welch", + "email": "whatthejeff@gmail.com" + }, + { + "name": "Volker Dusch", + "email": "github@wallbash.com" + }, + { + "name": "Bernhard Schussek", + "email": "bschussek@2bepublished.at" + }, + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + }, + { + "name": "Adam Harvey", + "email": "aharvey@php.net" + } + ], + "description": "Provides the functionality to export PHP variables for visualization", + "homepage": "http://www.github.com/sebastianbergmann/exporter", + "keywords": [ + "export", + "exporter" + ], + "time": "2017-04-03T13:19:02+00:00" + }, + { + "name": "sebastian/global-state", + "version": "2.0.0", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/global-state.git", + "reference": "e8ba02eed7bbbb9e59e43dedd3dddeff4a56b0c4" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/global-state/zipball/e8ba02eed7bbbb9e59e43dedd3dddeff4a56b0c4", + "reference": "e8ba02eed7bbbb9e59e43dedd3dddeff4a56b0c4", + "shasum": "" + }, + "require": { + "php": "^7.0" + }, + "require-dev": { + "phpunit/phpunit": "^6.0" + }, + "suggest": { + "ext-uopz": "*" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.0-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Snapshotting of global state", + "homepage": "http://www.github.com/sebastianbergmann/global-state", + "keywords": [ + "global state" + ], + "time": "2017-04-27T15:39:26+00:00" + }, + { + "name": "sebastian/object-enumerator", + "version": "3.0.3", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/object-enumerator.git", + "reference": "7cfd9e65d11ffb5af41198476395774d4c8a84c5" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/object-enumerator/zipball/7cfd9e65d11ffb5af41198476395774d4c8a84c5", + "reference": "7cfd9e65d11ffb5af41198476395774d4c8a84c5", + "shasum": "" + }, + "require": { + "php": "^7.0", + "sebastian/object-reflector": "^1.1.1", + "sebastian/recursion-context": "^3.0" + }, + "require-dev": { + "phpunit/phpunit": "^6.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.0.x-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Traverses array structures and object graphs to enumerate all referenced objects", + "homepage": "https://github.com/sebastianbergmann/object-enumerator/", + "time": "2017-08-03T12:35:26+00:00" + }, + { + "name": "sebastian/object-reflector", + "version": "1.1.1", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/object-reflector.git", + "reference": "773f97c67f28de00d397be301821b06708fca0be" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/object-reflector/zipball/773f97c67f28de00d397be301821b06708fca0be", + "reference": "773f97c67f28de00d397be301821b06708fca0be", + "shasum": "" + }, + "require": { + "php": "^7.0" + }, + "require-dev": { + "phpunit/phpunit": "^6.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.1-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Allows reflection of object attributes, including inherited and non-public ones", + "homepage": "https://github.com/sebastianbergmann/object-reflector/", + "time": "2017-03-29T09:07:27+00:00" + }, + { + "name": "sebastian/recursion-context", + "version": "3.0.0", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/recursion-context.git", + "reference": "5b0cd723502bac3b006cbf3dbf7a1e3fcefe4fa8" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/recursion-context/zipball/5b0cd723502bac3b006cbf3dbf7a1e3fcefe4fa8", + "reference": "5b0cd723502bac3b006cbf3dbf7a1e3fcefe4fa8", + "shasum": "" + }, + "require": { + "php": "^7.0" + }, + "require-dev": { + "phpunit/phpunit": "^6.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.0.x-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Jeff Welch", + "email": "whatthejeff@gmail.com" + }, + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + }, + { + "name": "Adam Harvey", + "email": "aharvey@php.net" + } + ], + "description": "Provides functionality to recursively process PHP variables", + "homepage": "http://www.github.com/sebastianbergmann/recursion-context", + "time": "2017-03-03T06:23:57+00:00" + }, + { + "name": "sebastian/resource-operations", + "version": "1.0.0", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/resource-operations.git", + "reference": "ce990bb21759f94aeafd30209e8cfcdfa8bc3f52" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/resource-operations/zipball/ce990bb21759f94aeafd30209e8cfcdfa8bc3f52", + "reference": "ce990bb21759f94aeafd30209e8cfcdfa8bc3f52", + "shasum": "" + }, + "require": { + "php": ">=5.6.0" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.0.x-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de" + } + ], + "description": "Provides a list of PHP built-in functions that operate on resources", + "homepage": "https://www.github.com/sebastianbergmann/resource-operations", + "time": "2015-07-28T20:34:47+00:00" + }, + { + "name": "sebastian/version", + "version": "2.0.1", + "source": { + "type": "git", + "url": "https://github.com/sebastianbergmann/version.git", + "reference": "99732be0ddb3361e16ad77b68ba41efc8e979019" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/sebastianbergmann/version/zipball/99732be0ddb3361e16ad77b68ba41efc8e979019", + "reference": "99732be0ddb3361e16ad77b68ba41efc8e979019", + "shasum": "" + }, + "require": { + "php": ">=5.6" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.0.x-dev" + } + }, + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Sebastian Bergmann", + "email": "sebastian@phpunit.de", + "role": "lead" + } + ], + "description": "Library that helps with managing the version number of Git-hosted PHP projects", + "homepage": "https://github.com/sebastianbergmann/version", + "time": "2016-10-03T07:35:21+00:00" + }, + { + "name": "squizlabs/php_codesniffer", + "version": "3.2.3", + "source": { + "type": "git", + "url": "https://github.com/squizlabs/PHP_CodeSniffer.git", + "reference": "4842476c434e375f9d3182ff7b89059583aa8b27" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/squizlabs/PHP_CodeSniffer/zipball/4842476c434e375f9d3182ff7b89059583aa8b27", + "reference": "4842476c434e375f9d3182ff7b89059583aa8b27", + "shasum": "" + }, + "require": { + "ext-simplexml": "*", + "ext-tokenizer": "*", + "ext-xmlwriter": "*", + "php": ">=5.4.0" + }, + "require-dev": { + "phpunit/phpunit": "^4.0 || ^5.0 || ^6.0 || ^7.0" + }, + "bin": [ + "bin/phpcs", + "bin/phpcbf" + ], + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.x-dev" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Greg Sherwood", + "role": "lead" + } + ], + "description": "PHP_CodeSniffer tokenizes PHP, JavaScript and CSS files and detects violations of a defined set of coding standards.", + "homepage": "http://www.squizlabs.com/php-codesniffer", + "keywords": [ + "phpcs", + "standards" + ], + "time": "2018-02-20T21:35:23+00:00" + }, + { + "name": "theseer/tokenizer", + "version": "1.1.0", + "source": { + "type": "git", + "url": "https://github.com/theseer/tokenizer.git", + "reference": "cb2f008f3f05af2893a87208fe6a6c4985483f8b" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/theseer/tokenizer/zipball/cb2f008f3f05af2893a87208fe6a6c4985483f8b", + "reference": "cb2f008f3f05af2893a87208fe6a6c4985483f8b", + "shasum": "" + }, + "require": { + "ext-dom": "*", + "ext-tokenizer": "*", + "ext-xmlwriter": "*", + "php": "^7.0" + }, + "type": "library", + "autoload": { + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Arne Blankerts", + "email": "arne@blankerts.de", + "role": "Developer" + } + ], + "description": "A small library for converting tokenized PHP source code into XML and potentially other formats", + "time": "2017-04-07T12:08:54+00:00" + }, + { + "name": "webmozart/assert", + "version": "1.3.0", + "source": { + "type": "git", + "url": "https://github.com/webmozart/assert.git", + "reference": "0df1908962e7a3071564e857d86874dad1ef204a" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/webmozart/assert/zipball/0df1908962e7a3071564e857d86874dad1ef204a", + "reference": "0df1908962e7a3071564e857d86874dad1ef204a", + "shasum": "" + }, + "require": { + "php": "^5.3.3 || ^7.0" + }, + "require-dev": { + "phpunit/phpunit": "^4.6", + "sebastian/version": "^1.0.1" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "1.3-dev" + } + }, + "autoload": { + "psr-4": { + "Webmozart\\Assert\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Bernhard Schussek", + "email": "bschussek@gmail.com" + } + ], + "description": "Assertions to validate method input/output with nice error messages.", + "keywords": [ + "assert", + "check", + "validate" + ], + "time": "2018-01-29T19:49:41+00:00" + } + ], + "aliases": [], + "minimum-stability": "stable", + "stability-flags": [], + "prefer-stable": false, + "prefer-lowest": false, + "platform": { + "php": "^5.5|^7.0" + }, + "platform-dev": [] +} diff --git a/phpcs.xml.dist b/phpcs.xml.dist new file mode 100644 index 0000000..0e86c93 --- /dev/null +++ b/phpcs.xml.dist @@ -0,0 +1,8 @@ + + + PSR2 without line length warning + + + + + diff --git a/phpunit.xml.dist b/phpunit.xml.dist new file mode 100644 index 0000000..4efaa66 --- /dev/null +++ b/phpunit.xml.dist @@ -0,0 +1,17 @@ + + + + + + + + ./tests + + + + + src/ + + + diff --git a/src/E621.php b/src/E621.php new file mode 100644 index 0000000..862341e --- /dev/null +++ b/src/E621.php @@ -0,0 +1,899 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API; + +use GuzzleHttp\Client; +use GuzzleHttp\Exception\RequestException; +use InvalidArgumentException; +use jacklul\E621API\Entity\Artist; +use jacklul\E621API\Entity\Blip; +use jacklul\E621API\Entity\Comment; +use jacklul\E621API\Entity\Dmail; +use jacklul\E621API\Entity\Forum; +use jacklul\E621API\Entity\Generic; +use jacklul\E621API\Entity\Note; +use jacklul\E621API\Entity\Pool; +use jacklul\E621API\Entity\PoolPost; +use jacklul\E621API\Entity\Post; +use jacklul\E621API\Entity\PostFlagHistory; +use jacklul\E621API\Entity\PostMd5; +use jacklul\E621API\Entity\PostTagHistory; +use jacklul\E621API\Entity\Response; +use jacklul\E621API\Entity\Set; +use jacklul\E621API\Entity\SetMaintainer; +use jacklul\E621API\Entity\SetPost; +use jacklul\E621API\Entity\Tag; +use jacklul\E621API\Entity\TagAlias; +use jacklul\E621API\Entity\TagImplication; +use jacklul\E621API\Entity\Ticket; +use jacklul\E621API\Entity\User; +use jacklul\E621API\Entity\UserRecord; +use jacklul\E621API\Entity\Wiki; + +/** + * Simple object-oriented e621 API wrapper + * Some useful code borrowed from https://github.com/php-telegram-bot/core + * + * @method Response postCreate(array $params) + * @method Response postUpdate(array $params) + * @method Response postShow(array $params) + * @method Response postCheckMd5(array $params) + * @method Response postTags(array $params) + * @method Response postIndex(array $params) + * @method Response postFlag(array $params) + * @method Response postDestroy(array $params) + * @method Response postDeletedIndex(array $params) + * @method Response postPopularByDay(array $params) + * @method Response postPopularByWeek(array $params) + * @method Response postPopularByMonth(array $params) + * @method Response postRevertTags(array $params) + * @method Response postVote(array $params) + * @method Response tagIndex(array $params) + * @method Response tagShow(array $params) + * @method Response tagUpdate(array $params) + * @method Response tagRelated(array $params) + * @method Response tagAliasIndex(array $params) + * @method Response tagImplicationIndex(array $params) + * @method Response artistIndex(array $params) + * @method Response artistCreate(array $params) + * @method Response artistUpdate(array $params) + * @method Response artistDestroy(array $params) + * @method Response commentShow(array $params) + * @method Response commentIndex(array $params) + * @method Response commentSearch(array $params) + * @method Response commentCreate(array $params) + * @method Response commentUpdate(array $params) + * @method Response commentDestroy(array $params) + * @method Response commentHide(array $params) + * @method Response commentUnhide(array $params) + * @method Response commentVote(array $params) + * @method Response blipCreate(array $params) + * @method Response blipUpdate(array $params) + * @method Response blipIndex(array $params) + * @method Response blipShow(array $params) + * @method Response blipHide(array $params) + * @method Response blipUnhide(array $params) + * @method Response wikiIndex(array $params) + * @method Response wikiCreate(array $params) + * @method Response wikiUpdate(array $params) + * @method Response wikiShow(array $params) + * @method Response wikiDestroy(array $params) + * @method Response wikiLock(array $params) + * @method Response wikiUnlock(array $params) + * @method Response wikiRevert(array $params) + * @method Response wikiHistory(array $params) + * @method Response wikiRecentChanges(array $params) + * @method Response noteIndex(array $params) + * @method Response noteSearch(array $params) + * @method Response noteHistory(array $params) + * @method Response noteRevert(array $params) + * @method Response noteUpdate(array $params) + * @method Response userIndex(array $params) + * @method Response userShow(array $params) + * @method Response userRecordShow(array $params) + * @method Response dmailCreate(array $params) + * @method Response dmailInbox(array $params) + * @method Response dmailShow(array $params) + * @method Response dmailHide(array $params) + * @method Response dmailUnhide(array $params) + * @method Response dmailHideAll(array $params) + * @method Response dmailUnhideAll(array $params) + * @method Response dmailMarkAllRead(array $params) + * @method Response forumCreate(array $params) + * @method Response forumUpdate(array $params) + * @method Response forumIndex(array $params) + * @method Response forumSearch(array $params) + * @method Response forumShow(array $params) + * @method Response forumHide(array $params) + * @method Response forumUnhide(array $params) + * @method Response poolIndex(array $params) + * @method Response poolShow(array $params) + * @method Response poolUpdate(array $params) + * @method Response poolCreate(array $params) + * @method Response poolDestroy(array $params) + * @method Response poolAddPost(array $params) + * @method Response poolRemovePost(array $params) + * @method Response setIndex(array $params) + * @method Response setShow(array $params) + * @method Response setCreate(array $params) + * @method Response setUpdate(array $params) + * @method Response setAddPost(array $params) + * @method Response setRemovePost(array $params) + * @method Response setDestroy(array $params) + * @method Response setMaintainers(array $params) + * @method Response setMaintainerIndex(array $params) + * @method Response setMaintainerCreate(array $params) + * @method Response setMaintainerDestroy(array $params) + * @method Response setMaintainerApprove(array $params) + * @method Response setMaintainerDeny(array $params) + * @method Response setMaintainerBlock(array $params) + * @method Response favoriteListUsers(array $params) + * @method Response postTagHistoryIndex(array $params) + * @method Response postFlagHistoryIndex(array $params) + * @method Response ticketCreate(array $params) + * @method Response ticketIndex(array $params) + * @method Response ticketShow(array $params) + */ +class E621 +{ + /** + * Library version + * + * @var string + */ + const VERSION = '0.1.0'; + + /** + * Base URL for API calls + * + * @var string + */ + private $base_uri = 'https://e621.net'; + + /** + * Guzzle's Client object + * + * @var Client + */ + private $client; + + /** + * Handler for requests in progress + * + * @var callable + */ + private $progress_handler; + + /** + * Handler for debug logging + * + * @var callable + */ + private $debug_log_handler; + + /** + * Temporary handle for request logging + * + * @var resource + */ + private $debug_log_stream_handle; + + /** + * List of supported API methods + * + * @var array + */ + public $actions = [ + 'postCreate' => [ + 'path' => 'post/create.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'postUpdate' => [ + 'path' => 'post/update.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'postShow' => [ + 'path' => 'post/show.json', + 'method' => 'GET', + 'class' => Post::class, + ], + 'postCheckMd5' => [ + 'path' => 'post/check_md5.json', + 'method' => 'GET', + 'class' => PostMd5::class, + ], + 'postTags' => [ + 'path' => 'post/tags.json', + 'method' => 'GET', + 'class' => Tag::class, + ], + 'postIndex' => [ + 'path' => 'post/index.json', + 'method' => 'GET', + 'class' => Post::class, + ], + 'postFlag' => [ + 'path' => 'post/flag.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'postDestroy' => [ + 'path' => 'post/destroy.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'postDeletedIndex' => [ + 'path' => 'post/deleted_index.json', + 'method' => 'GET', + 'class' => Post::class, + ], + 'postPopularByDay' => [ + 'path' => 'post/popular_by_day.json', + 'method' => 'GET', + 'class' => Post::class, + ], + 'postPopularByWeek' => [ + 'path' => 'post/popular_by_week.json', + 'method' => 'GET', + 'class' => Post::class, + ], + 'postPopularByMonth' => [ + 'path' => 'post/popular_by_month.json', + 'method' => 'GET', + 'class' => Post::class, + ], + 'postRevertTags' => [ + 'path' => 'post/revert_tags.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'postVote' => [ + 'path' => 'post/vote.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'tagIndex' => [ + 'path' => 'tag/index.json', + 'method' => 'GET', + 'class' => Tag::class, + ], + 'tagShow' => [ + 'path' => 'tag/show.json', + 'method' => 'GET', + 'class' => Tag::class, + ], + 'tagUpdate' => [ + 'path' => 'tag/update.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'tagRelated' => [ + 'path' => 'tag/related.json', + 'method' => 'GET', + 'class' => Tag::class, + ], + 'tagAliasIndex' => [ + 'path' => 'tag_alias/index.json', + 'method' => 'GET', + 'class' => TagAlias::class, + ], + 'tagImplicationIndex' => [ + 'path' => 'tag_implication/index.json', + 'method' => 'GET', + 'class' => TagImplication::class, + ], + 'artistIndex' => [ + 'path' => 'artist/index.json', + 'method' => 'GET', + 'class' => Artist::class, + ], + 'artistCreate' => [ + 'path' => 'artist/create.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'artistUpdate' => [ + 'path' => 'artist/update.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'artistDestroy' => [ + 'path' => 'artist/destroy.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'commentShow' => [ + 'path' => 'comment/show.json', + 'method' => 'GET', + 'class' => Comment::class, + ], + 'commentIndex' => [ + 'path' => 'comment/index.json', + 'method' => 'GET', + 'class' => Comment::class, + ], + 'commentSearch' => [ + 'path' => 'comment/search.json', + 'method' => 'GET', + 'class' => Comment::class, + ], + 'commentCreate' => [ + 'path' => 'comment/create.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'commentUpdate' => [ + 'path' => 'comment/update.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'commentDestroy' => [ + 'path' => 'comment/destroy.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'commentHide' => [ + 'path' => 'comment/hide.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'commentUnhide' => [ + 'path' => 'comment/unhide.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'commentVote' => [ + 'path' => 'comment/vote.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'blipCreate' => [ + 'path' => 'blip/create.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'blipUpdate' => [ + 'path' => 'blip/update.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'blipIndex' => [ + 'path' => 'blip/index.json', + 'method' => 'GET', + 'class' => Blip::class, + ], + 'blipShow' => [ + 'path' => 'blip/show.json', + 'method' => 'GET', + 'class' => Blip::class, + ], + 'blipHide' => [ + 'path' => 'blip/hide.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'blipUnhide' => [ + 'path' => 'blip/unhide.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'wikiIndex' => [ + 'path' => 'wiki/index.json', + 'method' => 'GET', + 'class' => Wiki::class, + ], + 'wikiCreate' => [ + 'path' => 'wiki/create.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'wikiUpdate' => [ + 'path' => 'wiki/update.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'wikiShow' => [ + 'path' => 'wiki/show.json', + 'method' => 'GET', + 'class' => Wiki::class, + ], + 'wikiDestroy' => [ + 'path' => 'wiki/destroy.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'wikiLock' => [ + 'path' => 'wiki/lock.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'wikiUnlock' => [ + 'path' => 'wiki/unlock.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'wikiRevert' => [ + 'path' => 'wiki/revert.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'wikiHistory' => [ + 'path' => 'wiki/history.json', + 'method' => 'GET', + 'class' => Generic::class, + ], + 'wikiRecentChanges' => [ + 'path' => 'wiki/recent_changes.json', + 'method' => 'GET', + 'class' => Generic::class, + ], + 'noteIndex' => [ + 'path' => 'note/index.json', + 'method' => 'GET', + 'class' => Note::class, + ], + 'noteSearch' => [ + 'path' => 'note/search.json', + 'method' => 'GET', + 'class' => Note::class, + ], + 'noteHistory' => [ + 'path' => 'note/history.json', + 'method' => 'GET', + 'class' => Generic::class, + ], + 'noteRevert' => [ + 'path' => 'note/revert.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'noteUpdate' => [ + 'path' => 'note/update.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'userIndex' => [ + 'path' => 'user/index.json', + 'method' => 'GET', + 'class' => User::class, + ], + 'userShow' => [ + 'path' => 'user/show.json', + 'method' => 'GET', + 'class' => User::class, + ], + 'userRecordShow' => [ + 'path' => 'user_record/show.json', + 'method' => 'GET', + 'class' => UserRecord::class, + ], + 'dmailCreate' => [ + 'path' => 'dmail/create.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'dmailInbox' => [ + 'path' => 'dmail/inbox.json', + 'method' => 'GET', + 'class' => Dmail::class, + ], + 'dmailShow' => [ + 'path' => 'dmail/show.json', + 'method' => 'GET', + 'class' => Dmail::class, + ], + 'dmailHide' => [ + 'path' => 'dmail/hide.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'dmailUnhide' => [ + 'path' => 'dmail/unhide.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'dmailHideAll' => [ + 'path' => 'dmail/hide_all.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'dmailUnhideAll' => [ + 'path' => 'dmail/unhide_all.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'dmailMarkAllRead' => [ + 'path' => 'dmail/mark_all_read.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'forumCreate' => [ + 'path' => 'forum/create.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'forumUpdate' => [ + 'path' => 'forum/update.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'forumIndex' => [ + 'path' => 'forum/index.json', + 'method' => 'GET', + 'class' => Forum::class, + ], + 'forumSearch' => [ + 'path' => 'forum/search.json', + 'method' => 'GET', + 'class' => Forum::class, + ], + 'forumShow' => [ + 'path' => 'forum/show.json', + 'method' => 'GET', + 'class' => Forum::class, + ], + 'forumHide' => [ + 'path' => 'forum/hide.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'forumUnhide' => [ + 'path' => 'forum/unhide.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'poolIndex' => [ + 'path' => 'pool/index.json', + 'method' => 'GET', + 'class' => Pool::class, + ], + 'poolShow' => [ + 'path' => 'pool/show.json', + 'method' => 'GET', + 'class' => PoolPost::class, + ], + 'poolUpdate' => [ + 'path' => 'pool/update.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'poolCreate' => [ + 'path' => 'pool/create.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'poolDestroy' => [ + 'path' => 'pool/destroy.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'poolAddPost' => [ + 'path' => 'pool/add_post.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'poolRemovePost' => [ + 'path' => 'pool/remove_post.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'setIndex' => [ + 'path' => 'set/index.json', + 'method' => 'GET', + 'class' => Set::class, + ], + 'setShow' => [ + 'path' => 'set/show.json', + 'method' => 'GET', + 'class' => SetPost::class, + ], + 'setCreate' => [ + 'path' => 'set/create.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'setUpdate' => [ + 'path' => 'set/update.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'setAddPost' => [ + 'path' => 'set/add_post.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'setRemovePost' => [ + 'path' => 'set/remove_post.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'setDestroy' => [ + 'path' => 'set/destroy.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'setMaintainers' => [ + 'path' => 'set/maintainers.json', + 'method' => 'GET', + 'class' => SetMaintainer::class, + ], + 'setMaintainerIndex' => [ + 'path' => 'set_maintainer/index.json', + 'method' => 'GET', + 'class' => SetMaintainer::class, + ], + 'setMaintainerCreate' => [ + 'path' => 'set_maintainer/create.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'setMaintainerDestroy' => [ + 'path' => 'set_maintainer/destroy.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'setMaintainerApprove.json' => [ + 'path' => 'set_maintainer/approve.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'setMaintainerDeny' => [ + 'path' => 'set_maintainer/deny.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'setMaintainerBlock' => [ + 'path' => 'set_maintainer/block.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'favoriteListUsers' => [ + 'path' => 'favorite/list_users.json', + 'method' => 'GET', + 'class' => User::class, + ], + 'postTagHistoryIndex' => [ + 'path' => 'post_tag_history/index.json', + 'method' => 'GET', + 'class' => PostTagHistory::class, + ], + 'postFlagHistoryIndex' => [ + 'path' => 'post_flag_history/index.json', + 'method' => 'GET', + 'class' => PostFlagHistory::class, + ], + 'ticketCreate' => [ + 'path' => 'ticket/create.json', + 'method' => 'POST', + 'class' => Generic::class, + ], + 'ticketIndex' => [ + 'path' => 'ticket/index.json', + 'method' => 'GET', + 'class' => Ticket::class, + ], + 'ticketShow' => [ + 'path' => 'ticket/show.json', + 'method' => 'GET', + 'class' => Ticket::class, + ], + ]; + + /** + * E621 constructor + * + * @param string $user_agent + * @param array $custom_options + * + * @throws InvalidArgumentException + */ + public function __construct($user_agent, array $custom_options = null) + { + if (empty($user_agent) && $user_agent !== false) { + throw new InvalidArgumentException('Argument "user_agent" must be set!'); + } + + $options = [ + 'base_uri' => $this->base_uri, + 'headers' => [ + 'User-Agent' => $user_agent . ' (E621API/' . self::VERSION . ' Guzzle/' . Client::VERSION . ' PHP/' . PHP_VERSION . ')', + 'Accept' => 'application/json', + ], + ]; + + if (strlen($options['headers']['User-Agent']) > 255) { + trigger_error('User-Agent field exceeds 255 characters!', E_USER_WARNING); + } + + if (is_array($custom_options) && !empty($custom_options)) { + $options = array_merge($options, $custom_options); + } + + $this->client = new Client($options); + } + + /** + * Main method for making requests + * + * @param string $path + * @param array $data + * @param string $method + * @param string $class + * + * @return string + * @throws InvalidArgumentException + */ + private function request($path = 'post/index.json', array $data = null, $method = 'GET', $class = null) + { + if (empty($path)) { + throw new InvalidArgumentException('Argument "path" cannot be empty!'); + } + + if (strtoupper($method) === 'GET') { + $options = ['query' => $data]; + } elseif (strtoupper($method) === 'POST') { + $options = $this->prepareRequestParams($data); + } else { + throw new InvalidArgumentException('Unsupported request method!'); + } + + ($this->progress_handler !== null && is_callable($this->progress_handler)) && $options['progress'] = $this->progress_handler; + ($this->debug_log_handler !== null && is_callable($this->debug_log_handler)) && $options['debug'] = $this->createDebugStream(); + + try { + $response = $this->client->request($method, $path, $options); + $result = json_decode((string) $response->getBody(), true); + } catch (RequestException $e) { + $this->debugLog($e); + $result = ($e->getResponse()) ? (string) $e->getResponse()->getBody() : 'Empty response / Request timed out'; + + // Replace the result when HTML code is detected or request result code isn't 200 + if ($e->getResponse()->getStatusCode() !== 200 || preg_match("/<[^<]+>/", $result) !== false) { + $result = (string) $e->getResponse()->getStatusCode() . ' ' . (string)$e->getResponse()->getReasonPhrase(); + } + + $result = ['success' => false, 'reason' => $result]; + } finally { + $this->endDebugStream(); + } + + // Search for result class if we don't have one + if (empty($class)) { + $class = Generic::class; + foreach ($this->actions as $key => $val) { + if ($val['path'] === $path) { + $class = $val['class']; + } + } + } + + return new Response($class, $result); + } + + /** + * Prepare request params for POST request, convert to multipart when needed + * + * @param array $data + * + * @return array + */ + private function prepareRequestParams(array $data) + { + $has_resource = false; + $multipart = []; + + foreach ($data as $key => $value) { + if (!is_array($value)) { + $multipart[] = ['name' => $key, 'contents' => $value]; + continue; + } + + foreach ($value as $multiKey => $multiValue) { + is_resource($multiValue) && $has_resource = true; + $multiName = $key . '[' .$multiKey . ']' . (is_array($multiValue) ? '[' . key($multiValue) . ']' : '') . ''; + $multipart[] = ['name' => $multiName, 'contents' => (is_array($multiValue) ? reset($multiValue) : $multiValue)]; + } + } + + if ($has_resource) { + return ['multipart' => $multipart]; + } + + return ['form_params' => $data]; + } + + /** + * @param string $action + * @param array $data + * + * @return mixed + * @throws InvalidArgumentException + */ + public function __call($action, array $data = []) + { + if (!isset($this->actions[$action]['path']) && !isset($this->actions[$action]['method']) && !isset($this->actions[$action]['class'])) { + throw new InvalidArgumentException('Action "' . $action . '" doesn\'t exist!'); + } + + return $this->request($this->actions[$action]['path'], isset($data[0]) ? $data[0] : null, $this->actions[$action]['method'], $this->actions[$action]['class']); + } + + /** + * Write to debug log + * + * @param $message + */ + private function debugLog($message) + { + $this->debug_log_handler !== null && is_callable($this->debug_log_handler) && call_user_func($this->debug_log_handler, $message); + } + + /** + * Get the stream handle of the temporary debug output + * + * @return mixed The stream if debug is active, else false + */ + private function createDebugStream() + { + if ($this->debug_log_stream_handle === null) { + $this->debug_log_stream_handle = fopen('php://temp', 'w+b'); + } + + return $this->debug_log_stream_handle; + } + + /** + * Write the temporary debug stream to log and close the stream handle + */ + private function endDebugStream() + { + if (is_resource($this->debug_log_stream_handle)) { + rewind($this->debug_log_stream_handle); + $this->debugLog('E621 API Verbose HTTP Request output:' . PHP_EOL . stream_get_contents($this->debug_log_stream_handle) . PHP_EOL); + fclose($this->debug_log_stream_handle); + $this->debug_log_stream_handle = null; + } + } + + /** + * Set progress handler + * + * @param callable $progress_handler + * + * @throws InvalidArgumentException + */ + public function setRequestProgressHandler($progress_handler) + { + if ($progress_handler !== null && is_callable($progress_handler)) { + $this->progress_handler = $progress_handler; + } else { + throw new InvalidArgumentException('Argument "progress_handler" must be callable!'); + } + } + + /** + * Set debug log handler + * + * @param mixed $debug_log_handler + * + * @throws InvalidArgumentException + */ + public function setDebugLogHandler($debug_log_handler) + { + if ($debug_log_handler !== null && is_callable($debug_log_handler)) { + $this->debug_log_handler = $debug_log_handler; + } else { + throw new InvalidArgumentException('Argument "debug_log_handler" must be callable!'); + } + } +} diff --git a/src/Entity/Artist.php b/src/Entity/Artist.php new file mode 100644 index 0000000..78e5163 --- /dev/null +++ b/src/Entity/Artist.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class Artist extends Entity +{ +} diff --git a/src/Entity/Blip.php b/src/Entity/Blip.php new file mode 100644 index 0000000..18a289e --- /dev/null +++ b/src/Entity/Blip.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class Blip extends Entity +{ +} diff --git a/src/Entity/Comment.php b/src/Entity/Comment.php new file mode 100644 index 0000000..bf92c6e --- /dev/null +++ b/src/Entity/Comment.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class Comment extends Entity +{ +} diff --git a/src/Entity/Dmail.php b/src/Entity/Dmail.php new file mode 100644 index 0000000..7a6d515 --- /dev/null +++ b/src/Entity/Dmail.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class Dmail extends Entity +{ +} diff --git a/src/Entity/Entity.php b/src/Entity/Entity.php new file mode 100644 index 0000000..ea3a0e4 --- /dev/null +++ b/src/Entity/Entity.php @@ -0,0 +1,60 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +abstract class Entity +{ + /** + * @param $data + */ + public function __construct($data) + { + foreach ($data as $key => $value) { + $this->$key = $value; + } + } + + /** + * @param $method + * @param $args + * + * @return mixed|null + */ + public function __call($method, $args) + { + $property = strtolower(ltrim(preg_replace('/[A-Z]/', '_$0', substr($method, 3)), '_')); + + if (substr($method, 0, 3) === 'get' && isset($this->$property)) { + return $this->$property; + } + + return null; + } + + /** + * @return string + */ + public function toJson() + { + return json_encode(get_object_vars($this)); + } + + /** + * @return string + */ + public function __toString() + { + return $this->toJson(); + } +} diff --git a/src/Entity/Forum.php b/src/Entity/Forum.php new file mode 100644 index 0000000..49459ff --- /dev/null +++ b/src/Entity/Forum.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class Forum extends Entity +{ +} diff --git a/src/Entity/Generic.php b/src/Entity/Generic.php new file mode 100644 index 0000000..45b8efd --- /dev/null +++ b/src/Entity/Generic.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class Generic extends Entity +{ +} diff --git a/src/Entity/Note.php b/src/Entity/Note.php new file mode 100644 index 0000000..1c2de5c --- /dev/null +++ b/src/Entity/Note.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class Note extends Entity +{ +} diff --git a/src/Entity/Pool.php b/src/Entity/Pool.php new file mode 100644 index 0000000..7dade1c --- /dev/null +++ b/src/Entity/Pool.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class Pool extends Entity +{ +} diff --git a/src/Entity/PoolPost.php b/src/Entity/PoolPost.php new file mode 100644 index 0000000..65f72b7 --- /dev/null +++ b/src/Entity/PoolPost.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class PoolPost extends Entity +{ +} diff --git a/src/Entity/Post.php b/src/Entity/Post.php new file mode 100644 index 0000000..5b8de34 --- /dev/null +++ b/src/Entity/Post.php @@ -0,0 +1,59 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @method int getId() + * @method string getAuthor() + * @method int getCreatorId() + * @method array getCreatedAt() + * @method string getStatus() + * @method string getSource() + * @method array getSources() + * @method string getTags() + * @method array getArtist() + * @method string getDescription() + * @method string getFavCount() + * @method string getScore() + * @method string getRating() + * @method string getParentId() + * @method bool getHasChildren() + * @method string getChildren() + * @method bool getHasNotes() + * @method bool getHasComments() + * @method string getMd5() + * @method string getFileUrl() + * @method string getFileExt() + * @method string getFileSize() + * @method string getWidth() + * @method string getHeight() + * @method string getSampleUrl() + * @method string getSampleWidth() + * @method string getSampleHeight() + * @method string getPreviewUrl() + * @method string getPreviewWidth() + * @method string getPreviewHeight() + * @method string getDelReason() + * + * @package jacklul\E621API\Entity + */ +class Post extends Entity +{ + public function getCreatedAtInt() + { + return isset($data['created_at']['s']) ? $data['created_at']['s'] : null; + } + + public function getChildrenArray() + { + return isset($data['children']) ? explode(',', $data['children']) : null; + } +} diff --git a/src/Entity/PostFlagHistory.php b/src/Entity/PostFlagHistory.php new file mode 100644 index 0000000..c42b98d --- /dev/null +++ b/src/Entity/PostFlagHistory.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class PostFlagHistory extends Entity +{ +} diff --git a/src/Entity/PostMd5.php b/src/Entity/PostMd5.php new file mode 100644 index 0000000..46d8e7f --- /dev/null +++ b/src/Entity/PostMd5.php @@ -0,0 +1,22 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @method string getMd5() + * @method string getExists() + * @method string getPostId() + * + * @package jacklul\E621API\Entity + */ +class PostMd5 extends Entity +{ +} diff --git a/src/Entity/PostTagHistory.php b/src/Entity/PostTagHistory.php new file mode 100644 index 0000000..eedf765 --- /dev/null +++ b/src/Entity/PostTagHistory.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class PostTagHistory extends Entity +{ +} diff --git a/src/Entity/Response.php b/src/Entity/Response.php new file mode 100644 index 0000000..2dccd18 --- /dev/null +++ b/src/Entity/Response.php @@ -0,0 +1,74 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +use InvalidArgumentException; + +/** + * @method bool getSuccess() + * @method mixed getResult() + */ +class Response extends Entity +{ + /** + * @param array $result + * @param string $class + * + * @throws InvalidArgumentException + */ + public function __construct($class, array $result = []) + { + if (!class_exists($class)) { + throw new InvalidArgumentException('Class doesn\'t exist: ' . $class); + } + + if (!is_array($result)) { + throw new InvalidArgumentException('Argument "timeout" must be an array!'); + } + + if (isset($result['success']) && $result['success'] === false) { + $data = [ + 'success' => false, + 'reason' => $result['reason'] + ]; + } elseif (count($result) === 0) { + $data = [ + 'success' => true, + 'result' => [] + ]; + } else { + if (isset($result[0])) { + /** @var $class[] $result */ + foreach ($result as &$item) { + $item = new $class($item); + } + } else { + /** @var $class $result */ + $result = new $class($result); + } + + $data = [ + 'success' => true, + 'result' => $result + ]; + } + + parent::__construct($data); + } + + /** + * @return bool + */ + public function isSuccessful() + { + return (bool) $this->getSuccess(); + } +} diff --git a/src/Entity/Set.php b/src/Entity/Set.php new file mode 100644 index 0000000..689007f --- /dev/null +++ b/src/Entity/Set.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class Set extends Entity +{ +} diff --git a/src/Entity/SetMaintainer.php b/src/Entity/SetMaintainer.php new file mode 100644 index 0000000..eb8a1ef --- /dev/null +++ b/src/Entity/SetMaintainer.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class SetMaintainer extends Entity +{ +} diff --git a/src/Entity/SetPost.php b/src/Entity/SetPost.php new file mode 100644 index 0000000..b283236 --- /dev/null +++ b/src/Entity/SetPost.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class SetPost extends Entity +{ +} diff --git a/src/Entity/Tag.php b/src/Entity/Tag.php new file mode 100644 index 0000000..2915d64 --- /dev/null +++ b/src/Entity/Tag.php @@ -0,0 +1,45 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @method string getName() + * @method string getId() + * @method string getCount() + * @method string getType() + * + * @property int type + * + * @package jacklul\E621API\Entity + */ +class Tag extends Entity +{ + /** + * @return null|string + */ + public function getTypeString() + { + switch ($this->type) { + case 0: + return 'general'; + case 1: + return 'artist'; + case 3: + return 'copyright'; + case 34: + return 'character'; + case 5: + return 'species'; + default: + return null; + } + } +} diff --git a/src/Entity/TagAlias.php b/src/Entity/TagAlias.php new file mode 100644 index 0000000..384e569 --- /dev/null +++ b/src/Entity/TagAlias.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class TagAlias extends Entity +{ +} diff --git a/src/Entity/TagImplication.php b/src/Entity/TagImplication.php new file mode 100644 index 0000000..d7f3f77 --- /dev/null +++ b/src/Entity/TagImplication.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class TagImplication extends Entity +{ +} diff --git a/src/Entity/Ticket.php b/src/Entity/Ticket.php new file mode 100644 index 0000000..744537b --- /dev/null +++ b/src/Entity/Ticket.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class Ticket extends Entity +{ +} diff --git a/src/Entity/User.php b/src/Entity/User.php new file mode 100644 index 0000000..ff23736 --- /dev/null +++ b/src/Entity/User.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class User extends Entity +{ +} diff --git a/src/Entity/UserRecord.php b/src/Entity/UserRecord.php new file mode 100644 index 0000000..7264a2d --- /dev/null +++ b/src/Entity/UserRecord.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class UserRecord extends Entity +{ +} diff --git a/src/Entity/Wiki.php b/src/Entity/Wiki.php new file mode 100644 index 0000000..70b191d --- /dev/null +++ b/src/Entity/Wiki.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Entity; + +/** + * @package jacklul\E621API\Entity + */ +class Wiki extends Entity +{ +} diff --git a/tests/E621Test.php b/tests/E621Test.php new file mode 100644 index 0000000..01e2644 --- /dev/null +++ b/tests/E621Test.php @@ -0,0 +1,74 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace jacklul\E621API\Tests; + +use jacklul\E621API\E621; +use PHPUnit\Framework\TestCase; +use InvalidArgumentException; + +/** + * @TODO test every public API method + * + * @package jacklul\E621API\Tests + */ +final class E621Test extends TestCase +{ + /** + * @var E621 + */ + private $api; + + protected function setUp() + { + $this->api = new E621('PHPUnit @ ' . php_uname()); + } + + protected function tearDown() + { + $this->api = null; + } + + public function testConstructWithoutUserAgent() + { + $this->expectException(\ArgumentCountError::class); + new E621(); + } + + public function testConstructWithInvalidCustomOptions() + { + $this->expectException(\TypeError::class); + new E621('test', ''); + } + + public function debugLogHandler($text) + { + } + + public function testSetDebugLogHandler() + { + $this->api->setDebugLogHandler([$this, 'debugLogHandler']); + + $this->expectException(InvalidArgumentException::class); + $this->api->setDebugLogHandler(['InvalidClass', 'debugLogHandler']); + } + + public function requestProgressHandler() + { + } + + public function testSetRequestProgressHandler() + { + $this->api->setRequestProgressHandler([$this, 'requestProgressHandler']); + + $this->expectException(InvalidArgumentException::class); + $this->api->setRequestProgressHandler(['InvalidClass', 'requestProgressHandler']); + } +}