diff --git a/.phpunit.result.cache b/.phpunit.result.cache
new file mode 100644
index 0000000..36b74f0
--- /dev/null
+++ b/.phpunit.result.cache
@@ -0,0 +1 @@
+C:37:"PHPUnit\Runner\DefaultTestResultCache":5600:{a:2:{s:7:"defects";a:35:{s:70:"CoinbaseCommerce\Tests\ApiClientTest::testFailOnGetInstanceWithoutInit";i:4;s:56:"CoinbaseCommerce\Tests\ApiClientTest::testInitWithParams";i:4;s:55:"CoinbaseCommerce\Tests\ApiClientTest::testCorrectReinit";i:4;s:64:"CoinbaseCommerce\Tests\ApiCollectionListTest::testInitCollection";i:4;s:55:"CoinbaseCommerce\Tests\ApiResourceTest::testRefreshFrom";i:4;s:60:"CoinbaseCommerce\Tests\ApiResourceTest::testUpdateAttributes";i:4;s:59:"CoinbaseCommerce\Tests\ApiResourceTest::testDeleteAttribute";i:4;s:59:"CoinbaseCommerce\Tests\ApiResourceTest::testDirtyAttributes";i:4;s:59:"CoinbaseCommerce\Tests\ApiResourceTest::testClearAttributes";i:4;s:56:"CoinbaseCommerce\Tests\ExceptionsTest::testApiExceptions";i:4;s:61:"CoinbaseCommerce\Tests\Resources\ChargeTest::testInsertMethod";i:4;s:59:"CoinbaseCommerce\Tests\Resources\ChargeTest::testSaveMethod";i:4;s:65:"CoinbaseCommerce\Tests\Resources\ChargeTest::testSaveMethodWithId";i:4;s:61:"CoinbaseCommerce\Tests\Resources\ChargeTest::testCreateMethod";i:4;s:62:"CoinbaseCommerce\Tests\Resources\ChargeTest::testRefreshMethod";i:4;s:63:"CoinbaseCommerce\Tests\Resources\ChargeTest::testRetrieveMethod";i:4;s:59:"CoinbaseCommerce\Tests\Resources\ChargeTest::testListMethod";i:4;s:58:"CoinbaseCommerce\Tests\Resources\ChargeTest::testAllMethod";i:4;s:62:"CoinbaseCommerce\Tests\Resources\ChargeTest::testResolveMethod";i:4;s:61:"CoinbaseCommerce\Tests\Resources\ChargeTest::testCancelMethod";i:4;s:64:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testRefreshMethod";i:4;s:65:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testRetrieveMethod";i:4;s:61:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testListMethod";i:4;s:63:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testInsertMethod";i:4;s:67:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testInsertSaveMethod";i:4;s:63:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testCreateMethod";i:4;s:63:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testUpdateMethod";i:4;s:67:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testUpdateByIdMethod";i:4;s:67:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testUpdateSaveMethod";i:4;s:61:"CoinbaseCommerce\Tests\Resources\EventTest::testRefreshMethod";i:4;s:62:"CoinbaseCommerce\Tests\Resources\EventTest::testRetrieveMethod";i:4;s:58:"CoinbaseCommerce\Tests\Resources\EventTest::testListMethod";i:4;s:64:"CoinbaseCommerce\Tests\WebhookTest::testFailedOnInvalidSecretKey";i:4;s:74:"CoinbaseCommerce\Tests\WebhookTest::testThrowExceptionOnInvalidJsonPayload";i:4;s:70:"CoinbaseCommerce\Tests\WebhookTest::testThrowExceptionOnNoEventPayload";i:4;}s:5:"times";a:39:{s:70:"CoinbaseCommerce\Tests\ApiClientTest::testFailOnGetInstanceWithoutInit";d:0.008;s:56:"CoinbaseCommerce\Tests\ApiClientTest::testInitWithParams";d:0.001;s:55:"CoinbaseCommerce\Tests\ApiClientTest::testCorrectReinit";d:0.001;s:64:"CoinbaseCommerce\Tests\ApiCollectionListTest::testInitCollection";d:0.03;s:55:"CoinbaseCommerce\Tests\ApiResourceTest::testRefreshFrom";d:0;s:60:"CoinbaseCommerce\Tests\ApiResourceTest::testUpdateAttributes";d:0;s:59:"CoinbaseCommerce\Tests\ApiResourceTest::testDeleteAttribute";d:0.001;s:59:"CoinbaseCommerce\Tests\ApiResourceTest::testDirtyAttributes";d:0;s:59:"CoinbaseCommerce\Tests\ApiResourceTest::testClearAttributes";d:0;s:56:"CoinbaseCommerce\Tests\ExceptionsTest::testApiExceptions";d:0.008;s:61:"CoinbaseCommerce\Tests\Resources\ChargeTest::testInsertMethod";d:0.001;s:59:"CoinbaseCommerce\Tests\Resources\ChargeTest::testSaveMethod";d:0.001;s:65:"CoinbaseCommerce\Tests\Resources\ChargeTest::testSaveMethodWithId";d:0;s:61:"CoinbaseCommerce\Tests\Resources\ChargeTest::testCreateMethod";d:0.001;s:62:"CoinbaseCommerce\Tests\Resources\ChargeTest::testRefreshMethod";d:0.001;s:63:"CoinbaseCommerce\Tests\Resources\ChargeTest::testRetrieveMethod";d:0.001;s:59:"CoinbaseCommerce\Tests\Resources\ChargeTest::testListMethod";d:0.002;s:58:"CoinbaseCommerce\Tests\Resources\ChargeTest::testAllMethod";d:0.001;s:62:"CoinbaseCommerce\Tests\Resources\ChargeTest::testResolveMethod";d:0.001;s:61:"CoinbaseCommerce\Tests\Resources\ChargeTest::testCancelMethod";d:0.001;s:64:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testRefreshMethod";d:0.001;s:65:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testRetrieveMethod";d:0.001;s:61:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testListMethod";d:0.001;s:63:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testInsertMethod";d:0.001;s:67:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testInsertSaveMethod";d:0.001;s:63:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testCreateMethod";d:0.001;s:63:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testUpdateMethod";d:0.001;s:67:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testUpdateByIdMethod";d:0.001;s:67:"CoinbaseCommerce\Tests\Resources\CheckoutTest::testUpdateSaveMethod";d:0.001;s:61:"CoinbaseCommerce\Tests\Resources\EventTest::testRefreshMethod";d:0.001;s:62:"CoinbaseCommerce\Tests\Resources\EventTest::testRetrieveMethod";d:0.001;s:58:"CoinbaseCommerce\Tests\Resources\EventTest::testListMethod";d:0.001;s:53:"CoinbaseCommerce\Tests\UtilTest::testHashEqualSuccess";d:0;s:42:"CoinbaseCommerce\Tests\UtilTest::testEqual";d:0;s:52:"CoinbaseCommerce\Tests\UtilTest::testGetResourcePath";d:0;s:62:"CoinbaseCommerce\Tests\WebhookTest::testSuccessfullyVerifyBody";d:0.001;s:64:"CoinbaseCommerce\Tests\WebhookTest::testFailedOnInvalidSecretKey";d:0;s:74:"CoinbaseCommerce\Tests\WebhookTest::testThrowExceptionOnInvalidJsonPayload";d:0;s:70:"CoinbaseCommerce\Tests\WebhookTest::testThrowExceptionOnNoEventPayload";d:0;}}}
\ No newline at end of file
diff --git a/composer.json b/composer.json
index 1bb9810..83a0ac6 100644
--- a/composer.json
+++ b/composer.json
@@ -1,45 +1,45 @@
{
- "name": "coinbase/coinbase-commerce",
- "description": "Coinbase Commerce API library",
- "keywords": [
- "bitcoin",
- "coinbase-commerce",
- "coinbase",
- "ethereum",
- "litecoin"
- ],
- "homepage": "https://commerce.coinbase.com/",
- "type": "library",
- "license": "Apache-2.0",
- "autoload": {
- "psr-4": {
- "CoinbaseCommerce\\": "src/"
+ "name": "coinbase/coinbase-commerce",
+ "description": "Coinbase Commerce API library",
+ "keywords": [
+ "bitcoin",
+ "coinbase-commerce",
+ "coinbase",
+ "ethereum",
+ "litecoin"
+ ],
+ "homepage": "https://commerce.coinbase.com/",
+ "type": "library",
+ "license": "Apache-2.0",
+ "autoload": {
+ "psr-4": {
+ "CoinbaseCommerce\\": "src/"
+ }
+ },
+ "autoload-dev": {
+ "psr-4": {
+ "CoinbaseCommerce\\Tests\\": "tests/"
+ }
+ },
+ "require": {
+ "php": ">=8.1",
+ "guzzlehttp/guzzle": "^7.0.1",
+ "psr/http-message": "^1.0"
+ },
+ "require-dev": {
+ "squizlabs/php_codesniffer": "3.*",
+ "phpunit/phpunit": "9.5"
+ },
+ "scripts": {
+ "lint": "./vendor/bin/phpcs",
+ "test": "./vendor/bin/phpunit --verbose",
+ "coverage": "./vendor/bin/phpunit --coverage-text"
+ },
+ "archive": {
+ "exclude": [
+ "/tests",
+ "/examples",
+ "/.circleci"
+ ]
}
- },
- "autoload-dev": {
- "psr-4": {
- "CoinbaseCommerce\\Tests\\": "tests/"
- }
- },
- "require": {
- "php": ">=5.4.0",
- "guzzlehttp/guzzle": "~5.0|~6.0",
- "psr/http-message": "^1.0"
- },
- "require-dev": {
- "phpunit/phpunit": "^4.7",
- "squizlabs/php_codesniffer": "3.*"
- },
- "scripts": {
- "lint": "./vendor/bin/phpcs",
- "test": "./vendor/bin/phpunit --verbose",
- "coverage": "./vendor/bin/phpunit --coverage-text"
- },
- "archive": {
- "exclude": [
- "/tests",
- "/examples",
- "/.circleci"
- ]
- }
}
diff --git a/phpunit.xml b/phpunit.xml
index 6c84ef8..dca0e0f 100644
--- a/phpunit.xml
+++ b/phpunit.xml
@@ -8,7 +8,6 @@
convertWarningsToExceptions="true"
processIsolation="false"
stopOnFailure="false"
- syntaxCheck="false"
>
@@ -16,12 +15,4 @@
./tests/BaseTest.php
-
-
- ./src
-
- ./vendor
-
-
-
-
\ No newline at end of file
+
diff --git a/src/ApiClient.php b/src/ApiClient.php
index 0396c05..6139ee5 100644
--- a/src/ApiClient.php
+++ b/src/ApiClient.php
@@ -21,10 +21,7 @@ class ApiClient
self::TIMEOUT_PARAM => 3
];
- /**
- * @var ApiClient
- */
- private static $instance;
+ private static ApiClient $instance;
/**
* @var
@@ -41,10 +38,7 @@ class ApiClient
*/
private $httpClient;
- /**
- * @var boolean
- */
- private $verifySSL = true ;
+ private bool $verifySSL = true ;
/**
* ApiClient constructor.
@@ -58,15 +52,11 @@ private function __clone()
}
/**
- * @param string $apiKey
- * @param null|string $baseUrl
- * @param null|string $apiVersion
- * @param null|integer $timeout
- * @return ApiClient
+ * @throws \Exception
*/
- public static function init($apiKey, $baseUrl = null, $apiVersion = null, $timeout = null)
+ public static function init(string $apiKey, ?string $baseUrl = null, ?string $apiVersion = null, ?int $timeout = null): ApiClient
{
- if (!self::$instance) {
+ if (!isset(self::$instance) || !self::$instance) {
self::$instance = new self();
}
@@ -79,46 +69,34 @@ public static function init($apiKey, $baseUrl = null, $apiVersion = null, $timeo
}
/**
- * @return ApiClient
* @throws \Exception
*/
- public static function getInstance()
+ public static function getInstance(): ApiClient
{
- if (!self::$instance) {
+ if (!isset(self::$instance) || !self::$instance) {
throw new \Exception('Please init client first.');
}
return self::$instance;
}
- /**
- * @param string $key
- * @return mixed
- */
- private function getParam($key)
+ private function getParam(string $key)
{
if (array_key_exists($key, $this->params)) {
return $this->params[$key];
}
}
- /**
- * @param string $key
- * @param mixed $value
- * @return $this
- */
- private function setParam($key, $value)
+ private function setParam(string $key, mixed $value): self
{
$this->params[$key] = $value;
return $this;
}
/**
- * @param string $value
- * @return $this
* @throws \Exception
*/
- public function setApiKey($value)
+ public function setApiKey(string $value): self
{
if (empty($value)) {
throw new \Exception('Api Key is required');
@@ -128,21 +106,14 @@ public function setApiKey($value)
return $this;
}
- /**
- * @return mixed
- */
- public function getApiKey()
+ public function getApiKey(): mixed
{
return $this->getParam(self::API_KEY_PARAM);
}
- /**
- * @param string $value
- * @return $this
- */
- public function setBaseUrl($value)
+ public function setBaseUrl(?string $value): self
{
- if (!empty($value) && \is_string($value)) {
+ if (!empty($value)) {
if (substr($value, -1) !== '/') {
$value .= '/';
}
@@ -153,65 +124,42 @@ public function setBaseUrl($value)
return $this;
}
- /**
- * @return mixed
- */
- public function getBaseUrl()
+ public function getBaseUrl(): mixed
{
return $this->getParam(self::BASE_API_URL_PARAM);
}
- /**
- * @param string $value
- * @return $this
- */
- public function setApiVersion($value)
+ public function setApiVersion(?string $value): self
{
- if (!empty($value) && \is_string($value)) {
+ if (!empty($value)) {
$this->setParam(self::API_VERSION_PARAM, $value);
}
return $this;
}
- /**
- * @return mixed
- */
- public function getApiVersion()
+ public function getApiVersion(): mixed
{
return $this->getParam(self::API_VERSION_PARAM);
}
- /**
- * @param integer $value
- * @return $this
- */
- public function setTimeout($value)
+ public function setTimeout(?int $value): self
{
- if (!empty($value) && \is_numeric($value)) {
+ if (!empty($value)) {
$this->setParam(self::TIMEOUT_PARAM, $value);
}
return $this;
}
- /**
- * @return mixed
- */
public function getTimeout()
{
return $this->getParam(self::TIMEOUT_PARAM);
}
- /**
- * @param array $query
- * @param array $body
- * @param array $headers
- * @return array
- */
- private function generateRequestOptions($query = [], $body = [], $headers = [])
+ private function generateRequestOptions(array $query = [], array $body = [], array $headers = []): array
{
- return $options = [
+ return [
'headers' => array_merge(
[
'Content-Type' => 'application/json',
@@ -228,13 +176,7 @@ private function generateRequestOptions($query = [], $body = [], $headers = [])
];
}
- /**
- * @param string $method
- * @param string $path
- * @param array $options
- * @return ApiResponse
- */
- private function makeRequest($method, $path, $options)
+ private function makeRequest(string $method, string $path, array $options): ApiResponse
{
try {
$path = Util::joinPath($this->getParam('baseApiUrl'), $path);
@@ -256,7 +198,7 @@ private function makeRequest($method, $path, $options)
}
}
- public function getHttpClient()
+ public function getHttpClient(): Client
{
if (!isset($this->httpClient)) {
$this->httpClient = new Client(['verify' => $this->verifySSL]);
@@ -265,80 +207,46 @@ public function getHttpClient()
return $this->httpClient;
}
- /**
- * @param $logger
- */
- public function setLogger($logger)
+ public function setLogger($logger): void
{
$this->logger = $logger;
}
- /**
- * @param $path
- * @param array $queryParams
- * @param array $headers
- * @return ApiResponse
- */
- public function get($path, $queryParams = [], $headers = [])
+ public function get(string $path, array $queryParams = [], array $headers = []): ApiResponse
{
$options = $this->generateRequestOptions($queryParams, $headers);
return $this->makeRequest('GET', $path, $options);
}
- /**
- * @param string $path
- * @param array $body
- * @param array $headers
- * @return ApiResponse
- */
- public function post($path, $body, $headers)
+ public function post(string $path, array $body, array $headers): ApiResponse
{
$options = $this->generateRequestOptions([], $body, $headers = []);
return $this->makeRequest('POST', $path, $options);
}
- /**
- * @param string $path
- * @param array $headers
- * @return ApiResponse
- */
- public function put($path, $body, $headers)
+ public function put(string $path, array $body, array $headers): ApiResponse
{
$options = $this->generateRequestOptions([], $body, $headers = []);
return $this->makeRequest('PUT', $path, $options);
}
- /**
- * @param string $path
- * @param array $headers
- * @return ApiResponse
- */
- public function delete($path, $headers = [])
+ public function delete(string $path, array $headers = []): ApiResponse
{
$options = $this->generateRequestOptions([], [], $headers);
return $this->makeRequest('DELETE', $path, $options);
}
- /**
- * @param ApiResponse $response
- */
- public function setLastResponse($response)
+ public function setLastResponse(ApiResponse $response): void
{
$this->response = $response;
}
- /**
- * @return ApiResponse
- */
- public function getLastResponse()
+ public function getLastResponse(): ApiResponse
{
return $this->response;
}
- /**
- * @param ApiResponse $response
- */
- public function logWarnings($response)
+ public function logWarnings(ApiResponse $response): void
{
if (!$this->logger) {
return;
@@ -355,12 +263,12 @@ public function logWarnings($response)
}
}
- public static function getClassName()
+ public static function getClassName(): string
{
return get_called_class();
}
- public function verifySsl($verify)
+ public function verifySsl($verify): void
{
if(!is_bool($verify)) {
return;
diff --git a/src/ApiErrorFactory.php b/src/ApiErrorFactory.php
index 19f36e0..85fa056 100644
--- a/src/ApiErrorFactory.php
+++ b/src/ApiErrorFactory.php
@@ -14,21 +14,10 @@
class ApiErrorFactory
{
- /**
- * @var array
- */
- private static $mapErrorMessageToClass = [];
+ private static array $mapErrorMessageToClass = [];
+ private static array $mapErrorCodeToClass = [];
- /**
- * @var array
- */
- private static $mapErrorCodeToClass = [];
-
- /**
- * @param $message
- * @return mixed|null
- */
- public static function getErrorClassByMessage($message)
+ public static function getErrorClassByMessage(mixed $message): mixed
{
if (empty(self::$mapErrorMessageToClass)) {
self::$mapErrorMessageToClass = [
@@ -42,14 +31,10 @@ public static function getErrorClassByMessage($message)
];
}
- return isset(self::$mapErrorMessageToClass[$message]) ? self::$mapErrorMessageToClass[$message]: null;
+ return self::$mapErrorMessageToClass[$message] ?? null;
}
- /**
- * @param $code
- * @return mixed|null
- */
- public static function getErrorClassByCode($code)
+ public static function getErrorClassByCode(int $code): mixed
{
if (empty(self::$mapErrorCodeToClass)) {
self::$mapErrorCodeToClass = [
@@ -62,20 +47,17 @@ public static function getErrorClassByCode($code)
];
}
- return isset(self::$mapErrorCodeToClass[$code]) ? self::$mapErrorCodeToClass[$code]: null;
+ return self::$mapErrorCodeToClass[$code] ?? null;
}
- /**
- * @param RequestException $exception
- */
- public static function create($exception)
+ public static function create(RequestException $exception): mixed
{
$response = $exception->getResponse();
$request = $exception->getRequest();
$code = $exception->getCode();
$data = $response ? json_decode($response->getBody(), true) : null;
- $errorMessage = isset($data['error']['message']) ? $data['error']['message'] : $exception->getMessage();
- $errorId = isset($data['error']['type']) ? $data['error']['type'] : null;
+ $errorMessage = $data['error']['message'] ?? $exception->getMessage();
+ $errorId = $data['error']['type'] ?? null;
$errorClass = self::getErrorClassByMessage($errorId) ?: self::getErrorClassByCode($code) ?: ApiException::getClassName();
diff --git a/src/ApiResourceList.php b/src/ApiResourceList.php
index 3722fa7..df13333 100644
--- a/src/ApiResourceList.php
+++ b/src/ApiResourceList.php
@@ -7,40 +7,18 @@ class ApiResourceList extends \ArrayObject
const PREV_CURSOR = 'ending_before';
const NEXT_CURSOR = 'starting_after';
- private static $apiClient;
+ private static ApiClient $apiClient;
- /**
- * @var array
- */
- protected $items = [];
-
- /**
- * @var array
- */
- protected $pagination = [];
-
- /**
- * @var string
- */
- protected $resourceClass;
-
- /**
- * @var array
- */
- protected $headers = [];
-
- /**
- * @var array
- */
- protected $params = [];
+ protected array $items = [];
+ protected array $pagination = [];
+ protected mixed $resourceClass;
+ protected array $headers = [];
+ protected array $params = [];
- /**
- * ApiResourceList constructor.
- * @param array $items
- * @param array $pagination
- */
- public function __construct($resourceClass, $items, $pagination, $params, $headers)
+ public function __construct(mixed $resourceClass, array $items, array $pagination, array $params, array $headers)
{
+ parent::__construct();
+
$this->resourceClass = $resourceClass;
$this->items = $items;
$this->pagination = $pagination;
@@ -48,50 +26,32 @@ public function __construct($resourceClass, $items, $pagination, $params, $heade
$this->headers = $headers;
}
- /**
- * @param $items
- */
- public function setItems($items)
+ public function setItems(array $items): void
{
$this->items = $items;
}
- /**
- * @param $pagination
- */
- public function setPagination($pagination)
+ public function setPagination(array $pagination): void
{
$this->pagination = $pagination;
}
- /**
- * @return array
- */
- public function getPagination()
+ public function getPagination(): array
{
return $this->pagination;
}
- /**
- * @return array
- */
- public function getParams()
+ public function getParams(): array
{
return $this->params;
}
- /**
- * @return bool
- */
- public function hasNext()
+ public function hasNext(): bool
{
return isset($this->pagination[self::CURSOR_PARAM][1]) && null !== $this->pagination[self::CURSOR_PARAM][1];
}
- /**
- * @return bool
- */
- public function loadNext()
+ public function loadNext(): bool
{
if (!$this->hasNext()) {
return false;
@@ -105,18 +65,12 @@ public function loadNext()
return true;
}
- /**
- * @return bool
- */
- public function hasPrev()
+ public function hasPrev(): bool
{
return isset($this->pagination[self::CURSOR_PARAM][0]) && null !== $this->pagination[self::CURSOR_PARAM][0];
}
- /**
- * @return bool
- */
- public function loadPrev()
+ public function loadPrev(): bool
{
if (!$this->hasPrev()) {
return false;
@@ -130,7 +84,7 @@ public function loadPrev()
return true;
}
- protected function loadPage($params)
+ protected function loadPage($params): void
{
$client = self::getClient();
$resourceClass = $this->resourceClass;
@@ -139,7 +93,7 @@ protected function loadPage($params)
$response = $client->get($path, $params, $this->headers);
$responseData = $response->bodyArray;
- $this->pagination = isset($responseData['pagination']) ? $responseData['pagination'] : [];
+ $this->pagination = $responseData['pagination'] ?? [];
$this->items = [];
if (isset($responseData['data'])) {
@@ -152,49 +106,52 @@ function ($item) {
}
}
- public function offsetGet($key)
+ public function offsetGet(mixed $key): mixed
{
return $this->items[$key];
}
- public function offsetSet($key, $value)
+ public function offsetSet(mixed $key, mixed $value): void
{
null === $key ? array_push($this->items, $value) : $this->items[$key] = $value;
}
- public function count()
+ public function count(): int
{
return count($this->items);
}
- public function countAll()
+ public function countAll(): mixed
{
if (isset($this->pagination['total'])) {
return $this->pagination['total'];
}
}
- public function asort()
+ public function asort(int $flags = SORT_REGULAR): bool
{
- asort($this->items);
+ return asort($this->items, $flags);
}
- public function ksort()
+ public function ksort(int $flags = SORT_REGULAR): bool
{
- ksort($this->items);
+ return ksort($this->items, $flags);
}
- public function offsetUnset($key)
+ public function offsetUnset($key): void
{
unset($this->items[$key]);
}
- public function getIterator()
+ public function getIterator(): \ArrayIterator
{
return new \ArrayIterator($this->items);
}
- public static function getClient()
+ /**
+ * @throws \Exception
+ */
+ public static function getClient(): ApiClient
{
if (self::$apiClient) {
return self::$apiClient;
@@ -202,12 +159,12 @@ public static function getClient()
return ApiClient::getInstance();
}
- public function setClient($client)
+ public static function setClient($client): void
{
self::$apiClient = $client;
}
- public static function getClassName()
+ public static function getClassName(): string
{
return get_called_class();
}
diff --git a/src/ApiResponse.php b/src/ApiResponse.php
index 792b939..264a83b 100644
--- a/src/ApiResponse.php
+++ b/src/ApiResponse.php
@@ -1,6 +1,8 @@
code = $response->getStatusCode();
- $this->headers = $response->getHeaders();
- $this->body = (string)$response->getBody();
- $lowerCaseKeys = array_change_key_case($this->headers);
- $this->requestId = array_key_exists(strtolower(self::REQUEST_ID_HEADER), $lowerCaseKeys)
- && !empty($lowerCaseKeys[strtolower(self::REQUEST_ID_HEADER)][0]) ?
- $lowerCaseKeys[strtolower(self::REQUEST_ID_HEADER)][0] : null;
+ $this->code = $response->getStatusCode();
+ $this->headers = $response->getHeaders();
+ $this->body = (string)$response->getBody();
+ $lowerCaseKeys = array_change_key_case($this->headers);
+ $this->requestId = array_key_exists(strtolower(self::REQUEST_ID_HEADER), $lowerCaseKeys)
+ && !empty($lowerCaseKeys[strtolower(self::REQUEST_ID_HEADER)][0]) ?
+ $lowerCaseKeys[strtolower(self::REQUEST_ID_HEADER)][0] : null;
- $this->bodyArray = !empty($this->body)? \json_decode($this->body, true): null;
- }
+ $this->bodyArray = !empty($this->body)? \json_decode($this->body, true): null;
}
}
diff --git a/src/Exceptions/InvalidResponseException.php b/src/Exceptions/InvalidResponseException.php
index 5e9db44..0bc95c9 100644
--- a/src/Exceptions/InvalidResponseException.php
+++ b/src/Exceptions/InvalidResponseException.php
@@ -3,6 +3,11 @@
class InvalidResponseException extends CoinbaseException
{
+ /**
+ * @var mixed|string
+ */
+ private mixed $body;
+
public function __construct($message = '', $body = '')
{
parent::__construct($message);
diff --git a/src/Resources/ApiResource.php b/src/Resources/ApiResource.php
index 4ddf20c..d271987 100644
--- a/src/Resources/ApiResource.php
+++ b/src/Resources/ApiResource.php
@@ -136,37 +136,37 @@ protected static function getClient()
return ApiClient::getInstance();
}
- public function offsetGet($key)
+ public function offsetGet($key): mixed
{
return $this->__get($key);
}
- public function offsetSet($key, $value)
+ public function offsetSet($key, $value): void
{
null === $key ? array_push($this->attributes, $value) : $this->attributes[$key] = $value;
}
- public function count()
+ public function count(): int
{
return count($this->attributes);
}
- public function asort()
+ public function asort(int $flags = SORT_REGULAR): bool
{
asort($this->attributes);
}
- public function ksort()
+ public function ksort(int $flags = SORT_REGULAR): bool
{
ksort($this->attributes);
}
- public function offsetUnset($key)
+ public function offsetUnset($key): void
{
unset($this->attributes[$key]);
}
- public function getIterator()
+ public function getIterator(): \Iterator
{
return new \ArrayIterator($this->attributes);
}
diff --git a/src/Util.php b/src/Util.php
index 32070a1..7ecd498 100644
--- a/src/Util.php
+++ b/src/Util.php
@@ -7,15 +7,12 @@
class Util
{
- private static $mapResourceByName = [];
+ private static array $mapResourceByName = [];
- /**
- * @param mixed $response
- */
- public static function convertToApiObject($response)
+ public static function convertToApiObject(mixed $response): mixed
{
if ($response instanceof ApiResponse) {
- $response = isset($response->bodyArray['data']) ? $response->bodyArray['data'] : null;
+ $response = $response->bodyArray['data'] ?? null;
}
if (is_array($response)) {
@@ -34,7 +31,7 @@ function (&$item) {
return $response;
}
- public static function getResourceClassByName($name)
+ public static function getResourceClassByName($name): mixed
{
if (empty(self::$mapResourceByName)) {
self::$mapResourceByName = [
@@ -44,13 +41,10 @@ public static function getResourceClassByName($name)
];
}
- return isset(self::$mapResourceByName[$name]) ? self::$mapResourceByName[$name] : null;
+ return self::$mapResourceByName[$name] ?? null;
}
- /**
- * @return string
- */
- public static function joinPath()
+ public static function joinPath(): string
{
$arguments = func_get_args();
array_walk(
@@ -63,12 +57,7 @@ function (&$item) {
return implode('/', $arguments);
}
- /**
- * @param mixed $prop1
- * @param mixed $prop2
- * @return bool
- */
- public static function equal($prop1, $prop2)
+ public static function equal(mixed $prop1, mixed $prop2): bool
{
if (is_array($prop1)) {
foreach ($prop1 as $key => $value) {
@@ -89,12 +78,7 @@ public static function equal($prop1, $prop2)
return $prop1 === $prop2;
}
- /**
- * @param string $str1
- * @param string $str2
- * @return bool
- */
- public static function hashEqual($str1, $str2)
+ public static function hashEqual(string $str1, string $str2): bool
{
if (function_exists('hash_equals')) {
return \hash_equals($str1, $str2);
diff --git a/src/Webhook.php b/src/Webhook.php
index f1d3698..58eac46 100644
--- a/src/Webhook.php
+++ b/src/Webhook.php
@@ -7,7 +7,11 @@
class Webhook
{
- public static function buildEvent($payload, $sigHeader, $secret)
+ /**
+ * @throws SignatureVerificationException
+ * @throws InvalidResponseException
+ */
+ public static function buildEvent(string $payload, string $sigHeader, string $secret): Event
{
$data = null;
@@ -26,7 +30,10 @@ public static function buildEvent($payload, $sigHeader, $secret)
return new Event($data['event']);
}
- public static function verifySignature($payload, $sigHeader, $secret)
+ /**
+ * @throws SignatureVerificationException
+ */
+ public static function verifySignature(string $payload, string $sigHeader, string $secret): void
{
$computedSignature = \hash_hmac('sha256', $payload, $secret);
diff --git a/tests/ApiClientTest.php b/tests/ApiClientTest.php
index ba1f694..bb6d45b 100644
--- a/tests/ApiClientTest.php
+++ b/tests/ApiClientTest.php
@@ -6,17 +6,15 @@
class ApiClientTest extends TestCase
{
- public function setUp()
+ public function setUp(): void
{
parent::setUp();
}
- /**
- * @expectedException \Exception
- * @expectedExceptionMessage Please init client first.
- */
public function testFailOnGetInstanceWithoutInit()
{
+ $this->expectException(\Exception::class);
+ $this->expectExceptionMessage("Please init client first.");
ApiClient::getInstance();
}
diff --git a/tests/ApiResourceTest.php b/tests/ApiResourceTest.php
index 787c965..c47cc90 100644
--- a/tests/ApiResourceTest.php
+++ b/tests/ApiResourceTest.php
@@ -2,11 +2,14 @@
namespace CoinbaseCommerce\Tests;
use CoinbaseCommerce\Resources\ApiResource;
+use PHPUnit\Framework\MockObject\MockObject;
use PHPUnit\Framework\TestCase;
class ApiResourceTest extends TestCase
{
- public function setUp()
+ private MockObject $apiResourceStub;
+
+ public function setUp(): void
{
parent::setUp();
$this->apiResourceStub = $this->getMockForAbstractClass(ApiResource::getClassName());
@@ -62,12 +65,12 @@ public function testUpdateAttributes()
]
);
- $this->assertEquals('Test Name', $this->apiResourceStub->name);
- $this->assertEquals('value1', $this->apiResourceStub->meta['option1']);
- $this->apiResourceStub->name = 'New Name';
- $this->apiResourceStub->meta['option1'] = 'value2';
- $this->assertEquals('New Name', $this->apiResourceStub->name);
- $this->assertEquals('value2', $this->apiResourceStub->meta['option1']);
+ $this->assertEquals('Test Name', $this->apiResourceStub["name"]);
+ $this->assertEquals('value1', $this->apiResourceStub["meta"]['option1']);
+ $this->apiResourceStub["name"] = 'New Name';
+ $this->apiResourceStub["meta"]['option1'] = 'value2';
+ $this->assertEquals('New Name', $this->apiResourceStub["name"]);
+ $this->assertEquals('value2', $this->apiResourceStub["meta"]['option1']);
}
public function testDeleteAttribute()
diff --git a/tests/BaseTest.php b/tests/BaseTest.php
index d068a9b..62be0ad 100644
--- a/tests/BaseTest.php
+++ b/tests/BaseTest.php
@@ -16,7 +16,7 @@ class BaseTest extends TestCase
protected $logger;
- public function setUp()
+ public function setUp(): void
{
$this->initMockClient();
diff --git a/tests/Resources/ChargeTest.php b/tests/Resources/ChargeTest.php
index 87101bd..6a4124d 100644
--- a/tests/Resources/ChargeTest.php
+++ b/tests/Resources/ChargeTest.php
@@ -7,7 +7,7 @@
class ChargeTest extends BaseTest
{
- public function setUp()
+ public function setUp(): void
{
parent::setUp();
Charge::setClient($this->apiClient);
@@ -43,12 +43,10 @@ public function testSaveMethod()
$this->assertEquals('7C7V5ECK', $chargeObj->code);
}
- /**
- * @expectedException \Exception
- * @expectedExceptionMessage Update is not allowed
- */
public function testSaveMethodWithId()
{
+ $this->expectException(\Exception::class);
+ $this->expectExceptionMessage("Update is not allowed");
$this->appendRequest(200, $this->parseJsonFile('charge.json'));
$chargeObj = new Charge(
[
diff --git a/tests/Resources/CheckoutTest.php b/tests/Resources/CheckoutTest.php
index 3ca863e..29bc53f 100644
--- a/tests/Resources/CheckoutTest.php
+++ b/tests/Resources/CheckoutTest.php
@@ -10,7 +10,7 @@
class CheckoutTest extends BaseTest
{
- public function setUp()
+ public function setUp(): void
{
parent::setUp();
Checkout::setClient($this->apiClient);
diff --git a/tests/Resources/EventTest.php b/tests/Resources/EventTest.php
index f3a4cfa..99dda8c 100644
--- a/tests/Resources/EventTest.php
+++ b/tests/Resources/EventTest.php
@@ -8,7 +8,7 @@
class EventTest extends BaseTest
{
- public function setUp()
+ public function setUp(): void
{
parent::setUp();
Event::setClient($this->apiClient);
diff --git a/tests/WebhookTest.php b/tests/WebhookTest.php
index 69f3593..1d67c9b 100644
--- a/tests/WebhookTest.php
+++ b/tests/WebhookTest.php
@@ -1,13 +1,15 @@
assertEquals('charge:created', $event->type);
}
- /**
- * @expectedException \CoinbaseCommerce\Exceptions\SignatureVerificationException
- */
public function testFailedOnInvalidSecretKey()
{
+ $this->expectException(SignatureVerificationException::class);
$invalidSecret = '30291a20-0bd1-4267-9b0f-e6e7b123c0bg';
$payload = '{"id":1,"scheduled_for":"2017-01-31T20:50:02Z","attempt_number":1,"event":{"id":"24934862-d980-46cb-9402-43c81b0cdba6","type":"charge:created","api_version":"2018-03-22","created_at":"2017-01-31T20:49:02Z","data":{"code":"66BEOV2A","name":"The Sovereign Individual","description":"Mastering the Transition to the Information Age","hosted_url":"https://commerce.coinbase.com/charges/66BEOV2A","created_at":"2017-01-31T20:49:02Z","expires_at":"2017-01-31T21:04:02Z","timeline":[{"time":"2017-01-31T20:49:02Z","status":"NEW"}],"metadata":{},"pricing_type":"no_price","payments":[],"addresses":{"bitcoin":"0000000000000000000000000000000000","ethereum":"0x0000000000000000000000000000000000000000","litecoin":"3000000000000000000000000000000000","bitcoincash":"bitcoincash:000000000000000000000000000000000000000000"}}}}';
$headerSignature = '8be7742c7d372f08a6a3224edadf18a22b65fa9e28f3f2de97376cdaa092590d';
@@ -36,12 +36,10 @@ public function testFailedOnInvalidSecretKey()
Webhook::buildEvent($payload, $headerSignature, $invalidSecret);
}
- /**
- * @expectedException \CoinbaseCommerce\Exceptions\InvalidResponseException
- * @expectedExceptionMessage Invalid payload provided. No JSON object could be decoded
- */
public function testThrowExceptionOnInvalidJsonPayload()
{
+ $this->expectException(InvalidResponseException::class);
+ $this->expectExceptionMessage("Invalid payload provided. No JSON object could be decoded");
$secret = '30291a20-0bd1-4267-9b0f-e6e7b123c0bf';
$invalidPayload = 'Not json';
$headerSignature = '8be7742c7d372f08a6a3224edadf18a22b65fa9e28f3f2de97376cdaa092590d';
@@ -49,12 +47,10 @@ public function testThrowExceptionOnInvalidJsonPayload()
Webhook::buildEvent($invalidPayload, $headerSignature, $secret);
}
- /**
- * @expectedException \CoinbaseCommerce\Exceptions\InvalidResponseException
- * @expectedExceptionMessage Invalid payload provided.
- */
public function testThrowExceptionOnNoEventPayload()
{
+ $this->expectException(InvalidResponseException::class);
+ $this->expectExceptionMessage("Invalid payload provided.");
$secret = '30291a20-0bd1-4267-9b0f-e6e7b123c0bf';
$invalidPayload = '{"id":1,"scheduled_for":"2017-01-31T20:50:02Z","attempt_number":1}';
$headerSignature = '8be7742c7d372f08a6a3224edadf18a22b65fa9e28f3f2de97376cdaa092590d';