From 202da5226cd0c8fbd8c386aaac5d8e3c6e8941c9 Mon Sep 17 00:00:00 2001 From: Simon Gabriel Date: Mon, 18 May 2020 14:03:26 +0200 Subject: [PATCH] Release 1.2.7.2 (#179) * [change] (PHPLIB-209) Add traceId to transactions and payment. * [Change] (PHPLIB-209) Fix several style issues. * [change] (PHPLIB-209) Add traceId tests. * [change] (PHPLIB-209) Update unit tests for traceId. * [change] (PHPLIB-209) Update changelog and version. * [change] (PHPLIB-209) Update CHANGELOG.md * [change] (PHPLIB-209) Fix tests. * Update src/Heidelpay.php Co-Authored-By: David Owusu <33735090+Ryouzanpaku@users.noreply.github.com> * Merge remote-tracking branch 'remotes/github/develop' into bugfix/PHPLIB-309/renaming-cc-holder-to-cardHolder (#171) * [bugfix] (PHPLIB-309) Rename Cards holder to cardHolder. * [change] (PHPLIB-209) Fix tests add update version and CHANGELOG.md * [change] (PHPLIB-309) Update test. * [change] (PHPLIB-309) Update unit test. * [change] (PHPLIB-309) Add unit tests to verify deprecated getter/setter. * [change] (PHPLIB-309) Add integration test to verify deprecated getter/setter. Co-authored-by: sixer1182 * [change] (PHPLIB-318) Refactor tests to fit latest API changes. (#176) Co-authored-by: sixer1182 * [change] (PHPLIB-300) Add description. (#172) Co-authored-by: sixer1182 * [change] (PHPLIB-307) Add email field to PayPal example. (#173) Co-authored-by: sixer1182 * change/PHPLIB-187/add-geolocation-to-card (#174) * [bugfix] (PHPLIB-309) Rename Cards holder to cardHolder. * [change] (PHPLIB-209) Fix tests add update version and CHANGELOG.md * [change] (PHPLIB-309) Update test. * [change] (PHPLIB-309) Update unit test. * [refactor] (PHPLIB-187) Geolocation: Move geolocation to trait. * [refactor] (PHPLIB-187) Geolocation: Add geolocation to card class. * [change] (PHPLIB-187) Fix styles. * [change] (PHPLIB-187) Update CHANGELOG.md * [change] (PHPLIB-187) Remove dead "code" * [change] (PHPLIB-187) Fix examples: Fix ids due to api changes. * [change] (PHPLIB-187) Fix examples: Fix ids due to api changes. Co-authored-by: sixer1182 * change/PHPLIB-304/update-webhook-support (#175) * [bugfix] (PHPLIB-309) Rename Cards holder to cardHolder. * [change] (PHPLIB-209) Fix tests add update version and CHANGELOG.md * [change] (PHPLIB-309) Update test. * [change] (PHPLIB-309) Update unit test. * [change] (PHPLIB-304) Update webhook events. * [change] (PHPLIB-304) Fix tests: Fix ids due to api changes. Co-authored-by: sixer1182 * change/PHPLIB-323/Update-errorcodes (#177) * [change] (PHPLIB-323) Update respons codes due to API changes. * [change] (PHPLIB-323) Update CHANGELOG.md * [change] (PHPLIB-323) Update respons codes due to API changes. * [change] (PHPLIB-323) Update respons codes due to API changes. Co-authored-by: sixer1182 * bugfix/PHPLIB-319/auth-has-empty-cancel-obj-when-payment-is-cancelled (#178) * [change] (PHPLIB-318) Refactor tests to fit latest API changes. * [change] (PHPLIB-323) Update respons codes due to API changes. * [change] (PHPLIB-323) Update CHANGELOG.md * [change] (PHPLIB-323) Update respons codes due to API changes. * [change] (PHPLIB-323) Update respons codes due to API changes. * [change] (PHPLIB-319) Do not add cancellation to authorization if it fails. * [refactor] (PHPLIB-319) Replace type hinting. * [refactor] (PHPLIB-319) Avoid adding the cancellation object twice. * [refactor] (PHPLIB-319) Update CHANGELOG.md * [refactor] (PHPLIB-319) Fix unit test. * [refactor] (PHPLIB-319) Fix CHANGELOG.md Co-authored-by: sixer1182 Co-authored-by: sixer1182 Co-authored-by: David Owusu <33735090+Ryouzanpaku@users.noreply.github.com> --- CHANGELOG.md | 19 +++++ examples/EmbeddedPayPage/Controller.php | 6 +- .../HirePurchaseDirectDebit/Controller.php | 2 +- examples/HostedPayPage/Controller.php | 4 +- examples/Invoice/Controller.php | 2 +- examples/InvoiceFactoring/Controller.php | 2 +- examples/InvoiceGuaranteed/Controller.php | 2 +- examples/PayPal/index.php | 4 + examples/Prepayment/Controller.php | 2 +- .../SepaDirectDebitGuaranteed/Controller.php | 2 +- src/Adapter/CurlAdapter.php | 3 +- src/Constants/ApiResponseCodes.php | 10 ++- src/Constants/WebhookEvents.php | 4 + src/Heidelpay.php | 14 ++-- src/Resources/AbstractHeidelpayResource.php | 11 +++ src/Resources/Customer.php | 16 +--- .../EmbeddedResources/GeoLocation.php | 2 +- src/Resources/Payment.php | 2 + src/Resources/PaymentTypes/Card.php | 38 ++++++++-- .../AbstractTransactionType.php | 2 + .../TransactionTypes/Authorization.php | 4 + src/Services/CancelService.php | 6 +- src/Traits/HasGeoLocation.php | 59 ++++++++++++++ src/Traits/HasTraceId.php | 55 ++++++++++++++ test/BasePaymentTest.php | 4 +- test/integration/BasketTest.php | 12 +-- test/integration/CustomerTest.php | 11 +-- test/integration/PaymentCancelTest.php | 9 ++- test/integration/PaymentTest.php | 10 ++- test/integration/PaymentTypes/CardTest.php | 41 +++++++++- .../PaymentTypes/InvoiceFactoringTest.php | 6 +- .../PaymentTypes/InvoiceGuaranteedTest.php | 4 +- test/integration/PaymentTypes/PaypageTest.php | 8 +- .../SepaDirectDebitGuaranteedTest.php | 4 +- .../PaymentTypes/SepaDirectDebitTest.php | 4 +- .../TransactionTypes/AuthorizationTest.php | 8 +- .../CancelAfterAuthorizationTest.php | 6 +- .../CancelAfterChargeTest.php | 9 +-- .../TransactionTypes/ChargeTest.php | 8 +- .../TransactionTypes/PayoutTest.php | 8 +- .../TransactionTypes/ShipmentTest.php | 12 ++- test/unit/Resources/CustomerTest.php | 4 +- test/unit/Resources/PaymentTest.php | 36 +++++++-- test/unit/Resources/PaymentTypes/CardTest.php | 76 ++++++++++++++++--- .../AbstractTransactionTypeTest.php | 39 +++++++++- test/unit/Services/HttpServiceTest.php | 2 +- test/unit/Services/PaymentServiceTest.php | 69 ++++++++++++----- 47 files changed, 519 insertions(+), 142 deletions(-) create mode 100644 src/Traits/HasGeoLocation.php create mode 100644 src/Traits/HasTraceId.php diff --git a/CHANGELOG.md b/CHANGELOG.md index 0807fe14..10309e24 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,6 +3,24 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/) and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.html). +## [1.2.7.2][1.2.7.2] + +### Fix +* Rename Cards property holder to cardHolder. +* Add cancellation object to authorization only if cancellation has been successful. + +### Change +* Fix some minor issues. +* Refactor tests due to API changes. +* Update response codes due to API changes. + +### Added +* TraceId property to payment and transactions. +* Email form field to PayPal example. +* Description to zgReferenceId setter/getter. +* Added geolocation to Card resource. +* Payout webhook events. + ## [1.2.7.1][1.2.7.1] ### Added @@ -394,3 +412,4 @@ The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/) a [1.2.6.0]: https://github.com/heidelpay/heidelpayPHP/compare/1.2.5.1..1.2.6.0 [1.2.7.0]: https://github.com/heidelpay/heidelpayPHP/compare/1.2.6.0..1.2.7.0 [1.2.7.1]: https://github.com/heidelpay/heidelpayPHP/compare/1.2.7.0..1.2.7.1 +[1.2.7.2]: https://github.com/heidelpay/heidelpayPHP/compare/1.2.7.1..1.2.7.2 diff --git a/examples/EmbeddedPayPage/Controller.php b/examples/EmbeddedPayPage/Controller.php index 9701e0b1..ca9d4e61 100644 --- a/examples/EmbeddedPayPage/Controller.php +++ b/examples/EmbeddedPayPage/Controller.php @@ -67,14 +67,14 @@ $paypage->setLogoImage('https://dev.heidelpay.com/devHeidelpay_400_180.jpg') ->setShopName('My Test Shop') ->setTagline('Try and stop us from being awesome!') - ->setOrderId('OrderNr' . microtime(true)) - ->setInvoiceId('InvoiceNr' . microtime(true)); + ->setOrderId('o' . microtime(true)) + ->setInvoiceId('i' . microtime(true)); // ... in order to enable FlexiPay Rate (Hire Purchase) you will need to set the effectiveInterestRate as well. $paypage->setEffectiveInterestRate(4.99); // ... a Basket is mandatory for HirePurchase - $orderId = str_replace(['0.', ' '], '', microtime(false)); + $orderId = 'o' . str_replace(['0.', ' '], '', microtime(false)); $basketItem = new BasketItem('Hat', 100.0, 119.0, 1); $basket = new Basket($orderId, 119.0, 'EUR', [$basketItem]); diff --git a/examples/HirePurchaseDirectDebit/Controller.php b/examples/HirePurchaseDirectDebit/Controller.php index 7b7f8c77..eb23746d 100644 --- a/examples/HirePurchaseDirectDebit/Controller.php +++ b/examples/HirePurchaseDirectDebit/Controller.php @@ -68,7 +68,7 @@ function redirect($url, $merchantMessage = '', $clientMessage = '') $heidelpay->setDebugMode(true)->setDebugHandler(new ExampleDebugHandler()); // Use the quote or order id from your shop - $orderId = str_replace(['0.', ' '], '', microtime(false)); + $orderId = 'o' . str_replace(['0.', ' '], '', microtime(false)); /** @var HirePurchaseDirectDebit $paymentType */ $paymentType = $heidelpay->fetchPaymentType($paymentTypeId); diff --git a/examples/HostedPayPage/Controller.php b/examples/HostedPayPage/Controller.php index 771a6ba7..4ae1db7a 100644 --- a/examples/HostedPayPage/Controller.php +++ b/examples/HostedPayPage/Controller.php @@ -68,7 +68,7 @@ function redirect($url, $merchantMessage = '', $clientMessage = '') // These are the mandatory parameters for the payment page ... $paypage = new Paypage(119.0, 'EUR', RETURN_CONTROLLER_URL); - $orderId = str_replace(['0.', ' '], '', microtime(false)); + $orderId = 'o' . str_replace(['0.', ' '], '', microtime(false)); // ... however you can customize the Payment Page using additional parameters. $paypage->setLogoImage('https://dev.heidelpay.com/devHeidelpay_400_180.jpg') @@ -82,7 +82,7 @@ function redirect($url, $merchantMessage = '', $clientMessage = '') ->setImprintUrl('https://www.heidelpay.com/it/') ->setHelpUrl('https://www.heidelpay.com/at/') ->setContactUrl('https://www.heidelpay.com/en/about-us/about-heidelpay/') - ->setInvoiceId('InvoiceNr' . microtime(true)); + ->setInvoiceId('i' . microtime(true)); // ... in order to enable FlexiPay Rate (Hire Purchase) you will need to set the effectiveInterestRate as well. $paypage->setEffectiveInterestRate(4.99); diff --git a/examples/Invoice/Controller.php b/examples/Invoice/Controller.php index ea343cfe..10cb17cb 100644 --- a/examples/Invoice/Controller.php +++ b/examples/Invoice/Controller.php @@ -61,7 +61,7 @@ function redirect($url, $merchantMessage = '', $clientMessage = '') $invoice = $heidelpay->createPaymentType(new Invoice()); $customer = CustomerFactory::createCustomer('Max', 'Mustermann'); - $orderId = str_replace(['0.', ' '], '', microtime(false)); + $orderId = 'o' . str_replace(['0.', ' '], '', microtime(false)); $transaction = $invoice->charge(12.99, 'EUR', CONTROLLER_URL, $customer, $orderId); diff --git a/examples/InvoiceFactoring/Controller.php b/examples/InvoiceFactoring/Controller.php index 11e7e9cc..5ef89181 100755 --- a/examples/InvoiceFactoring/Controller.php +++ b/examples/InvoiceFactoring/Controller.php @@ -73,7 +73,7 @@ function redirect($url, $merchantMessage = '', $clientMessage = '') ->setCountry('DE'); $customer->setBirthDate('2000-02-12')->setBillingAddress($address)->setShippingAddress($address); - $orderId = str_replace(['0.', ' '], '', microtime(false)); + $orderId = 'o' . str_replace(['0.', ' '], '', microtime(false)); // A Basket is mandatory for Invoice Factoring payment type $basketItem = new BasketItem('Hat', 100.0, 119.0, 1); diff --git a/examples/InvoiceGuaranteed/Controller.php b/examples/InvoiceGuaranteed/Controller.php index e4c9c37c..49e04fce 100755 --- a/examples/InvoiceGuaranteed/Controller.php +++ b/examples/InvoiceGuaranteed/Controller.php @@ -64,7 +64,7 @@ function redirect($url, $merchantMessage = '', $clientMessage = '') $heidelpay = new Heidelpay(HEIDELPAY_PHP_PAYMENT_API_PRIVATE_KEY); $heidelpay->setDebugMode(true)->setDebugHandler(new ExampleDebugHandler()); - $orderId = str_replace(['0.', ' '], '', microtime(false)); + $orderId = 'o' . str_replace(['0.', ' '], '', microtime(false)); // A Basket is mandatory for Invoice Factoring payment type $basketItem = new BasketItem('Hat', 100.0, 119.0, 1); diff --git a/examples/PayPal/index.php b/examples/PayPal/index.php index 5f4dac2e..07d0139b 100755 --- a/examples/PayPal/index.php +++ b/examples/PayPal/index.php @@ -74,6 +74,7 @@ +
@@ -84,6 +85,9 @@ // Create an Paypal instance let Paypal = heidelpayInstance.Paypal(); + Paypal.create('email', { + containerId: 'container-example-paypal' + }) // Handle payment form submission let form = document.getElementById('payment-form'); diff --git a/examples/Prepayment/Controller.php b/examples/Prepayment/Controller.php index bbe2062a..293f6531 100644 --- a/examples/Prepayment/Controller.php +++ b/examples/Prepayment/Controller.php @@ -61,7 +61,7 @@ function redirect($url, $merchantMessage = '', $clientMessage = '') $prepayment = $heidelpay->createPaymentType(new Prepayment()); $customer = CustomerFactory::createCustomer('Max', 'Mustermann'); - $orderId = str_replace(['0.', ' '], '', microtime(false)); + $orderId = 'o' . str_replace(['0.', ' '], '', microtime(false)); $transaction = $prepayment->charge(12.99, 'EUR', CONTROLLER_URL, $customer, $orderId); diff --git a/examples/SepaDirectDebitGuaranteed/Controller.php b/examples/SepaDirectDebitGuaranteed/Controller.php index 40482b55..a2752c28 100755 --- a/examples/SepaDirectDebitGuaranteed/Controller.php +++ b/examples/SepaDirectDebitGuaranteed/Controller.php @@ -64,7 +64,7 @@ function redirect($url, $merchantMessage = '', $clientMessage = '') $heidelpay = new Heidelpay(HEIDELPAY_PHP_PAYMENT_API_PRIVATE_KEY); $heidelpay->setDebugMode(true)->setDebugHandler(new ExampleDebugHandler()); - $orderId = str_replace(['0.', ' '], '', microtime(false)); + $orderId = 'o' . str_replace(['0.', ' '], '', microtime(false)); // A Basket is mandatory for SEPA direct debit guaranteed payment type $basketItem = new BasketItem('Hat', 100.0, 119.0, 1); diff --git a/src/Adapter/CurlAdapter.php b/src/Adapter/CurlAdapter.php index ef8f010d..4ed982d5 100755 --- a/src/Adapter/CurlAdapter.php +++ b/src/Adapter/CurlAdapter.php @@ -25,6 +25,7 @@ */ namespace heidelpayPHP\Adapter; +use heidelpayPHP\Heidelpay; use heidelpayPHP\Services\EnvironmentService; use function extension_loaded; use heidelpayPHP\Exceptions\HeidelpayApiException; @@ -126,7 +127,7 @@ public function setHeaders(array $headers) */ public function setUserAgent($userAgent) { - $this->setOption(CURLOPT_USERAGENT, 'HeidelpayPHP'); + $this->setOption(CURLOPT_USERAGENT, Heidelpay::SDK_TYPE); } /** diff --git a/src/Constants/ApiResponseCodes.php b/src/Constants/ApiResponseCodes.php index fc6d5b08..e494fef7 100755 --- a/src/Constants/ApiResponseCodes.php +++ b/src/Constants/ApiResponseCodes.php @@ -50,12 +50,16 @@ class ApiResponseCodes const API_ERROR_ADDRESSES_DO_NOT_MATCH = 'API.330.100.106'; const API_ERROR_CURRENCY_IS_NOT_SUPPORTED = 'API.330.100.202'; /** + * API_ERROR_AUTHORIZE_ALREADY_CANCELLED + * * @deprecated since 1.2.3.0 * @see ApiResponseCodes::API_ERROR_ALREADY_CANCELLED */ const API_ERROR_AUTHORIZE_ALREADY_CANCELLED = 'API.340.100.014'; const API_ERROR_ALREADY_CANCELLED = 'API.340.100.014'; /** + * API_ERROR_CHARGE_ALREADY_CHARGED_BACK + * * @deprecated since 1.2.3.0 * @see ApiResponseCodes::API_ERROR_ALREADY_CHARGED_BACK */ @@ -70,15 +74,17 @@ class ApiResponseCodes const API_ERROR_CUSTOMER_CAN_NOT_BE_FOUND = 'API.500.100.100'; const API_ERROR_REQUEST_DATA_IS_INVALID = 'API.500.300.999'; const API_ERROR_RECURRING_PAYMENT_NOT_SUPPORTED = 'API.500.550.004'; - const API_ERROR_ACTIVATE_RECURRING_VIA_TRANSACTION = 'API.500.550.005'; - const API_ERROR_RECURRING_ALREADY_ACTIVE = 'API.500.550.006'; const API_ERROR_WEBHOOK_EVENT_ALREADY_REGISTERED = 'API.510.310.009'; const API_ERROR_WEBHOOK_CAN_NOT_BE_FOUND = 'API.510.310.008'; const API_ERROR_BASKET_ITEM_IMAGE_INVALID_URL = 'API.600.630.004'; /** + * API_ERROR_BASKET_ITEM_IMAGE_INVALID_EXTENSION + * * @deprecated since 1.2.5.0 Will be removed in next major version. */ const API_ERROR_BASKET_ITEM_IMAGE_INVALID_EXTENSION = 'API.600.630.005'; + const API_ERROR_ACTIVATE_RECURRING_VIA_TRANSACTION = 'API.640.550.005'; + const API_ERROR_RECURRING_ALREADY_ACTIVE = 'API.640.550.006'; const API_ERROR_INVALID_KEY = 'API.710.000.002'; const API_ERROR_INSUFFICIENT_PERMISSION = 'API.710.000.005'; const API_ERROR_WRONG_AUTHENTICATION_METHOD = 'API.710.000.007'; diff --git a/src/Constants/WebhookEvents.php b/src/Constants/WebhookEvents.php index e6b5f0ae..7679e9fa 100755 --- a/src/Constants/WebhookEvents.php +++ b/src/Constants/WebhookEvents.php @@ -50,6 +50,8 @@ class WebhookEvents // payout events const PAYOUT = 'payout'; + const PAYOUT_SUCCEEDED = 'payout.succeeded'; + const PAYOUT_FAILED = 'payout.failed'; // types events const TYPES = 'types'; @@ -87,6 +89,8 @@ class WebhookEvents self::CHARGE_CANCELED, self::CHARGEBACK, self::PAYOUT, + self::PAYOUT_SUCCEEDED, + self::PAYOUT_FAILED, self::TYPES, self::CUSTOMER, self::CUSTOMER_CREATED, diff --git a/src/Heidelpay.php b/src/Heidelpay.php index 581f7fd4..4912ba81 100755 --- a/src/Heidelpay.php +++ b/src/Heidelpay.php @@ -63,8 +63,8 @@ class Heidelpay implements HeidelpayParentInterface, PaymentServiceInterface, Re { const BASE_URL = 'api.heidelpay.com'; const API_VERSION = 'v1'; - const SDK_TYPE = 'HeidelpayPHP'; - const SDK_VERSION = '1.2.7.1'; + const SDK_TYPE = 'heidelpayPHP'; + const SDK_VERSION = '1.2.7.2'; /** @var string $key */ private $key; @@ -172,11 +172,11 @@ public function setLocale($locale): Heidelpay } /** - * @param ResourceServiceInterface $resourceService + * @param ResourceService $resourceService * * @return Heidelpay */ - public function setResourceService(ResourceServiceInterface $resourceService): Heidelpay + public function setResourceService(ResourceService $resourceService): Heidelpay { $this->resourceService = $resourceService->setHeidelpay($this); return $this; @@ -193,11 +193,11 @@ public function getResourceService(): ResourceService } /** - * @param PaymentServiceInterface $paymentService + * @param PaymentService $paymentService * * @return Heidelpay */ - public function setPaymentService(PaymentServiceInterface $paymentService): Heidelpay + public function setPaymentService(PaymentService $paymentService): Heidelpay { $this->paymentService = $paymentService->setHeidelpay($this); return $this; @@ -1024,7 +1024,7 @@ public function debugLog($message) if ($this->isDebugMode()) { $debugHandler = $this->getDebugHandler(); if ($debugHandler instanceof DebugHandlerInterface) { - $debugHandler->log('(' . (string)(getmypid()) . ') ' . $message); + $debugHandler->log('(' . getmypid() . ') ' . $message); } } } diff --git a/src/Resources/AbstractHeidelpayResource.php b/src/Resources/AbstractHeidelpayResource.php index dd39d1d6..fb5af5b2 100755 --- a/src/Resources/AbstractHeidelpayResource.php +++ b/src/Resources/AbstractHeidelpayResource.php @@ -490,6 +490,17 @@ protected function getResourcePath(): string public function handleResponse(stdClass $response, $method = HttpAdapterInterface::REQUEST_GET) { self::updateValues($this, $response); + + // Todo: Workaround to be removed when API sends TraceID in processing-group + if ( + isset($response->resources->traceId) && + is_callable([$this, 'setTraceId']) && + is_callable([$this, 'getTraceId']) && + $this->getTraceId() === null + ) { + $this->setTraceId($response->resources->traceId); + } + // Todo: Workaround end } /** diff --git a/src/Resources/Customer.php b/src/Resources/Customer.php index 6ebd728e..a62b6aec 100755 --- a/src/Resources/Customer.php +++ b/src/Resources/Customer.php @@ -28,12 +28,14 @@ use heidelpayPHP\Constants\Salutations; use heidelpayPHP\Resources\EmbeddedResources\Address; use heidelpayPHP\Resources\EmbeddedResources\CompanyInfo; -use heidelpayPHP\Resources\EmbeddedResources\GeoLocation; +use heidelpayPHP\Traits\HasGeoLocation; use stdClass; use function in_array; class Customer extends AbstractHeidelpayResource { + use HasGeoLocation; + /** @var string $firstname */ protected $firstname; @@ -70,9 +72,6 @@ class Customer extends AbstractHeidelpayResource /** @var CompanyInfo $companyInfo */ protected $companyInfo; - /** @var GeoLocation $geoLocation */ - private $geoLocation; - /** * Customer constructor. * @@ -90,7 +89,6 @@ public function __construct(string $firstname = null, string $lastname = null) $this->lastname = $lastname; $this->billingAddress = new Address(); $this->shippingAddress = new Address(); - $this->geoLocation = new GeoLocation(); } // @@ -324,14 +322,6 @@ public function setCompanyInfo(CompanyInfo $companyInfo): Customer return $this; } - /** - * @return GeoLocation|null - */ - public function getGeoLocation() - { - return $this->geoLocation; - } - // // diff --git a/src/Resources/EmbeddedResources/GeoLocation.php b/src/Resources/EmbeddedResources/GeoLocation.php index aba16a81..1eca406b 100644 --- a/src/Resources/EmbeddedResources/GeoLocation.php +++ b/src/Resources/EmbeddedResources/GeoLocation.php @@ -1,6 +1,6 @@ holder; + return $this->cardHolder; } /** - * @param string $holder + * @param string $cardHolder * * @return Card */ - public function setHolder($holder): Card + public function setCardHolder($cardHolder): Card { - $this->holder = $holder; + $this->cardHolder = $cardHolder; return $this; } + /** + * @return string|null + * + * @deprecated since 1.2.7.2 + */ + public function getHolder() + { + return $this->getCardHolder(); + } + + /** + * @param string $cardHolder + * + * @return Card + * + * @deprecated since 1.2.7.2 + */ + public function setHolder($cardHolder): Card + { + return $this->setCardHolder($cardHolder); + } + /** * @return bool|null */ diff --git a/src/Resources/TransactionTypes/AbstractTransactionType.php b/src/Resources/TransactionTypes/AbstractTransactionType.php index 77c4830f..9112e277 100755 --- a/src/Resources/TransactionTypes/AbstractTransactionType.php +++ b/src/Resources/TransactionTypes/AbstractTransactionType.php @@ -33,6 +33,7 @@ use heidelpayPHP\Traits\HasDate; use heidelpayPHP\Traits\HasOrderId; use heidelpayPHP\Traits\HasStates; +use heidelpayPHP\Traits\HasTraceId; use heidelpayPHP\Traits\HasUniqueAndShortId; use RuntimeException; use stdClass; @@ -42,6 +43,7 @@ abstract class AbstractTransactionType extends AbstractHeidelpayResource use HasOrderId; use HasStates; use HasUniqueAndShortId; + use HasTraceId; use HasCustomerMessage; use HasDate; diff --git a/src/Resources/TransactionTypes/Authorization.php b/src/Resources/TransactionTypes/Authorization.php index eb0fa6cc..a4519630 100755 --- a/src/Resources/TransactionTypes/Authorization.php +++ b/src/Resources/TransactionTypes/Authorization.php @@ -204,6 +204,8 @@ protected function setExternalOrderId($externalOrderId): Authorization } /** + * Returns the reference Id of the insurance provider if applicable. + * * @return string|null */ public function getZgReferenceId() @@ -212,6 +214,8 @@ public function getZgReferenceId() } /** + * Sets the reference Id of the insurance provider. + * * @param string|null $zgReferenceId * * @return Authorization diff --git a/src/Services/CancelService.php b/src/Services/CancelService.php index 18cffcb0..3e6c2bf2 100644 --- a/src/Services/CancelService.php +++ b/src/Services/CancelService.php @@ -90,10 +90,10 @@ public function getResourceService(): ResourceService public function cancelAuthorization(Authorization $authorization, float $amount = null): Cancellation { $cancellation = new Cancellation($amount); - $cancellation->setPayment($authorization->getPayment()); - $authorization->addCancellation($cancellation); - $this->getResourceService()->createResource($cancellation); + $cancellation->setPayment($authorization->getPayment())->setParentResource($authorization); + /** @var Cancellation $cancellation */ + $cancellation = $this->getResourceService()->createResource($cancellation); return $cancellation; } diff --git a/src/Traits/HasGeoLocation.php b/src/Traits/HasGeoLocation.php new file mode 100644 index 00000000..2f961cc0 --- /dev/null +++ b/src/Traits/HasGeoLocation.php @@ -0,0 +1,59 @@ + + * + * @package heidelpayPHP\Traits + */ +namespace heidelpayPHP\Traits; + +use heidelpayPHP\Resources\EmbeddedResources\GeoLocation; + +trait HasGeoLocation +{ + /** @var GeoLocation $geoLocation */ + private $geoLocation; + + // + + /** + * @return GeoLocation + */ + public function getGeoLocation(): GeoLocation + { + if (empty($this->geoLocation)) { + $this->geoLocation = new GeoLocation(); + } + return $this->geoLocation; + } + + /** + * @param GeoLocation $geoLocation + * + * @return $this + */ + public function setGeoLocation(GeoLocation $geoLocation): self + { + $this->geoLocation = $geoLocation; + return $this; + } + + // +} diff --git a/src/Traits/HasTraceId.php b/src/Traits/HasTraceId.php new file mode 100644 index 00000000..8f4c56c3 --- /dev/null +++ b/src/Traits/HasTraceId.php @@ -0,0 +1,55 @@ + + * + * @package heidelpayPHP\Traits + */ +namespace heidelpayPHP\Traits; + +trait HasTraceId +{ + /** @var string $traceId */ + private $traceId; + + // + + /** + * @return string|null + */ + public function getTraceId() + { + return $this->traceId; + } + + /** + * @param string $traceId + * + * @return $this + */ + protected function setTraceId(string $traceId): self + { + $this->traceId = $traceId; + return $this; + } + + // +} diff --git a/test/BasePaymentTest.php b/test/BasePaymentTest.php index bbdc8e3a..6ec5f2d7 100755 --- a/test/BasePaymentTest.php +++ b/test/BasePaymentTest.php @@ -182,7 +182,7 @@ protected function assertPending($transaction) */ public function createBasket(): Basket { - $orderId = self::generateRandomId(); + $orderId = 'b' . self::generateRandomId(); $basket = new Basket($orderId, 119.0, 'EUR'); $basket->setAmountTotalVat(19.0); $basket->setNote('This basket is creatable!'); @@ -223,7 +223,7 @@ protected function createCardObject(string $cardNumber = '5453010000059543'): Ca { $expiryDate = $this->getNextYearsTimestamp()->format('m/Y'); $card = new Card($cardNumber, $expiryDate); - $card->setCvc('123'); + $card->setCvc('123')->setCardHolder('max mustermann'); return $card; } diff --git a/test/integration/BasketTest.php b/test/integration/BasketTest.php index cd09af81..c2a17c92 100755 --- a/test/integration/BasketTest.php +++ b/test/integration/BasketTest.php @@ -74,7 +74,7 @@ public function minBasketShouldBeCreatableAndFetchable() */ public function maxBasketShouldBeCreatableAndFetchableWorkAround() { - $basket = new Basket(self::generateRandomId(), 123.4, 'EUR', []); + $basket = new Basket('b' . self::generateRandomId(), 123.4, 'EUR', []); $basket->setNote('This basket is creatable!'); $basketItem = (new BasketItem('myItem', 1234, 2345, 12)) ->setBasketItemReferenceId('refId') @@ -116,7 +116,7 @@ public function maxBasketShouldBeCreatableAndFetchableWorkAround() */ public function basketItemWithInvalidUrlWillThrowAnError($expectException, $imageUrl, $exceptionCode = null) { - $basket = new Basket(self::generateRandomId(), 123.4, 'EUR', []); + $basket = new Basket('b' . self::generateRandomId(), 123.4, 'EUR', []); $basketItem = (new BasketItem('myItem', 1234, 2345, 12))->setImageUrl($imageUrl); $basket->addBasketItem($basketItem); @@ -143,7 +143,7 @@ public function basketItemWithInvalidUrlWillThrowAnError($expectException, $imag */ public function basketShouldBeUpdateable() { - $orderId = self::generateRandomId(); + $orderId = 'o'. self::generateRandomId(); $basket = new Basket($orderId, 123.4, 'EUR', []); $basket->setNote('This basket is creatable!'); $basketItem = (new BasketItem('myItem', 1234, 2345, 12))->setBasketItemReferenceId('refId'); @@ -175,7 +175,7 @@ public function basketShouldBeUpdateable() */ public function authorizeTransactionsShouldPassAlongTheBasketIdIfSet() { - $orderId = self::generateRandomId(); + $orderId = 'o'. self::generateRandomId(); $basket = new Basket($orderId, 123.4, 'EUR', []); $basket->setNote('This basket is creatable!'); $basketItem = (new BasketItem('myItem', 123.4, 234.5, 12))->setBasketItemReferenceId('refId'); @@ -224,7 +224,7 @@ public function chargeTransactionsShouldPassAlongTheBasketIdIfSet() */ public function authorizeTransactionsShouldCreateBasketIfItDoesNotExistYet() { - $orderId = self::generateRandomId(); + $orderId = 'o'. self::generateRandomId(); $basket = new Basket($orderId, 123.4, 'EUR', []); $basket->setNote('This basket is creatable!'); $basketItem = (new BasketItem('myItem', 1234, 2345, 12))->setBasketItemReferenceId('refId'); @@ -250,7 +250,7 @@ public function authorizeTransactionsShouldCreateBasketIfItDoesNotExistYet() */ public function chargeTransactionsShouldCreateBasketIfItDoesNotExistYet() { - $orderId = self::generateRandomId(); + $orderId = 'o'. self::generateRandomId(); $basket = new Basket($orderId, 123.4, 'EUR', []); $basket->setNote('This basket is creatable!'); $basket->setAmountTotalVat(10.9); diff --git a/test/integration/CustomerTest.php b/test/integration/CustomerTest.php index d99338ef..6a514d0a 100755 --- a/test/integration/CustomerTest.php +++ b/test/integration/CustomerTest.php @@ -29,7 +29,6 @@ use heidelpayPHP\Constants\Salutations; use heidelpayPHP\Exceptions\HeidelpayApiException; use heidelpayPHP\Resources\Customer; -use heidelpayPHP\Resources\EmbeddedResources\GeoLocation; use heidelpayPHP\Resources\Payment; use heidelpayPHP\Resources\PaymentTypes\Paypal; use heidelpayPHP\test\BasePaymentTest; @@ -52,25 +51,21 @@ class CustomerTest extends BasePaymentTest */ public function minCustomerCanBeCreatedAndFetched(): Customer { - /** @var Customer $customer */ $customer = $this->getMinimalCustomer(); $this->assertEmpty($customer->getId()); $this->heidelpay->createCustomer($customer); $this->assertNotEmpty($customer->getId()); $geoLocation = $customer->getGeoLocation(); - $this->assertInstanceOf(GeoLocation::class, $geoLocation); $this->assertNull($geoLocation->getClientIp()); $this->assertNull($geoLocation->getCountryCode()); - /** @var Customer $fetchedCustomer */ $fetchedCustomer = $this->heidelpay->fetchCustomer($customer->getId()); $exposeArray = $customer->expose(); $exposeArray['salutation'] = Salutations::UNKNOWN; $this->assertEquals($exposeArray, $fetchedCustomer->expose()); $geoLocation = $fetchedCustomer->getGeoLocation(); - $this->assertInstanceOf(GeoLocation::class, $geoLocation); $this->assertNotEmpty($geoLocation->getClientIp()); $this->assertNotEmpty($geoLocation->getCountryCode()); @@ -123,7 +118,7 @@ public function customerCanBeFetchedById(Customer $customer) */ public function customerCanBeFetchedByCustomerId() { - $customerId = str_replace([' ', '.'], '', microtime()); + $customerId = 'c' . self::generateRandomId(); $customer = $this->getMaximumCustomer()->setCustomerId($customerId); $this->heidelpay->createCustomer($customer); @@ -173,7 +168,7 @@ public function customerCanBeFetchedByObjectWithData(Customer $customer) */ public function transactionShouldCreateAndReferenceCustomerIfItDoesNotExistYet() { - $customerId = 'customer' . self::generateRandomId(); + $customerId = 'c' . self::generateRandomId(); $customer = $this->getMaximumCustomerInclShippingAddress()->setCustomerId($customerId); /** @var Paypal $paypal */ @@ -379,7 +374,7 @@ public function customerShouldBeFetchedByCustomerIdAndUpdatedIfItAlreadyExists() */ public function addressNameCanHoldFirstAndLastNameConcatenated() { - $customerId = 'customer' . self::generateRandomId(); + $customerId = 'c' . self::generateRandomId(); $customer = $this->getMaximumCustomerInclShippingAddress()->setCustomerId($customerId); $longName = 'firstfirstfirstfirstfirstfirstfirstfirst lastlastlastlastlastlastlastlastlastlast'; $customer->getShippingAddress()->setName($longName); diff --git a/test/integration/PaymentCancelTest.php b/test/integration/PaymentCancelTest.php index 8491a34d..f052e359 100644 --- a/test/integration/PaymentCancelTest.php +++ b/test/integration/PaymentCancelTest.php @@ -106,12 +106,12 @@ public function fullCancelOnPaymentWithAuthorizeAndMultipleChargesShouldBePossib $this->assertTrue($payment->isPending()); $this->assertAmounts($payment, 123.44, 0.0, 123.44, 0.0); - $payment->charge(100.44); + $charge1 = $payment->charge(100.44); $this->assertTrue($payment->isPartlyPaid()); $this->assertAmounts($payment, 23.0, 100.44, 123.44, 0.0); $payment = $this->heidelpay->fetchPayment($authorization->getPaymentId()); - $payment->charge(23.00); + $charge2 = $payment->charge(23.00); $this->assertTrue($payment->isCompleted()); $this->assertAmounts($payment, 0.0, 123.44, 123.44, 0.0); @@ -119,6 +119,11 @@ public function fullCancelOnPaymentWithAuthorizeAndMultipleChargesShouldBePossib $this->assertCount(2, $payment->cancelAmount()); $this->assertTrue($payment->isCanceled()); $this->assertAmounts($payment, 0.0, 0.0, 123.44, 123.44); + + $allCancellations = $payment->getCancellations(); + $this->assertCount(2, $allCancellations); + $this->assertEquals($charge1->getId(), $allCancellations[0]->getParentResource()->getId()); + $this->assertEquals($charge2->getId(), $allCancellations[1]->getParentResource()->getId()); } /** diff --git a/test/integration/PaymentTest.php b/test/integration/PaymentTest.php index ebab4006..08948ab2 100755 --- a/test/integration/PaymentTest.php +++ b/test/integration/PaymentTest.php @@ -52,6 +52,10 @@ public function paymentShouldBeFetchableById(): void $this->assertInstanceOf(Authorization::class, $payment->getAuthorization()); $this->assertNotEmpty($payment->getAuthorization()->getId()); $this->assertNotNull($payment->getState()); + + $traceId = $authorize->getTraceId(); + $this->assertNotEmpty($traceId); + $this->assertSame($traceId, $payment->getTraceId()); } /** @@ -174,7 +178,7 @@ public function paymentChargeOnAuthorizeShouldTakeResourceIds() { $card = $this->heidelpay->createPaymentType($this->createCardObject()); $authorization = $this->heidelpay->authorize(100.00, 'EUR', $card, 'http://heidelpay.com', null, null, null, null, false); - $charge = $this->heidelpay->chargePayment($authorization->getPaymentId(), null, 'order-' . self::generateRandomId(), 'invoice-' . self::generateRandomId()); + $charge = $this->heidelpay->chargePayment($authorization->getPaymentId(), null, 'EUR', 'o' . self::generateRandomId(), 'i' . self::generateRandomId()); $this->assertNotEmpty($charge->getId()); } @@ -224,7 +228,7 @@ public function paymentShouldBeFetchedByOrderIdIfIdIsNotSet() */ public function shouldAllowNonUniqueOrderId() { - $orderId = self::generateRandomId(); + $orderId = 'o' . self::generateRandomId(); /** @var Card $card */ $card = $this->heidelpay->createPaymentType($this->createCardObject()); @@ -250,7 +254,7 @@ public function shouldAllowNonUniqueOrderId() */ public function shouldAllowNonUniqueInvoiceId() { - $invoiceId = self::generateRandomId(); + $invoiceId = 'i' . self::generateRandomId(); /** @var Card $card */ $card = $this->heidelpay->createPaymentType($this->createCardObject()); diff --git a/test/integration/PaymentTypes/CardTest.php b/test/integration/PaymentTypes/CardTest.php index b901886d..a42c5a49 100755 --- a/test/integration/PaymentTypes/CardTest.php +++ b/test/integration/PaymentTypes/CardTest.php @@ -58,9 +58,14 @@ class CardTest extends BasePaymentTest */ public function cardShouldBeCreatable(string $cardNumber, CardDetails $expectedCardDetails): BasePaymentType { - /** @var Card $card */ $card = $this->createCardObject($cardNumber); $this->assertNull($card->getId()); + + $geoLocation = $card->getGeoLocation(); + $this->assertNull($geoLocation->getClientIp()); + $this->assertNull($geoLocation->getCountryCode()); + + /** @var Card $card */ $card = $this->heidelpay->createPaymentType($card); $this->assertInstanceOf(Card::class, $card); @@ -68,6 +73,10 @@ public function cardShouldBeCreatable(string $cardNumber, CardDetails $expectedC $this->assertSame($this->heidelpay, $card->getHeidelpayObject()); $this->assertEquals($expectedCardDetails, $card->getCardDetails()); + $geoLocation = $card->getGeoLocation(); + $this->assertNotEmpty($geoLocation->getClientIp()); + $this->assertNotEmpty($geoLocation->getCountryCode()); + return $card; } @@ -81,8 +90,8 @@ public function cardShouldBeCreatable(string $cardNumber, CardDetails $expectedC */ public function cardWith3dsFlagShouldSetItAlsoInTransactions() { - /** @var Card $card */ $card = $this->createCardObject()->set3ds(false); + /** @var Card $card */ $card = $this->heidelpay->createPaymentType($card); $this->assertFalse($card->get3ds()); @@ -180,6 +189,33 @@ public function cardCanBeFetched() $card = $this->createCardObject(); $card = $this->heidelpay->createPaymentType($card); $this->assertNotNull($card->getId()); + $this->assertNotNull($card->getCardHolder()); + + /** @var Card $fetchedCard */ + $fetchedCard = $this->heidelpay->fetchPaymentType($card->getId()); + $this->assertNotNull($fetchedCard->getId()); + $this->assertEquals($this->maskNumber($card->getNumber()), $fetchedCard->getNumber()); + $this->assertEquals($card->getExpiryDate(), $fetchedCard->getExpiryDate()); + $this->assertEquals('***', $fetchedCard->getCvc()); + $this->assertEquals($card->getCardHolder(), $fetchedCard->getCardHolder()); + } + + /** + * Verify that a card object can be fetched from the api using its id. + * + * @test + * + * @throws HeidelpayApiException A HeidelpayApiException is thrown if there is an error returned on API-request. + * @throws RuntimeException A RuntimeException is thrown when there is an error while using the SDK. + * + * @deprecated since 1.2.7.2 + */ + public function cardCanBeFetchedOld() + { + $card = $this->createCardObject(); + $this->heidelpay->createPaymentType($card); + $this->assertNotNull($card->getId()); + $this->assertNotEmpty($card->getHolder()); /** @var Card $fetchedCard */ $fetchedCard = $this->heidelpay->fetchPaymentType($card->getId()); @@ -187,6 +223,7 @@ public function cardCanBeFetched() $this->assertEquals($this->maskNumber($card->getNumber()), $fetchedCard->getNumber()); $this->assertEquals($card->getExpiryDate(), $fetchedCard->getExpiryDate()); $this->assertEquals('***', $fetchedCard->getCvc()); + $this->assertEquals($card->getHolder(), $fetchedCard->getHolder()); } /** diff --git a/test/integration/PaymentTypes/InvoiceFactoringTest.php b/test/integration/PaymentTypes/InvoiceFactoringTest.php index 6dfd6461..bbbbba16 100755 --- a/test/integration/PaymentTypes/InvoiceFactoringTest.php +++ b/test/integration/PaymentTypes/InvoiceFactoringTest.php @@ -231,7 +231,7 @@ public function verifyInvoiceFactoringShipmentWithInvoiceIdOnHeidelpayObject() // perform shipment $payment = $charge->getPayment(); - $invoiceId = substr(str_replace(['0.',' '], '', microtime(false)), 0, 16); + $invoiceId = 'i' . self::generateRandomId(); $shipment = $this->heidelpay->ship($payment, $invoiceId); $this->assertNotNull($shipment->getId()); $this->assertEquals($invoiceId, $shipment->getInvoiceId()); @@ -259,7 +259,7 @@ public function verifyInvoiceFactoringShipmentWithInvoiceIdOnPaymentObject() $charge = $invoiceFactoring->charge(119.0, 'EUR', self::RETURN_URL, $customer, $basket->getOrderId(), null, $basket); $payment = $charge->getPayment(); - $invoiceId = substr(str_replace(['0.',' '], '', microtime(false)), 0, 16); + $invoiceId = 'i' . self::generateRandomId(); $shipment = $payment->ship($invoiceId); $this->assertNotNull($shipment->getId()); $this->assertEquals($invoiceId, $shipment->getInvoiceId()); @@ -282,7 +282,7 @@ public function verifyInvoiceFactoringShipmentWithPreSetInvoiceId() $customer->setShippingAddress($customer->getBillingAddress()); $basket = $this->createBasket(); - $invoiceId = substr(str_replace(['0.',' '], '', microtime(false)), 0, 16); + $invoiceId = 'i' . self::generateRandomId(); $charge = $invoiceFactoring->charge(119.0, 'EUR', self::RETURN_URL, $customer, $basket->getOrderId(), null, $basket, null, $invoiceId); $payment = $charge->getPayment(); diff --git a/test/integration/PaymentTypes/InvoiceGuaranteedTest.php b/test/integration/PaymentTypes/InvoiceGuaranteedTest.php index 9a44d60c..3108ae78 100755 --- a/test/integration/PaymentTypes/InvoiceGuaranteedTest.php +++ b/test/integration/PaymentTypes/InvoiceGuaranteedTest.php @@ -69,7 +69,7 @@ public function verifyInvoiceGuaranteedShipment() $this->assertNotEmpty($charge->getHolder()); $this->assertNotEmpty($charge->getDescriptor()); - $shipment = $this->heidelpay->ship($charge->getPayment(), self::generateRandomId(), self::generateRandomId()); + $shipment = $this->heidelpay->ship($charge->getPayment(), 'i' . self::generateRandomId(), 'o' . self::generateRandomId()); $this->assertTransactionResourceHasBeenCreated($shipment); } @@ -143,7 +143,7 @@ public function verifyInvoiceIdInShipmentWillOverrideTheOneFromCharge() $invoiceGuaranteed = $this->heidelpay->createPaymentType(new InvoiceGuaranteed()); $customer = $this->getMaximumCustomerInclShippingAddress()->setShippingAddress($this->getBillingAddress()); - $invoiceId = self::generateRandomId(); + $invoiceId = 'i' . self::generateRandomId(); $charge = $invoiceGuaranteed->charge(100.0, 'EUR', self::RETURN_URL, $customer, null, null, null, null, $invoiceId); $chargeInvoiceId = $charge->getPayment()->getInvoiceId(); diff --git a/test/integration/PaymentTypes/PaypageTest.php b/test/integration/PaymentTypes/PaypageTest.php index e009f1c2..0ca30dcb 100644 --- a/test/integration/PaymentTypes/PaypageTest.php +++ b/test/integration/PaymentTypes/PaypageTest.php @@ -63,10 +63,10 @@ public function minimalPaypageChargeShouldBeCreatableAndFetchable() */ public function maximumPaypageChargeShouldBeCreatable() { - $orderId = self::generateRandomId(); + $orderId = 'o'. self::generateRandomId(); $basket = $this->createBasket(); $customer = CustomerFactory::createCustomer('Max', 'Mustermann'); - $invoiceId = self::generateRandomId(); + $invoiceId = 'i'. self::generateRandomId(); $paypage = (new Paypage(119.0, 'EUR', self::RETURN_URL)) ->setLogoImage('https://dev.heidelpay.com/devHeidelpay_400_180.jpg') ->setFullPageImage('https://www.heidelpay.com/fileadmin/content/header-Imges-neu/Header_Phone_12.jpg') @@ -120,10 +120,10 @@ public function minimalPaypageAuthorizeShouldBeCreatableAndFetchable() */ public function maximumPaypageAuthorizeShouldBeCreatable() { - $orderId = self::generateRandomId(); + $orderId = 'o'. self::generateRandomId(); $basket = $this->createBasket(); $customer = CustomerFactory::createCustomer('Max', 'Mustermann'); - $invoiceId = self::generateRandomId(); + $invoiceId = 'i'. self::generateRandomId(); $paypage = (new Paypage(119.0, 'EUR', self::RETURN_URL)) ->setLogoImage('https://dev.heidelpay.com/devHeidelpay_400_180.jpg') ->setFullPageImage('https://www.heidelpay.com/fileadmin/content/header-Imges-neu/Header_Phone_12.jpg') diff --git a/test/integration/PaymentTypes/SepaDirectDebitGuaranteedTest.php b/test/integration/PaymentTypes/SepaDirectDebitGuaranteedTest.php index 7b995aa1..5da33d97 100755 --- a/test/integration/PaymentTypes/SepaDirectDebitGuaranteedTest.php +++ b/test/integration/PaymentTypes/SepaDirectDebitGuaranteedTest.php @@ -43,8 +43,8 @@ class SepaDirectDebitGuaranteedTest extends BasePaymentTest */ public function sepaDirectDebitGuaranteedShouldBeCreatableWithMandatoryFieldsOnly() { - /** @var SepaDirectDebitGuaranteed $directDebitGuaranteed */ $directDebitGuaranteed = new SepaDirectDebitGuaranteed('DE89370400440532013000'); + /** @var SepaDirectDebitGuaranteed $directDebitGuaranteed */ $directDebitGuaranteed = $this->heidelpay->createPaymentType($directDebitGuaranteed); $this->assertInstanceOf(SepaDirectDebitGuaranteed::class, $directDebitGuaranteed); $this->assertNotNull($directDebitGuaranteed->getId()); @@ -66,8 +66,8 @@ public function sepaDirectDebitGuaranteedShouldBeCreatableWithMandatoryFieldsOnl */ public function sepaDirectDebitGuaranteedShouldBeCreatable(): SepaDirectDebitGuaranteed { - /** @var SepaDirectDebitGuaranteed $directDebitGuaranteed */ $directDebitGuaranteed = (new SepaDirectDebitGuaranteed('DE89370400440532013000'))->setHolder('John Doe')->setBic('COBADEFFXXX'); + /** @var SepaDirectDebitGuaranteed $directDebitGuaranteed */ $directDebitGuaranteed = $this->heidelpay->createPaymentType($directDebitGuaranteed); $this->assertInstanceOf(SepaDirectDebitGuaranteed::class, $directDebitGuaranteed); $this->assertNotNull($directDebitGuaranteed->getId()); diff --git a/test/integration/PaymentTypes/SepaDirectDebitTest.php b/test/integration/PaymentTypes/SepaDirectDebitTest.php index fae570e1..7f28a490 100755 --- a/test/integration/PaymentTypes/SepaDirectDebitTest.php +++ b/test/integration/PaymentTypes/SepaDirectDebitTest.php @@ -43,8 +43,8 @@ class SepaDirectDebitTest extends BasePaymentTest */ public function sepaDirectDebitShouldBeCreatableWithMandatoryFieldsOnly() { - /** @var SepaDirectDebit $directDebit */ $directDebit = new SepaDirectDebit('DE89370400440532013000'); + /** @var SepaDirectDebit $directDebit */ $directDebit = $this->heidelpay->createPaymentType($directDebit); $this->assertInstanceOf(SepaDirectDebit::class, $directDebit); $this->assertNotNull($directDebit->getId()); @@ -64,8 +64,8 @@ public function sepaDirectDebitShouldBeCreatableWithMandatoryFieldsOnly() */ public function sepaDirectDebitShouldBeCreatable() { - /** @var SepaDirectDebit $sdd */ $sdd = (new SepaDirectDebit('DE89370400440532013000'))->setHolder('Max Mustermann')->setBic('COBADEFFXXX'); + /** @var SepaDirectDebit $sdd */ $sdd = $this->heidelpay->createPaymentType($sdd); $this->assertInstanceOf(SepaDirectDebit::class, $sdd); $this->assertNotNull($sdd->getId()); diff --git a/test/integration/TransactionTypes/AuthorizationTest.php b/test/integration/TransactionTypes/AuthorizationTest.php index c1991dd2..ee5252c7 100644 --- a/test/integration/TransactionTypes/AuthorizationTest.php +++ b/test/integration/TransactionTypes/AuthorizationTest.php @@ -54,6 +54,10 @@ public function authorizeWithTypeId() $this->assertNotEmpty($authorize->getId()); $this->assertNotEmpty($authorize->getUniqueId()); $this->assertNotEmpty($authorize->getShortId()); + + $traceId = $authorize->getTraceId(); + $this->assertNotEmpty($traceId); + $this->assertSame($traceId, $authorize->getPayment()->getTraceId()); } /** @@ -175,10 +179,10 @@ public function authorizeShouldAcceptAllParameters() /** @var Card $card */ $card = $this->heidelpay->createPaymentType($this->createCardObject()); $customer = $this->getMinimalCustomer(); - $orderId = self::generateRandomId(); + $orderId = 'o' . self::generateRandomId(); $metadata = (new Metadata())->addMetadata('key', 'value'); $basket = $this->createBasket(); - $invoiceId = self::generateRandomId(); + $invoiceId = 'i' . self::generateRandomId(); $paymentReference = 'paymentReference'; $authorize = $card->authorize(119.0, 'EUR', self::RETURN_URL, $customer, $orderId, $metadata, $basket, true, $invoiceId, $paymentReference); diff --git a/test/integration/TransactionTypes/CancelAfterAuthorizationTest.php b/test/integration/TransactionTypes/CancelAfterAuthorizationTest.php index db0c4241..34e859cb 100644 --- a/test/integration/TransactionTypes/CancelAfterAuthorizationTest.php +++ b/test/integration/TransactionTypes/CancelAfterAuthorizationTest.php @@ -26,7 +26,6 @@ use heidelpayPHP\Exceptions\HeidelpayApiException; use heidelpayPHP\Resources\TransactionTypes\Authorization; -use heidelpayPHP\Resources\TransactionTypes\Cancellation; use heidelpayPHP\test\BasePaymentTest; use RuntimeException; @@ -57,6 +56,10 @@ public function fullCancelOnAuthorization() $this->assertNotEmpty($cancellation); $this->assertAmounts($secPayment, 0.0, 0.0, 0.0, 0.0); $this->assertTrue($secPayment->isCanceled()); + + $traceId = $cancellation->getTraceId(); + $this->assertNotEmpty($traceId); + $this->assertSame($traceId, $cancellation->getPayment()->getTraceId()); } /** @@ -75,7 +78,6 @@ public function partCancelOnPayment() $cancelArray = $payment->cancelAmount(10.0); - /** @var Cancellation $cancel */ $cancel = $cancelArray[0]; $this->assertTransactionResourceHasBeenCreated($cancel); $this->assertEquals(10.0, $cancel->getAmount()); diff --git a/test/integration/TransactionTypes/CancelAfterChargeTest.php b/test/integration/TransactionTypes/CancelAfterChargeTest.php index 157ce73d..a3041740 100644 --- a/test/integration/TransactionTypes/CancelAfterChargeTest.php +++ b/test/integration/TransactionTypes/CancelAfterChargeTest.php @@ -26,7 +26,6 @@ use heidelpayPHP\Exceptions\HeidelpayApiException; use heidelpayPHP\Resources\PaymentTypes\SepaDirectDebit; -use heidelpayPHP\Resources\TransactionTypes\Cancellation; use heidelpayPHP\Resources\TransactionTypes\Charge; use heidelpayPHP\test\BasePaymentTest; use RuntimeException; @@ -68,10 +67,13 @@ public function chargeShouldBeFetchable(): Charge */ public function chargeShouldBeFullyRefundable(Charge $charge) { - /** @var Cancellation $refund */ $refund = $this->heidelpay->cancelCharge($charge); $this->assertNotNull($refund); $this->assertNotEmpty($refund->getId()); + + $traceId = $charge->getTraceId(); + $this->assertNotEmpty($traceId); + $this->assertSame($traceId, $charge->getPayment()->getTraceId()); } /** @@ -87,7 +89,6 @@ public function chargeShouldBeFullyRefundableWithId() $paymentType = $this->heidelpay->createPaymentType(new SepaDirectDebit('DE89370400440532013000')); $charge = $this->heidelpay->charge(100.0000, 'EUR', $paymentType, self::RETURN_URL); - /** @var Cancellation $refund */ $refund = $this->heidelpay->cancelChargeById($charge->getPayment()->getId(), $charge->getId()); $this->assertNotNull($refund); $this->assertNotEmpty($refund->getId()); @@ -110,7 +111,6 @@ public function chargeShouldBePartlyRefundableWithId() $this->assertAmounts($firstPayment, 0, 100, 100, 0); $this->assertTrue($firstPayment->isCompleted()); - /** @var Cancellation $refund */ $refund = $this->heidelpay->cancelChargeById($charge->getPayment()->getId(), $charge->getId(), 10.0); $this->assertNotNull($refund); $this->assertNotEmpty($refund->getId()); @@ -138,7 +138,6 @@ public function chargeShouldBePartlyRefundable() $this->assertAmounts($firstPayment, 0, 100, 100, 0); $this->assertTrue($firstPayment->isCompleted()); - /** @var Cancellation $refund */ $refund = $this->heidelpay->cancelCharge($charge, 10.0); $this->assertNotNull($refund); $this->assertNotEmpty($refund->getId()); diff --git a/test/integration/TransactionTypes/ChargeTest.php b/test/integration/TransactionTypes/ChargeTest.php index a5c0e027..8e5c01bd 100644 --- a/test/integration/TransactionTypes/ChargeTest.php +++ b/test/integration/TransactionTypes/ChargeTest.php @@ -98,10 +98,10 @@ public function chargeShouldAcceptAllParameters() /** @var Card $paymentType */ $paymentType = $this->heidelpay->createPaymentType($this->createCardObject()); $customer = $this->getMinimalCustomer(); - $orderId = self::generateRandomId(); + $orderId = 'o'. self::generateRandomId(); $metadata = (new Metadata())->addMetadata('key', 'value'); $basket = $this->createBasket(); - $invoiceId = self::generateRandomId(); + $invoiceId = 'i'. self::generateRandomId(); $paymentReference = 'paymentReference'; // perform request @@ -148,10 +148,10 @@ public function chargeWithCustomerShouldAcceptAllParameters() $ivg = $this->heidelpay->createPaymentType(new InvoiceGuaranteed()); $customer = $this->getMaximumCustomer(); $customer->setShippingAddress($customer->getBillingAddress()); - $orderId = self::generateRandomId(); + $orderId = 'o'. self::generateRandomId(); $metadata = (new Metadata())->addMetadata('key', 'value'); $basket = $this->createBasket(); - $invoiceId = self::generateRandomId(); + $invoiceId = 'i'. self::generateRandomId(); $paymentReference = 'paymentReference'; // perform request diff --git a/test/integration/TransactionTypes/PayoutTest.php b/test/integration/TransactionTypes/PayoutTest.php index cec76e23..398a57c1 100644 --- a/test/integration/TransactionTypes/PayoutTest.php +++ b/test/integration/TransactionTypes/PayoutTest.php @@ -59,6 +59,10 @@ public function payoutCanBeCalledForCardType() $this->assertEquals(self::RETURN_URL, $payout->getReturnUrl()); $this->assertAmounts($payment, 0, 0, -100, 0); + + $traceId = $payout->getTraceId(); + $this->assertNotEmpty($traceId); + $this->assertSame($traceId, $payout->getPayment()->getTraceId()); } /** @@ -160,10 +164,10 @@ public function payoutShouldAcceptAllParameters() /** @var Card $card */ $card = $this->heidelpay->createPaymentType($this->createCardObject()); $customer = $this->getMinimalCustomer(); - $orderId = self::generateRandomId(); + $orderId = 'o'. self::generateRandomId(); $metadata = (new Metadata())->addMetadata('key', 'value'); $basket = $this->createBasket(); - $invoiceId = self::generateRandomId(); + $invoiceId = 'i'. self::generateRandomId(); $paymentReference = 'paymentReference'; $payout = $card->payout(119.0, 'EUR', self::RETURN_URL, $customer, $orderId, $metadata, $basket, $invoiceId, $paymentReference); diff --git a/test/integration/TransactionTypes/ShipmentTest.php b/test/integration/TransactionTypes/ShipmentTest.php index d3c2063f..b18d87b5 100644 --- a/test/integration/TransactionTypes/ShipmentTest.php +++ b/test/integration/TransactionTypes/ShipmentTest.php @@ -48,7 +48,7 @@ public function shipmentShouldBeCreatableAndFetchable() $this->assertNotNull($charge->getId()); $this->assertNotNull($charge); - $shipment = $this->heidelpay->ship($charge->getPayment(), self::generateRandomId(), self::generateRandomId()); + $shipment = $this->heidelpay->ship($charge->getPayment(), 'i'. self::generateRandomId(), 'i'. self::generateRandomId()); $this->assertNotNull($shipment->getId()); $this->assertNotNull($shipment); @@ -72,12 +72,16 @@ public function shipmentCanBeCalledOnThePaymentObject() $charge = $this->heidelpay->charge(100.0, 'EUR', $invoiceGuaranteed, self::RETURN_URL, $customer); $payment = $charge->getPayment(); - $shipment = $payment->ship(self::generateRandomId(), self::generateRandomId()); + $shipment = $payment->ship('i'. self::generateRandomId(), 'o'. self::generateRandomId()); $this->assertNotNull($shipment); $this->assertNotEmpty($shipment->getId()); $this->assertNotEmpty($shipment->getUniqueId()); $this->assertNotEmpty($shipment->getShortId()); + $traceId = $shipment->getTraceId(); + $this->assertNotEmpty($traceId); + $this->assertSame($traceId, $shipment->getPayment()->getTraceId()); + $fetchedShipment = $this->heidelpay->fetchShipment($shipment->getPayment()->getId(), $shipment->getId()); $this->assertNotEmpty($fetchedShipment); $this->assertEquals($shipment->expose(), $fetchedShipment->expose()); @@ -98,7 +102,7 @@ public function shipmentShouldBePossibleWithPaymentObject() $charge = $this->heidelpay->charge(100.0, 'EUR', $invoiceGuaranteed, self::RETURN_URL, $customer); $payment = $charge->getPayment(); - $shipment = $this->heidelpay->ship($payment, self::generateRandomId(), self::generateRandomId()); + $shipment = $this->heidelpay->ship($payment, 'i'. self::generateRandomId(), 'o'. self::generateRandomId()); $this->assertNotNull($shipment->getId()); $this->assertNotNull($shipment); } @@ -118,7 +122,7 @@ public function shipmentStatusIsSetCorrectly() $charge = $this->heidelpay->charge(100.0, 'EUR', $invoiceGuaranteed, self::RETURN_URL, $customer); $payment = $charge->getPayment(); - $shipment = $this->heidelpay->ship($payment, self::generateRandomId(), self::generateRandomId()); + $shipment = $this->heidelpay->ship($payment, 'i'. self::generateRandomId(), 'o'. self::generateRandomId()); $this->assertSuccess($shipment); } } diff --git a/test/unit/Resources/CustomerTest.php b/test/unit/Resources/CustomerTest.php index ddfc7c4c..de55dc3a 100755 --- a/test/unit/Resources/CustomerTest.php +++ b/test/unit/Resources/CustomerTest.php @@ -64,7 +64,9 @@ public function settersAndGettersShouldWork() $this->assertNull($customer->getMobile()); $this->assertNull($customer->getEmail()); $this->assertNull($customer->getCompany()); - $this->assertInstanceOf(GeoLocation::class, $customer->getGeoLocation()); + $geoLocation = $customer->getGeoLocation(); + $this->assertNull($geoLocation->getClientIp()); + $this->assertNull($geoLocation->getCountryCode()); $customer->setCustomerId('MyCustomerId-123'); $this->assertEquals('MyCustomerId-123', $customer->getCustomerId()); diff --git a/test/unit/Resources/PaymentTest.php b/test/unit/Resources/PaymentTest.php index 33646d40..ab1ea16c 100755 --- a/test/unit/Resources/PaymentTest.php +++ b/test/unit/Resources/PaymentTest.php @@ -60,22 +60,48 @@ class PaymentTest extends BasePaymentTest */ public function gettersAndSettersShouldWorkProperly() { + // initial check $payment = (new Payment())->setParentResource(new Heidelpay('s-priv-1234')); $this->assertNull($payment->getRedirectUrl()); $this->assertNull($payment->getCustomer()); /** @noinspection UnnecessaryAssertionInspection */ $this->assertInstanceOf(Amount::class, $payment->getAmount()); + $this->assertNull($payment->getTraceId()); - $payment->handleResponse((object)['redirectUrl' => 'https://my-redirect-url.test']); - $this->assertEquals('https://my-redirect-url.test', $payment->getRedirectUrl()); - + // update + $ids = (object)['traceId' => 'myTraceId']; + $payment->handleResponse((object)['redirectUrl' => 'https://my-redirect-url.test', 'processing' => $ids]); $authorize = new Authorization(); $payment->setAuthorization($authorize); - $this->assertSame($authorize, $payment->getAuthorization(true)); - $payout = new Payout(); $payment->setPayout($payout); + + // check + $this->assertEquals('https://my-redirect-url.test', $payment->getRedirectUrl()); + $this->assertSame($authorize, $payment->getAuthorization(true)); $this->assertSame($payout, $payment->getPayout(true)); + $this->assertSame('myTraceId', $payment->getTraceId()); + } + + /** + * @test + * + * @throws HeidelpayApiException A HeidelpayApiException is thrown if there is an error returned on API-request. + * @throws RuntimeException A RuntimeException is thrown when there is an error while using the SDK. + * + * Todo: Workaround to be removed when API sends TraceID in processing-group + */ + public function checkTraceIdWorkaround() + { + // initial check + $payment = (new Payment())->setParentResource(new Heidelpay('s-priv-1234')); + $this->assertNull($payment->getTraceId()); + + // update + $payment->handleResponse((object)['resources' => (object)['traceId' => 'myTraceId']]); + + // check + $this->assertSame('myTraceId', $payment->getTraceId()); } /** diff --git a/test/unit/Resources/PaymentTypes/CardTest.php b/test/unit/Resources/PaymentTypes/CardTest.php index ab419c6b..1ca1ca8d 100755 --- a/test/unit/Resources/PaymentTypes/CardTest.php +++ b/test/unit/Resources/PaymentTypes/CardTest.php @@ -29,6 +29,7 @@ use heidelpayPHP\test\BasePaymentTest; use PHPUnit\Framework\AssertionFailedError; use PHPUnit\Framework\Exception; +use ReflectionException; use RuntimeException; use stdClass; @@ -105,6 +106,10 @@ public function constructorShouldSetParameters() $this->assertEquals($number, $card->getNumber()); $this->assertEquals($expiryDate, $card->getExpiryDate()); + + $geoLocation = $card->getGeoLocation(); + $this->assertNull($geoLocation->getClientIp()); + $this->assertNull($geoLocation->getCountryCode()); } /** @@ -183,6 +188,24 @@ public function verifyCvcCanBeSetAndChanged() * @throws Exception */ public function verifyHolderCanBeSetAndChanged() + { + $this->assertEquals(null, $this->card->getCardHolder()); + $this->card->setCardHolder('Julia Heideich'); + $this->assertEquals('Julia Heideich', $this->card->getCardHolder()); + $this->card->setCardHolder(self::TEST_HOLDER); + $this->assertEquals(self::TEST_HOLDER, $this->card->getCardHolder()); + } + + /** + * Verify setting holder. + * + * @test + * + * @throws Exception + * + * @deprecated since 1.2.7.2 + */ + public function verifyHolderCanBeSetAndChangedOld() { $this->assertEquals(null, $this->card->getHolder()); $this->card->setHolder('Julia Heideich'); @@ -191,6 +214,28 @@ public function verifyHolderCanBeSetAndChanged() $this->assertEquals(self::TEST_HOLDER, $this->card->getHolder()); } + /** + * Verify setting holder. + * + * @test + * + * @throws Exception + * @throws \PHPUnit\Framework\MockObject\RuntimeException + * @throws ReflectionException + * + * @deprecated since 1.2.7.2 + */ + public function verifyHolderSettersPropagate() + { + $cardMock = $this->getMockBuilder(Card::class)->disableOriginalConstructor()->setMethods(['setCardHolder', 'getCardHolder'])->getMock(); + $cardMock->expects($this->once())->method('setCardHolder')->with('set my CardHolder'); + $cardMock->expects($this->once())->method('getCardHolder')->willReturn('get my CardHolder'); + + /** @var Card $cardMock */ + $cardMock->setHolder('set my CardHolder'); + $this->assertSame('get my CardHolder', $cardMock->getHolder()); + } + /** * Verify card3ds flag. * @@ -225,25 +270,32 @@ public function card3dsFlagShouldBeSettableInCardResource() */ public function verifyCardCanBeUpdated() { - $testResponse = new stdClass(); - $testResponse->id = self::TEST_ID; - $testResponse->number = self::TEST_NUMBER; - $testResponse->brand = self::TEST_BRAND; - $testResponse->cvc = self::TEST_CVC; - $testResponse->expiryDate = self::TEST_EXPIRY_DATE; - $testResponse->holder = self::TEST_HOLDER; + $newGeoLocation = (object)['clientIp' => 'client ip', 'countryCode' => 'country code']; + $newValues = (object)[ + 'id' => self::TEST_ID, + 'number' => self::TEST_NUMBER, + 'brand' => self::TEST_BRAND, + 'cvc' => self::TEST_CVC, + 'expiryDate' => self::TEST_EXPIRY_DATE, + 'cardHolder' => self::TEST_HOLDER, + 'geolocation' => $newGeoLocation + ]; - $this->card->handleResponse($testResponse); + $this->card->handleResponse($newValues); $this->assertEquals(self::TEST_ID, $this->card->getId()); $this->assertEquals(self::TEST_NUMBER, $this->card->getNumber()); $this->assertEquals(self::TEST_BRAND, $this->card->getBrand()); $this->assertEquals(self::TEST_CVC, $this->card->getCvc()); $this->assertEquals(self::TEST_EXPIRY_DATE, $this->card->getExpiryDate()); - $this->assertEquals(self::TEST_HOLDER, $this->card->getHolder()); + $this->assertEquals(self::TEST_HOLDER, $this->card->getCardHolder()); $cardDetails = $this->card->getCardDetails(); $this->assertNull($cardDetails); + $geoLocation = $this->card->getGeoLocation(); + $this->assertEquals('client ip', $geoLocation->getClientIp()); + $this->assertEquals('country code', $geoLocation->getCountryCode()); + $cardDetails = new stdClass; $cardDetails->cardType = 'my card type'; $cardDetails->account = 'CREDIT'; @@ -252,15 +304,15 @@ public function verifyCardCanBeUpdated() $cardDetails->issuerName = 'my issuer name'; $cardDetails->issuerUrl = 'https://my.issuer.url'; $cardDetails->issuerPhoneNumber = '+49 6221 6471-400'; - $testResponse->cardDetails = $cardDetails; + $newValues->cardDetails = $cardDetails; - $this->card->handleResponse($testResponse); + $this->card->handleResponse($newValues); $this->assertEquals(self::TEST_ID, $this->card->getId()); $this->assertEquals(self::TEST_NUMBER, $this->card->getNumber()); $this->assertEquals(self::TEST_BRAND, $this->card->getBrand()); $this->assertEquals(self::TEST_CVC, $this->card->getCvc()); $this->assertEquals(self::TEST_EXPIRY_DATE, $this->card->getExpiryDate()); - $this->assertEquals(self::TEST_HOLDER, $this->card->getHolder()); + $this->assertEquals(self::TEST_HOLDER, $this->card->getCardHolder()); $details = $this->card->getCardDetails(); $this->assertInstanceOf(CardDetails::class, $details); $this->assertEquals('my card type', $details->getCardType()); diff --git a/test/unit/Resources/TransactionTypes/AbstractTransactionTypeTest.php b/test/unit/Resources/TransactionTypes/AbstractTransactionTypeTest.php index baa19fa7..534e0e99 100755 --- a/test/unit/Resources/TransactionTypes/AbstractTransactionTypeTest.php +++ b/test/unit/Resources/TransactionTypes/AbstractTransactionTypeTest.php @@ -49,11 +49,15 @@ class AbstractTransactionTypeTest extends BasePaymentTest */ public function theGettersAndSettersShouldWorkProperly() { + // initial check $payment = new Payment(); $transactionType = new DummyTransactionType(); $this->assertNull($transactionType->getPayment()); $this->assertNull($transactionType->getDate()); $this->assertNull($transactionType->getPaymentId()); + $this->assertNull($transactionType->getShortId()); + $this->assertNull($transactionType->getUniqueId()); + $this->assertNull($transactionType->getTraceId()); $this->assertFalse($transactionType->isError()); $this->assertFalse($transactionType->isSuccess()); @@ -66,27 +70,54 @@ public function theGettersAndSettersShouldWorkProperly() $transactionType->setPayment($payment); $this->assertNull($transactionType->getRedirectUrl()); + // update $payment->setId('MyPaymentId'); $date = (new DateTime('now'))->format('Y-m-d H:i:s'); - $transactionType->setPayment($payment); $transactionType->setDate($date); - $transactionType->handleResponse((object)['isError' => true, 'isPending' => true, 'isSuccess' => true]); + $ids = (object)['shortId' => 'myShortId', 'uniqueId' => 'myUniqueId', 'traceId' => 'myTraceId']; + $transactionType->handleResponse((object)['isError' => true, 'isPending' => true, 'isSuccess' => true, 'processing' => $ids]); $messageResponse = (object)['code' => '1234', 'customer' => 'Customer message!']; $transactionType->handleResponse((object)['message' => $messageResponse]); + // check again $this->assertSame($payment, $transactionType->getPayment()); - $this->assertEquals($date, $transactionType->getDate()); + $this->assertSame($date, $transactionType->getDate()); $this->assertNull($transactionType->getExternalId()); - $this->assertEquals($payment->getId(), $transactionType->getPaymentId()); + $this->assertSame($payment->getId(), $transactionType->getPaymentId()); $this->assertTrue($transactionType->isSuccess()); $this->assertTrue($transactionType->isPending()); $this->assertTrue($transactionType->isError()); + $this->assertSame('myShortId', $transactionType->getShortId()); + $this->assertSame('myUniqueId', $transactionType->getUniqueId()); + $this->assertSame('myTraceId', $transactionType->getTraceId()); $message = $transactionType->getMessage(); $this->assertSame('1234', $message->getCode()); $this->assertSame('Customer message!', $message->getCustomer()); } + /** + * Verify getters and setters work properly. + * + * @test + * + * @throws \Exception + * + * Todo: Workaround to be removed when API sends TraceID in processing-group + */ + public function checkTraceIdWorkaround() + { + // initial check + $transactionType = new DummyTransactionType(); + $this->assertNull($transactionType->getTraceId()); + + // update + $transactionType->handleResponse((object)['resources' => (object)['traceId' => 'myTraceId']]); + + // check again + $this->assertSame('myTraceId', $transactionType->getTraceId()); + } + /** * Verify getRedirectUrl() calls Payment::getRedirectUrl(). * diff --git a/test/unit/Services/HttpServiceTest.php b/test/unit/Services/HttpServiceTest.php index 581eb355..8200e0b4 100755 --- a/test/unit/Services/HttpServiceTest.php +++ b/test/unit/Services/HttpServiceTest.php @@ -124,7 +124,7 @@ static function ($url) { '{"dummyResource": "JsonSerialized"}', 'GET' ); - $adapterMock->expects($this->once())->method('setUserAgent')->with('HeidelpayPHP'); + $adapterMock->expects($this->once())->method('setUserAgent')->with('heidelpayPHP'); $headers = [ 'Authorization' => 'Basic cy1wcml2LU15VGVzdEtleTo=', 'Content-Type' => 'application/json', diff --git a/test/unit/Services/PaymentServiceTest.php b/test/unit/Services/PaymentServiceTest.php index 91287a2e..76a409ca 100755 --- a/test/unit/Services/PaymentServiceTest.php +++ b/test/unit/Services/PaymentServiceTest.php @@ -24,6 +24,7 @@ */ namespace heidelpayPHP\test\unit\Services; +use heidelpayPHP\Constants\ApiResponseCodes; use heidelpayPHP\Constants\TransactionTypes; use heidelpayPHP\Exceptions\HeidelpayApiException; use heidelpayPHP\Heidelpay; @@ -62,8 +63,6 @@ class PaymentServiceTest extends BasePaymentTest * Verify setters and getters work properly. * * @test - * - * @throws RuntimeException */ public function gettersAndSettersShouldWorkProperly() { @@ -100,7 +99,7 @@ public function authorizeShouldCreateNewAuthorizationAndPayment($card3ds) $metadata = (new Metadata())->setId('myMetadataId'); $basket = (new Basket())->setId('myBasketId'); - /** @var ResourceServiceInterface|MockObject $resourceSrvMock */ + /** @var ResourceService|MockObject $resourceSrvMock */ $resourceSrvMock = $this->getMockBuilder(ResourceService::class)->disableOriginalConstructor()->setMethods(['createResource'])->getMock(); $paymentSrv = (new Heidelpay('s-priv-123'))->setResourceService($resourceSrvMock)->getPaymentService(); $resourceSrvMock->expects($this->once())->method('createResource') @@ -166,7 +165,7 @@ public function chargeShouldCreateNewPaymentAndCharge($card3ds) in_array($charge, $newPayment->getCharges(), true); })); - /** @var ResourceServiceInterface $resourceSrvMock */ + /** @var ResourceService $resourceSrvMock */ $paymentSrv = $heidelpay->setResourceService($resourceSrvMock)->getPaymentService(); $returnedCharge = $paymentSrv->charge(1.234, 'myCurrency', $paymentType, 'myUrl', $customer, 'myId', $metadata, $basket, $card3ds); $this->assertSame($paymentType, $returnedCharge->getPayment()->getPaymentType()); @@ -229,7 +228,7 @@ public function chargePaymentShouldCallCreateOnResourceServiceWithNewCharge() $heidelpay = new Heidelpay('s-priv-123'); $payment = (new Payment())->setParentResource($heidelpay)->setId('myPaymentId'); - /** @var ResourceServiceInterface|MockObject $resourceSrvMock */ + /** @var ResourceService|MockObject $resourceSrvMock */ $resourceSrvMock = $this->getMockBuilder(ResourceService::class)->disableOriginalConstructor()->setMethods(['createResource'])->getMock(); $resourceSrvMock->expects($this->once())->method('createResource') ->with($this->callback(static function ($charge) use ($payment) { @@ -264,7 +263,7 @@ public function chargePaymentShouldSetArgumentsInNewChargeObject() $heidelpay = new Heidelpay('s-priv-123'); $payment = (new Payment())->setParentResource($heidelpay)->setId('myPaymentId'); - /** @var ResourceServiceInterface|MockObject $resourceSrvMock */ + /** @var ResourceService|MockObject $resourceSrvMock */ $resourceSrvMock = $this->getMockBuilder(ResourceService::class)->disableOriginalConstructor()->setMethods(['createResource'])->getMock(); $resourceSrvMock->expects($this->once())->method('createResource') ->with($this->callback(static function ($charge) use ($payment) { @@ -304,22 +303,54 @@ public function cancelAuthorizationShouldCallCreateOnResourceServiceWithNewCance $payment = (new Payment())->setParentResource($heidelpay)->setId('myPaymentId'); $authorization = (new Authorization())->setPayment($payment)->setId('s-aut-1'); - /** @var ResourceServiceInterface|MockObject $resourceSrvMock */ + /** @var ResourceService|MockObject $resourceSrvMock */ $resourceSrvMock = $this->getMockBuilder(ResourceService::class)->disableOriginalConstructor()->setMethods(['createResource'])->getMock(); $resourceSrvMock->expects($this->once())->method('createResource') - ->with($this->callback(static function ($cancellation) use ($authorization, $payment) { + ->with($this->callback(static function ($cancellation) use ($payment) { /** @var Cancellation $cancellation */ $newPayment = $cancellation->getPayment(); return $cancellation instanceof Cancellation && $cancellation->getAmount() === 12.122 && $newPayment instanceof Payment && - $newPayment === $payment && - in_array($cancellation, $authorization->getCancellations(), true); - })); + $newPayment === $payment; + }))->will($this->returnArgument(0)); $cancelSrv = $heidelpay->setResourceService($resourceSrvMock)->getCancelService(); $returnedCancellation = $cancelSrv->cancelAuthorization($authorization, 12.122); - $this->assertArraySubset([$returnedCancellation], $authorization->getCancellations()); + + $this->assertSame(12.122, $returnedCancellation->getAmount()); + $this->assertSame($payment, $returnedCancellation->getPayment()); + } + + /** + * Verify cancelAuthorization will create a cancellation object and call create on ResourceService with it. + * + * @test + * + * @throws HeidelpayApiException + * @throws ReflectionException + * @throws RuntimeException + */ + public function cancelAuthorizationShouldNotAddCancellationIfCancellationFails(): void + { + $heidelpay = new Heidelpay('s-priv-123'); + $payment = (new Payment())->setParentResource($heidelpay)->setId('myPaymentId'); + $authorization = (new Authorization())->setPayment($payment)->setId('s-aut-1'); + + /** @var ResourceService|MockObject $resourceSrvMock */ + $resourceSrvMock = $this->getMockBuilder(ResourceService::class)->disableOriginalConstructor()->setMethods(['createResource'])->getMock(); + $cancellationException = new HeidelpayApiException( + 'Cancellation failed', + 'something went wrong', + ApiResponseCodes::API_ERROR_ALREADY_CANCELLED + ); + $resourceSrvMock->expects($this->once())->method('createResource')->willThrowException($cancellationException); + + $cancelSrv = $heidelpay->setResourceService($resourceSrvMock)->getCancelService(); + $this->expectException(HeidelpayApiException::class); + $this->expectExceptionCode(ApiResponseCodes::API_ERROR_ALREADY_CANCELLED); + $cancelSrv->cancelAuthorization($authorization, 12.122); + $this->assertCount(0, $authorization->getCancellations()); } /** @@ -336,7 +367,7 @@ public function cancelAuthorizationByPaymentShouldCallCancelAuthorization() $authorization = (new Authorization())->setId('s-aut-1'); $heidelpay = new Heidelpay('s-priv-1234'); - /** @var ResourceServiceInterface|MockObject $resourceSrvMock */ + /** @var ResourceService|MockObject $resourceSrvMock */ $resourceSrvMock = $this->getMockBuilder(ResourceService::class)->setMethods(['fetchAuthorization'])->disableOriginalConstructor()->getMock(); $resourceSrvMock->expects($this->exactly(2))->method('fetchAuthorization')->willReturn($authorization); /** @var CancelService|MockObject $cancelSrvMock */ @@ -391,7 +422,7 @@ public function cancelChargeShouldCreateCancellationAndCallsCreate() $payment = (new Payment())->setParentResource($heidelpay); $charge = (new Charge())->setPayment($payment); - /** @var ResourceServiceInterface|MockObject $resourceSrvMock */ + /** @var ResourceService|MockObject $resourceSrvMock */ $resourceSrvMock = $this->getMockBuilder(ResourceService::class)->setMethods(['createResource'])->disableOriginalConstructor()->getMock(); $resourceSrvMock->expects($this->once())->method('createResource') ->with($this->callback(static function ($cancellation) use ($payment, $charge) { @@ -424,7 +455,7 @@ public function shipShouldCreateShipmentAndCallCreateOnResourceServiceWithIt() $heidelpay = new Heidelpay('s-priv-1234'); $payment = new Payment(); - /** @var ResourceServiceInterface|MockObject $resourceSrvMock */ + /** @var ResourceService|MockObject $resourceSrvMock */ $resourceSrvMock = $this->getMockBuilder(ResourceService::class)->setMethods(['createResource'])->disableOriginalConstructor()->getMock(); $resourceSrvMock->expects($this->exactly(2))->method('createResource') ->with($this->callback(static function ($shipment) use ($payment) { @@ -460,7 +491,7 @@ public function payoutShouldCreatePaymentAndCallPayoutWithPayment() $customer = (new Customer())->setId('customerId'); $metadata = (new Metadata())->setId('metadataId'); - /** @var ResourceServiceInterface|MockObject $resourceSrvMock */ + /** @var ResourceService|MockObject $resourceSrvMock */ $resourceSrvMock = $this->getMockBuilder(ResourceService::class)->disableOriginalConstructor()->setMethods(['createResource'])->getMock(); $resourceSrvMock->expects(self::once())->method('createResource') ->with(self::callback(static function ($payout) use ($customer, $metadata) { @@ -493,7 +524,7 @@ public function payoutShouldCreateNewPayout() $metadata = (new Metadata())->setId('id-3'); $heidelpay = new Heidelpay('s-priv-123'); - /** @var ResourceServiceInterface|MockObject $resourceSrvMock */ + /** @var ResourceService|MockObject $resourceSrvMock */ $resourceSrvMock = $this->getMockBuilder(ResourceService::class)->disableOriginalConstructor()->setMethods(['createResource'])->getMock(); $resourceSrvMock->expects($this->once())->method('createResource') ->with($this->callback(static function ($payout) use ($customer, $basket, $metadata) { @@ -548,7 +579,7 @@ public function paymentShouldBeCreatedByInitPayPage(string $action) { $method = 'initPayPage' . $action; - /** @var ResourceServiceInterface|MockObject $resourceSrvMock */ + /** @var ResourceService|MockObject $resourceSrvMock */ $resourceSrvMock = $this->getMockBuilder(ResourceService::class)->setMethods(['createResource'])->disableOriginalConstructor()->getMock(); $paymentSrv = (new Heidelpay('s-priv-1234'))->setResourceService($resourceSrvMock)->getPaymentService(); @@ -592,7 +623,7 @@ public function paymentShouldBeCreatedByInitPayPage(string $action) public function fetchInstalmentPlansWillCallFetchOnResourceService() { $heidelpay = new Heidelpay('s-priv-1234'); - /** @var MockObject|ResourceServiceInterface $resourceSrvMock */ + /** @var MockObject|ResourceService $resourceSrvMock */ $resourceSrvMock = $this->getMockBuilder(ResourceService::class)->setConstructorArgs(['heidelpay' => $heidelpay])->setMethods(['fetchResource'])->getMock(); $heidelpay->setResourceService($resourceSrvMock);