diff --git a/CHANGELOG.md b/CHANGELOG.md index 72d54f30..fb516714 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,6 +6,20 @@ ## Latest version #### Enhancements: +- GP-API: Onboard merchants feature +- GP-API: Decoupled Authentication + +#### Bug Fixes: +- GP-API: Fix phone country code for ISO code "DO" +- GP-API/GP-ECOM: Fix end-to-end examples +- Portico: APPLE PAY / GOOGLE PAY fix + +## v6.0.0 (11/03/2022) +#### Enhancements: +- Security vulnerabilities fixes + +## v6.0.0 (10/20/2022) +#### Enhancements: - GP-API/GP-ECOM: Sunset 3DS1 - Add method on CountryUtil to extract phone country code based on ISO-2/ISO-3/the name of the country - GP-API Update unit tests with new set of credentials for GP-API diff --git a/examples/gp-api/end-to-end/check3dsVersion.php b/examples/gp-api/end-to-end/check3dsVersion.php index 4642c067..802cb240 100644 --- a/examples/gp-api/end-to-end/check3dsVersion.php +++ b/examples/gp-api/end-to-end/check3dsVersion.php @@ -14,17 +14,7 @@ // TODO: consume card data sent from the JS Library ($requestData) -$rawData = ""; -try { - if (file_exists('php://input')) { - $rawData = json_decode(file_get_contents($rawData)); - } -} catch (ApiException $e) { - // TODO: add your error handling here - print_r($e); -} - -$decodedData = json_decode($rawData); +$decodedData = json_decode(file_get_contents('php://input')); $paymenttoken = $decodedData->tokenResponse; // configure client & request settings diff --git a/examples/gp-api/end-to-end/initiateAuthentication.php b/examples/gp-api/end-to-end/initiateAuthentication.php index a99edb55..fd3a3685 100644 --- a/examples/gp-api/end-to-end/initiateAuthentication.php +++ b/examples/gp-api/end-to-end/initiateAuthentication.php @@ -26,15 +26,7 @@ use GlobalPayments\Api\Services\Secure3dService; use GlobalPayments\Api\ServicesContainer; -$requestData = ""; -try { - if (file_exists('php://input')) { - $requestData = json_decode(file_get_contents($requestData)); - } -} catch (Exception $e) { - // TODO: add your error handling here - print_r($e); -} +$requestData = json_decode(file_get_contents('php://input')); $config = new GpApiConfig(); $config->appId = GenerateToken::APP_ID; diff --git a/examples/gp-ecom/3DS2-Challenge/with-GP-js-library/ThreeDSecure2/CheckVersion.php b/examples/gp-ecom/3DS2-Challenge/with-GP-js-library/ThreeDSecure2/CheckVersion.php index e6755463..5e45c8c8 100644 --- a/examples/gp-ecom/3DS2-Challenge/with-GP-js-library/ThreeDSecure2/CheckVersion.php +++ b/examples/gp-ecom/3DS2-Challenge/with-GP-js-library/ThreeDSecure2/CheckVersion.php @@ -22,15 +22,7 @@ $config->merchantContactUrl = 'https://www.example.com'; ServicesContainer::configureService($config); -$requestData = ""; -try { - if (file_exists('php://input')) { - $requestData = json_decode(file_get_contents($requestData)); - } -} catch (Exception $e) { - // TODO: add your error handling here - print_r($e); -} +$requestData = json_decode(file_get_contents('php://input')); $cardData = $requestData->card; $card = new CreditCardData(); diff --git a/metadata.xml b/metadata.xml index 69a1ba93..ba315a23 100644 --- a/metadata.xml +++ b/metadata.xml @@ -1,3 +1,3 @@ - 6.0.1 + 6.0.2 \ No newline at end of file diff --git a/src/Builders/PayFacBuilder.php b/src/Builders/PayFacBuilder.php index 4626b1e2..0c6a56fa 100644 --- a/src/Builders/PayFacBuilder.php +++ b/src/Builders/PayFacBuilder.php @@ -1,6 +1,13 @@ + */ + public $productData = []; + + /** + * @var PersonList + */ + public $personsData; + + /** + * @var integer + */ + public $page; + + /** + * @var integer + */ + public $pageSize; + + /** + * @var PaymentStatistics + */ + public $paymentStatistics; + + /** + * @var StatusChangeReason + */ + public $statusChangeReason; + + /** @var User */ + public $userReference; + + /** + * @var array + */ + public $paymentMethodsFunctions; + + /** @var string */ + public $idempotencyKey; + const UPLOAD_FILE_TYPES = [ 'tif', 'tiff', 'bmp', 'jpg', 'jpeg', 'gif', 'png', 'doc', 'docx' ]; @@ -72,9 +127,34 @@ public function __construct($type) public function execute($configName = 'default') { parent::execute($configName); - $client = ServicesContainer::instance()->getPayFac($configName); - return $client->processPayFac($this); + switch ($this->transactionModifier) + { + case TransactionModifier::MERCHANT: + return $client->processBoardingUser($this); + default: + return $client->processPayFac($this); + } + } + + public function __get($name) + { + switch ($name) { + case 'userId': + if ($this->userReference instanceof UserReference) { + return $this->userReference->userId; + } + return null; + default: + break; + } + } + + public function __isset($name) + { + return in_array($name, [ + 'userId', + ]) || isset($this->{$name}); } protected function setupValidations() @@ -87,7 +167,7 @@ protected function setupValidations() ->check('businessData')->isNotNull() ->check('userPersonalData')->isNotNull() ->check('creditCardInformation')->isNotNull(); - + $this->validations->of( TransactionType::EDIT | TransactionType::RESET_PASSWORD | @@ -108,31 +188,31 @@ protected function setupValidations() ) ->with(TransactionModifier::NONE) ->check('accountNumber')->isNotNull(); - + $this->validations->of( TransactionType::UPDATE_OWNERSHIP_DETAILS ) ->with(TransactionModifier::NONE) ->check('beneficialOwnerData')->isNotNull(); - + $this->validations->of( TransactionType::UPLOAD_CHARGEBACK_DOCUMENT ) ->with(TransactionModifier::NONE) ->check('uploadDocumentData')->isNotNull(); - + $this->validations->of( TransactionType::OBTAIN_SSO_KEY ) ->with(TransactionModifier::NONE) ->check('singleSignOnData')->isNotNull(); - + $this->validations->of( TransactionType::UPDATE_BANK_ACCOUNT_OWNERSHIP ) ->with(TransactionModifier::NONE) ->check('beneficialOwnerData')->isNotNull(); - + $this->validations->of( TransactionType::ADD_FUNDS | TransactionType::SWEEP_FUNDS | @@ -143,30 +223,37 @@ protected function setupValidations() ) ->with(TransactionModifier::NONE) ->check('amount')->isNotNull(); - + $this->validations->of(TransactionType::ADD_CARD_FLASH_FUNDS) ->with(TransactionModifier::NONE) ->check('flashFundsPaymentCardData')->isNotNull(); - + $this->validations->of(TransactionType::DISBURSE_FUNDS) ->with(TransactionModifier::NONE) ->check('receivingAccountNumber')->isNotNull(); - + $this->validations->of(TransactionType::SPEND_BACK) ->with(TransactionModifier::NONE) ->check('allowPending')->isNotNull() ->check('receivingAccountNumber')->isNotNull(); - + $this->validations->of(TransactionType::SPLIT_FUNDS) ->with(TransactionModifier::NONE) ->check('transNum')->isNotNull() ->check('receivingAccountNumber')->isNotNull(); - + $this->validations->of(TransactionType::REVERSE_SPLITPAY) ->with(TransactionModifier::NONE) ->check('transNum')->isNotNull() ->check('requireCCRefund')->isNotNull() ->check('ccAmount')->isNotNull(); + + $this->validations->of( + TransactionType::FETCH | + TransactionType::EDIT + ) + ->with(TransactionModifier::MERCHANT) + ->check('userId')->isNotNull(); } /* @@ -174,9 +261,13 @@ protected function setupValidations() * * var Object GlobalPayments\Api\Entities\PayFac\BankAccountData; */ - public function withBankAccountData(BankAccountData $bankAccountData) + public function withBankAccountData(BankAccountData $bankAccountData, $paymentMethodFunction = null) { $this->bankAccountData = $bankAccountData; + if (!empty($paymentMethodFunction)) { + $paymentMethodFunction = PaymentMethodFunction::validate($paymentMethodFunction); + $this->paymentMethodsFunctions[get_class($bankAccountData)] = $paymentMethodFunction; + } return $this; } /* @@ -232,9 +323,14 @@ public function withUserPersonalData(UserPersonalData $userPersonalData) return $this; } - public function withCreditCardData($creditCardInformation) + public function withCreditCardData($creditCardInformation, $paymentMethodFunction = null) { $this->creditCardInformation = $creditCardInformation; + if (!empty($paymentMethodFunction)) { + $paymentMethodFunction = PaymentMethodFunction::validate($paymentMethodFunction); + $this->paymentMethodsFunctions[get_class($creditCardInformation)] = $paymentMethodFunction; + } + return $this; } @@ -390,5 +486,80 @@ public function withDeviceDetails($deviceDetails) $this->deviceDetails = $deviceDetails; return $this; } - + + public function withDescription($description) + { + $this->description = $description; + return $this; + } + + /** + * Set the request productData + * + * @param array $productData Request productData + * + * @return $this + */ + public function withProductData(array $productData) + { + $this->productData = $productData; + return $this; + } + + /** + * Set the request customer Data + * + * @param PersonList $personsData Request customer Data + * + * @return $this + */ + public function withPersonsData(PersonList $personsData) + { + $this->personsData = $personsData; + return $this; + } + + public function withUserReference(UserReference $userReference) + { + $this->userReference = $userReference; + return $this; + } + + public function withModifier($transactionModifier) + { + $this->transactionModifier = $transactionModifier; + return $this; + } + + public function withPaymentStatistics($paymentStatistics) + { + $this->paymentStatistics = $paymentStatistics; + return $this; + } + + public function withStatusChangeReason($statusChangeReason) + { + $this->statusChangeReason = $statusChangeReason; + return $this; + } + + /** + * Set the gateway paging criteria for the report + * @param $page + * @param $pageSize + * @return $this + */ + public function withPaging($page, $pageSize) + { + $this->page = $page; + $this->pageSize = $pageSize; + return $this; + } + + public function withIdempotencyKey($value) + { + $this->idempotencyKey = $value; + + return $this; + } } diff --git a/src/Builders/ReportBuilder.php b/src/Builders/ReportBuilder.php index a09c9e87..5ccd1505 100644 --- a/src/Builders/ReportBuilder.php +++ b/src/Builders/ReportBuilder.php @@ -21,6 +21,17 @@ abstract class ReportBuilder extends BaseBuilder */ public $timeZoneConversion; + + /** + * @var integer + */ + public $page; + + /** + * @var integer + */ + public $pageSize; + /** * @param ReportType $reportType * @@ -52,4 +63,17 @@ public function execute($configName = 'default') return $client->processReport($this); } + + /** + * Set the gateway paging criteria for the report + * @param $page + * @param $pageSize + * @return $this + */ + public function withPaging($page, $pageSize) + { + $this->page = $page; + $this->pageSize = $pageSize; + return $this; + } } diff --git a/src/Builders/RequestBuilder/GpApi/GpApiPayFacRequestBuilder.php b/src/Builders/RequestBuilder/GpApi/GpApiPayFacRequestBuilder.php new file mode 100644 index 00000000..132df63c --- /dev/null +++ b/src/Builders/RequestBuilder/GpApi/GpApiPayFacRequestBuilder.php @@ -0,0 +1,318 @@ +builder = $builder; + $requestData = $queryParams = null; + switch ($builder->transactionType) { + case TransactionType::CREATE: + if (TransactionModifier::MERCHANT) { + $endpoint = GpApiRequest::MERCHANT_MANAGEMENT_ENDPOINT; + $verb = 'POST'; + if (empty($builder->userPersonalData)) { + throw new ArgumentException('Merchant data is mandatory!'); + } + $requestData = $this->buildCreateMerchantRequest(); + } + break; + case TransactionType::EDIT: + if (TransactionModifier::MERCHANT) { + $endpoint = GpApiRequest::MERCHANT_MANAGEMENT_ENDPOINT . '/' . $builder->userReference->userId; + $verb = 'PATCH'; + $requestData = $this->buildEditMerchantRequest(); + } + break; + case TransactionType::FETCH: + if (TransactionModifier::MERCHANT) { + $endpoint = GpApiRequest::MERCHANT_MANAGEMENT_ENDPOINT . '/' . $builder->userId; + $verb = 'GET'; + } + break; + default: + return ''; + } + + if (empty($endpoint)) { + throw new ArgumentException('Action not available on this service!'); + } + return new GpApiRequest($endpoint, $verb, $requestData, $queryParams); + } + + private function setPaymentMethod() + { + if (!empty($this->builder->creditCardInformation)) { + $cardInfo = [ + 'functions' => $this->builder->paymentMethodsFunctions[get_class($this->builder->creditCardInformation)] ?? null, + 'card' => $this->builder->creditCardInformation instanceof CreditCardData ? + $this->mapCreditCardInfo($this->builder->creditCardInformation) : null + ]; + } + if (!empty($this->builder->bankAccountData)) { + $bankData = [ + 'functions' => $this->builder->paymentMethodsFunctions[get_class($this->builder->bankAccountData)] ?? null, + 'name' => !empty($this->builder->bankAccountData) ? $this->builder->bankAccountData->accountHolderName : null, + 'bank_transfer' => $this->builder->bankAccountData instanceof BankAccountData ? + $this->mapBankTransferInfo($this->builder->bankAccountData) : null + ]; + } + return [ + $cardInfo ?? null, + $bankData ?? null + ]; + } + + private function mapBankTransferInfo(BankAccountData $bankAccountData) + { + return [ + 'account_holder_type' => $bankAccountData->accountOwnershipType, + 'account_number' => $bankAccountData->accountNumber, + 'account_type' => $bankAccountData->accountType, + 'bank' => [ + 'name' => $bankAccountData->bankName, + 'code' => $bankAccountData->routingNumber, //@TODO confirmantion from GP-API team + 'international_code' => '', //@TODO + 'address' => [ + 'line_1' => $bankAccountData->bankAddress->streetAddress1 ?? null, + 'line_2' => $bankAccountData->bankAddress->streetAddress2 ?? null, + 'line_3' => $bankAccountData->bankAddress->streetAddress3 ?? null, + 'city' => $bankAccountData->bankAddress->city ?? null, + 'postal_code' => $bankAccountData->bankAddress->postalCode ?? null, + 'state' => $bankAccountData->bankAddress->state ?? null, + 'country' => !empty($bankAccountData->bankAddress) ? + CountryUtils::getCountryCodeByCountry($bankAccountData->bankAddress->countryCode) : '', + ] + ] + ]; + } + + private function mapCreditCardInfo(CreditCardData $creditCardInformation) + { + return [ + 'name' => $creditCardInformation->cardHolderName, + 'number' => $creditCardInformation->number, + 'expiry_month' => substr($creditCardInformation->expMonth, 2, 2), + 'expiry_year' => substr($creditCardInformation->expYear, 0, 2) + ]; + } + + private function setProductList($productData) + { + /** @var Product $product */ + foreach ($productData as $product) { + if (!$product instanceof Product) { + continue; + } + $products[] = [ + 'quantity' => $product->quantity, + 'id' => $product->productId + ]; + } + + return $products ?? []; + } + + private function setAddressList() + { + /** @var UserPersonalData $merchantData */ + $merchantData = $this->builder->userPersonalData; + $addressList = []; + if (!empty($merchantData->userAddress->streetAddress1)) { + $addressList[AddressType::BUSINESS] = $merchantData->userAddress; + } + if (!empty($merchantData->mailingAddress->streetAddress1)) { + $addressList[AddressType::SHIPPING] = $merchantData->mailingAddress; + } + /** @var Address $address */ + foreach ($addressList as $addressType => $address) { + $addresses[] = [ + 'line_1' => $address->streetAddress1, + 'line_2' => $address->streetAddress2, + 'city' => $address->city, + 'postal_code' => $address->postalCode, + 'state' => $address->state, + 'country' => CountryUtils::getCountryCodeByCountry($address->countryCode), + 'functions' => [$addressType] + ]; + } + + return $addresses ?? []; + } + + /** + * Request body for POST /merchants + * + * @return array + */ + private function buildCreateMerchantRequest() + { + return array_merge( + $this->setMerchantInfo(), + [ + 'description' => $this->builder->description, + 'type' => $this->builder->userPersonalData->type, + 'addresses' => $this->setAddressList(), + 'payment_processing_statistics' => $this->setPaymentStatistics(), + 'tier' => [ + 'reference' => $this->builder->userPersonalData->tier + ], + 'payment_methods' => $this->setPaymentMethod(), + 'persons' => $this->setPersonList(), + 'products' => !empty($this->builder->productData) ? $this->setProductList($this->builder->productData) : null, + ] + ); + } + + private function setMerchantInfo() + { + if (empty($this->builder->userPersonalData)) { + return []; + } + /** @var UserPersonalData $merchantData */ + $merchantData = $this->builder->userPersonalData; + return [ + 'name' => $merchantData->userName, + 'legal_name' => $merchantData->legalName, + 'dba' => $merchantData->dba, + 'merchant_category_code' => $merchantData->merchantCategoryCode, + 'website' => $merchantData->website, + 'currency' => $merchantData->currencyCode, + 'tax_id_reference' => $merchantData->taxIdReference, + 'notification_email' => $merchantData->notificationEmail, + 'status' => $this->builder->userReference->userStatus ?? null, + 'notifications' => [ + 'status_url' => $merchantData->notificationStatusUrl + ] + ]; + } + + private function setPaymentStatistics() + { + if (empty($this->builder->paymentStatistics)) { + return []; + } + return [ + 'total_monthly_sales_amount' => $this->builder->paymentStatistics->totalMonthlySalesAmount, + 'average_ticket_sales_amount' => $this->builder->paymentStatistics->averageTicketSalesAmount, + 'highest_ticket_sales_amount' => $this->builder->paymentStatistics->highestTicketSalesAmount + ]; + } + + private function setPersonList() + { + $persons = []; + if (empty($this->builder->personsData)) { + return $persons; + } + /** @var Person $person */ + foreach ($this->builder->personsData as $person) { + $personInfo = [ + 'functions' => [$person->functions], + 'first_name' => $person->firstName, + 'middle_name' => $person->middleName, + 'last_name' => $person->lastName, + 'email' => $person->email, + 'date_of_birth' => !empty($person->dateOfBirth) ? + (new \DateTime($person->dateOfBirth))->format('Y-m-d') : null, + 'national_id_reference' => $person->nationalIdReference, + 'equity_percentage' => $person->equityPercentage, + 'job_title' => $person->jobTitle + ]; + if (!empty($person->address)) { + $personInfo['address'] = [ + 'line_1' => $person->address->streetAddress1, + 'line_2' => $person->address->streetAddress2, + 'line_3' => $person->address->streetAddress3, + 'city' => $person->address->city, + 'state' => $person->address->state, + 'postal_code' => $person->address->postalCode, + 'country' => $person->address->countryCode, + ]; + } + if (!empty($person->homePhone)) { + $personInfo['contact_phone'] = [ + 'country_code' => $person->homePhone->countryCode, + 'subscriber_number' => $person->homePhone->number, + ]; + } + if (!empty($person->workPhone)) { + $personInfo['work_phone'] = [ + 'country_code' => $person->workPhone->countryCode, + 'subscriber_number' => $person->workPhone->number, + ]; + } + $persons[] = $personInfo; + } + + return $persons; + } + + /** + * Request body for PATCH /merchants/{id} + * + * @return array + */ + private function buildEditMerchantRequest() + { + $requestBody = $this->setMerchantInfo(); + return array_merge( + $requestBody, + [ + 'description' => $this->builder->description, + 'status_change_reason' => $this->builder->statusChangeReason, + 'addresses' => $this->setAddressList(), + 'persons' => $this->setPersonList(), + 'payment_processing_statistics' => $this->setPaymentStatistics(), + 'payment_methods' => $this->setPaymentMethod(), + ] + ); + } +} \ No newline at end of file diff --git a/src/Builders/RequestBuilder/GpApi/GpApiReportRequestBuilder.php b/src/Builders/RequestBuilder/GpApi/GpApiReportRequestBuilder.php index 692c6ade..9ab1b88a 100644 --- a/src/Builders/RequestBuilder/GpApi/GpApiReportRequestBuilder.php +++ b/src/Builders/RequestBuilder/GpApi/GpApiReportRequestBuilder.php @@ -7,18 +7,21 @@ use GlobalPayments\Api\Builders\TransactionReportBuilder; use GlobalPayments\Api\Entities\Enums\GatewayProvider; use GlobalPayments\Api\Entities\Enums\ReportType; +use GlobalPayments\Api\Entities\Enums\TransactionModifier; +use GlobalPayments\Api\Entities\Enums\TransactionType; use GlobalPayments\Api\Entities\GpApi\GpApiRequest; use GlobalPayments\Api\Entities\IRequestBuilder; use GlobalPayments\Api\Mapping\EnumMapping; use GlobalPayments\Api\PaymentMethods\CreditCardData; use GlobalPayments\Api\ServiceConfigs\Gateways\GpApiConfig; use GlobalPayments\Api\Utils\StringUtils; +use GlobalPayments\Api\Entities\Exceptions\ArgumentException; class GpApiReportRequestBuilder implements IRequestBuilder { public static function canProcess($builder) { - if ($builder instanceof TransactionReportBuilder) { + if ($builder instanceof ReportBuilder) { return true; } @@ -232,8 +235,14 @@ public function buildRequest(BaseBuilder $builder, $config) $queryParams['expiration_date'] = !empty($builder->searchBuilder->expirationDate) ? $builder->searchBuilder->expirationDate->format('Y-m-d') : null; break; + case ReportType::FIND_MERCHANTS_PAGED: + $endpoint = GpApiRequest::MERCHANT_MANAGEMENT_ENDPOINT; + $verb = 'GET'; + $queryParams['page'] = $builder->page; + $queryParams['page_size'] = $builder->pageSize; + break; default: - return null; + throw new ArgumentException(sprintf("Unknown report type!")); } return new GpApiRequest($endpoint, $verb, $payload, $queryParams); diff --git a/src/Builders/RequestBuilder/GpApi/GpApiSecure3DRequestBuilder.php b/src/Builders/RequestBuilder/GpApi/GpApiSecure3DRequestBuilder.php index b4a36b56..6c8c0867 100644 --- a/src/Builders/RequestBuilder/GpApi/GpApiSecure3DRequestBuilder.php +++ b/src/Builders/RequestBuilder/GpApi/GpApiSecure3DRequestBuilder.php @@ -5,6 +5,7 @@ use GlobalPayments\Api\Builders\BaseBuilder; use GlobalPayments\Api\Builders\Secure3dBuilder; use GlobalPayments\Api\Entities\Enums\AuthenticationSource; +use GlobalPayments\Api\Entities\Enums\DecoupledFlowRequest; use GlobalPayments\Api\Entities\Enums\GatewayProvider; use GlobalPayments\Api\Entities\Enums\TransactionType; use GlobalPayments\Api\Entities\GpApi\DTO\PaymentMethod; @@ -79,8 +80,8 @@ private function verifyEnrolled(Secure3dBuilder $builder, GpApiConfig $config) $threeDS['payment_method'] = $this->setPaymentMethodParam($builder->paymentMethod); $threeDS['notifications'] = [ 'challenge_return_url' => $config->challengeNotificationUrl, - 'three_ds_method_return_url' => $config->methodNotificationUrl - + 'three_ds_method_return_url' => $config->methodNotificationUrl, + 'decoupled_notification_url' => $builder->decoupledNotificationUrl ?? null ]; if (!empty($builder->storedCredential)) { $this->setStoreCredentialParam($builder->storedCredential, $threeDS); @@ -91,7 +92,6 @@ private function verifyEnrolled(Secure3dBuilder $builder, GpApiConfig $config) private function initiateAuthenticationData(Secure3dBuilder $builder, GpApiConfig $config) { - $threeDS = []; $threeDS['three_ds'] = [ 'source' => (string) $builder->authenticationSource, 'preference' => $builder->challengeRequestIndicator, @@ -233,6 +233,14 @@ private function initiateAuthenticationData(Secure3dBuilder $builder, GpApiConfi 'sdk_trans_reference' => $builder->mobileData->sdkTransReference ]; } + $threeDS['notifications'] = [ + 'decoupled_notification_url' => $builder->decoupledNotificationUrl ?? null + ]; + if (isset($builder->decoupledFlowRequest)) { + $threeDS['decoupled_flow_request'] = $builder->decoupledFlowRequest === true ? DecoupledFlowRequest::DECOUPLED_PREFERRED : + DecoupledFlowRequest::DO_NOT_USE_DECOUPLED; + } + $threeDS['decoupled_flow_timeout'] = $builder->decoupledFlowTimeout ?? null; return $threeDS; } diff --git a/src/Builders/RequestBuilder/RequestBuilderFactory.php b/src/Builders/RequestBuilder/RequestBuilderFactory.php index 59f2973a..5b384a94 100644 --- a/src/Builders/RequestBuilder/RequestBuilderFactory.php +++ b/src/Builders/RequestBuilder/RequestBuilderFactory.php @@ -5,6 +5,7 @@ use GlobalPayments\Api\Builders\BaseBuilder; use GlobalPayments\Api\Builders\RequestBuilder\GpApi\GpApiAuthorizationRequestBuilder; use GlobalPayments\Api\Builders\RequestBuilder\GpApi\GpApiManagementRequestBuilder; +use GlobalPayments\Api\Builders\RequestBuilder\GpApi\GpApiPayFacRequestBuilder; use GlobalPayments\Api\Builders\RequestBuilder\GpApi\GpApiReportRequestBuilder; use GlobalPayments\Api\Builders\RequestBuilder\GpApi\GpApiSecure3DRequestBuilder; use GlobalPayments\Api\Builders\RequestBuilder\GpEcom\GpEcomAuthorizationRequestBuilder; @@ -26,7 +27,8 @@ class RequestBuilderFactory GpApiAuthorizationRequestBuilder::class, GpApiManagementRequestBuilder::class, GpApiReportRequestBuilder::class, - GpApiSecure3DRequestBuilder::class + GpApiSecure3DRequestBuilder::class, + GpApiPayFacRequestBuilder::class ] ]; diff --git a/src/Builders/Secure3dBuilder.php b/src/Builders/Secure3dBuilder.php index 166bd4fd..25f4fed1 100644 --- a/src/Builders/Secure3dBuilder.php +++ b/src/Builders/Secure3dBuilder.php @@ -884,11 +884,7 @@ public function withCustomerEmail($value) */ public function withDecoupledFlowRequest($decoupledFlowRequest) { - if ($decoupledFlowRequest == true) { - $this->decoupledFlowRequest = "TRUE"; - } else { - $this->decoupledFlowRequest = "FALSE"; - } + $this->decoupledFlowRequest = $decoupledFlowRequest; return $this; } diff --git a/src/Builders/TransactionReportBuilder.php b/src/Builders/TransactionReportBuilder.php index ba0e3ba9..3e1d566d 100644 --- a/src/Builders/TransactionReportBuilder.php +++ b/src/Builders/TransactionReportBuilder.php @@ -40,16 +40,6 @@ class TransactionReportBuilder extends ReportBuilder */ public $transactionId; - /** - * @var integer - */ - public $page; - - /** - * @var integer - */ - public $pageSize; - /** * @var TransactionSortProperty */ @@ -205,19 +195,6 @@ public function withTransactionId($value) return $this; } - /** - * Set the gateway paging criteria for the report - * @param $page - * @param $pageSize - * @return $this - */ - public function withPaging($page, $pageSize) - { - $this->page = $page; - $this->pageSize = $pageSize; - return $this; - } - /** * Sets the gateway settlement dispute id as criteria for the report. * diff --git a/src/Builders/UserReportBuilder.php b/src/Builders/UserReportBuilder.php new file mode 100644 index 00000000..95ad5809 --- /dev/null +++ b/src/Builders/UserReportBuilder.php @@ -0,0 +1,41 @@ +transactionType = $reportType; + } + + protected function setupValidations() + { + // TODO: Implement setupValidations() method. + } + + public function withModifier($transactionModifier) + { + $this->transactionModifier = $transactionModifier; + + return $this; + } +} \ No newline at end of file diff --git a/src/Entities/Enums/AddressType.php b/src/Entities/Enums/AddressType.php index 167c4503..3846f977 100644 --- a/src/Entities/Enums/AddressType.php +++ b/src/Entities/Enums/AddressType.php @@ -8,4 +8,5 @@ class AddressType extends Enum { const BILLING = 'BILLING'; const SHIPPING = 'SHIPPING'; + const BUSINESS = 'BUSINESS'; } diff --git a/src/Entities/Enums/DecoupledFlowRequest.php b/src/Entities/Enums/DecoupledFlowRequest.php new file mode 100644 index 00000000..6e4b152a --- /dev/null +++ b/src/Entities/Enums/DecoupledFlowRequest.php @@ -0,0 +1,11 @@ + "Denmark", "numeric" => "208", "alpha2" => "DK", "alpha3" => "DNK", "phoneCode" => ["45"]], ["name" => "Djibouti", "numeric" => "262", "alpha2" => "DJ", "alpha3" => "DJI", "phoneCode" => ["253"]], ["name" => "Dominica", "numeric" => "212", "alpha2" => "DM", "alpha3" => "DMA", "phoneCode" => ["1-767"]], - ["name" => "Dominican Republic", "numeric" => "214", "alpha2" => "DO", "alpha3" => "DOM", "phoneCode" => ["1-809, 1-829, 1-849"]], + ["name" => "Dominican Republic", "numeric" => "214", "alpha2" => "DO", "alpha3" => "DOM", "phoneCode" => ["1-809", "1-829", "1-849"]], ["name" => "Ecuador", "numeric" => "218", "alpha2" => "EC", "alpha3" => "ECU", "phoneCode" => ["593"]], ["name" => "Egypt", "numeric" => "818", "alpha2" => "EG", "alpha3" => "EGY", "phoneCode" => ["20"]], ["name" => "El Salvador", "numeric" => "222", "alpha2" => "SV", "alpha3" => "SLV", "phoneCode" => ["503"]], diff --git a/src/Entities/Enums/PaymentMethodFunction.php b/src/Entities/Enums/PaymentMethodFunction.php new file mode 100644 index 00000000..09f6b695 --- /dev/null +++ b/src/Entities/Enums/PaymentMethodFunction.php @@ -0,0 +1,12 @@ + + */ + public $links; +} \ No newline at end of file diff --git a/src/Entities/User.php b/src/Entities/User.php new file mode 100644 index 00000000..7f590207 --- /dev/null +++ b/src/Entities/User.php @@ -0,0 +1,183 @@ + */ + public $addresses = []; + + /** + * @var PhoneNumber + */ + public $contactPhone; + + /** + * A a further description of the status of merchant boarding. + * + * @var string + */ + public $statusDescription; + + /** + * The result of the action executed. + * + * @var string + */ + public $responseCode; + + /** @var $userReference */ + public $userReference; + + /** @var PersonList */ + public $personList; + + /** @var PaymentMethodList */ + public $paymentMethodList; + + public function __set($name, $value) + { + switch ($name) { + case 'userId': + if (!$this->userReference instanceof UserReference) { + $this->userReference = new UserReference(); + } + $this->userReference->userId = $value; + return; + case 'userType': + if (!$this->userReference instanceof UserReference) { + $this->userReference = new UserReference(); + } + $this->userReference->userType = $value; + return; + case 'userStatus': + if (!$this->userReference instanceof UserReference) { + $this->userReference = new UserReference(); + } + $this->userReference->userStatus = $value; + return; + default: + break; + } + + if (property_exists($this, $name)) { + return $this->{$name} = $value; + } + + throw new ArgumentException(sprintf('Property `%s` does not exist on User', $name)); + } + + public function __get($name) + { + switch ($name) { + case 'userId': + if ($this->userReference !== null) { + return $this->userReference->userId; + } + return null; + case 'userType': + if ($this->userReference !== null) { + return $this->userReference->userType; + } + return null; + case 'userStatus': + if ($this->userReference !== null) { + return $this->userReference->userStatus; + } + return null; + default: + break; + } + + if (property_exists($this, $name)) { + return $this->{$name}; + } + + throw new ArgumentException(sprintf('Property `%s` does not exist on User', $name)); + } + + public function __isset($name) + { + return in_array($name, [ + 'userId', + 'userStatus', + 'userType', + ]) || isset($this->{$name}); + } + + /** + * Creates an `User` object from an existing user ID. + * + * @param string $userId + * @param UserType $userType + * + * @return User + * @throws ArgumentException + */ + public static function fromId(string $userId,string $userType) + { + $userType = UserType::validate($userType); + + $user = new User(); + $user->userReference = new UserReference(); + $user->userReference->userId = $userId; + $user->userReference->userType = $userType; + + return $user; + + } + + public function edit() + { + $builder = (new PayFacBuilder(TransactionType::EDIT)) + ->withUserReference($this->userReference); + + if ($this->userReference->userType !== null) { + $builder = $builder->withModifier(constant( TransactionModifier::class."::{$this->userReference->userType}")); + } + + return $builder; + } +} diff --git a/src/Entities/UserLinks.php b/src/Entities/UserLinks.php new file mode 100644 index 00000000..00146914 --- /dev/null +++ b/src/Entities/UserLinks.php @@ -0,0 +1,23 @@ +maybeSetKey($request, 'merchant_contact_url', $this->merchantContactUrl); $request = $this->maybeSetKey($request, 'merchant_initiated_request_type', $builder->getMerchantInitiatedRequestType()); $request = $this->maybeSetKey($request, 'whitelist_status', $builder->getWhitelistStatus()); - $request = $this->maybeSetKey($request, 'decoupled_flow_request', $builder->getDecoupledFlowRequest()); - $request = $this->maybeSetKey($request, 'decoupled_flow_timeout', $builder->getDecoupledFlowTimeout()); - $request = $this->maybeSetKey($request, 'decoupled_notification_url', $builder->getDecoupledNotificationUrl()); + $request = $this->maybeSetKey($request, 'decoupled_flow_request', $builder->decoupledFlowRequest ?? null); + $request = $this->maybeSetKey($request, 'decoupled_flow_timeout', $builder->decoupledFlowTimeout ?? null); + $request = $this->maybeSetKey($request, 'decoupled_notification_url', $builder->decoupledNotificationUrl ?? null); $request = $this->maybeSetKey($request, 'enable_exemption_optimization', $builder->enableExemptionOptimization); // card details diff --git a/src/Gateways/GpApiConnector.php b/src/Gateways/GpApiConnector.php index 1f6223c3..91853ca8 100644 --- a/src/Gateways/GpApiConnector.php +++ b/src/Gateways/GpApiConnector.php @@ -4,13 +4,16 @@ use GlobalPayments\Api\Builders\AuthorizationBuilder; use GlobalPayments\Api\Builders\ManagementBuilder; +use GlobalPayments\Api\Builders\PayFacBuilder; use GlobalPayments\Api\Builders\ReportBuilder; use GlobalPayments\Api\Builders\RequestBuilder\RequestBuilderFactory; use GlobalPayments\Api\Builders\Secure3dBuilder; use GlobalPayments\Api\Entities\Enums\PaymentMethodType; use GlobalPayments\Api\Entities\Enums\Secure3dVersion; +use GlobalPayments\Api\Entities\Enums\TransactionType; use GlobalPayments\Api\Entities\Exceptions\ApiException; use GlobalPayments\Api\Entities\Exceptions\GatewayException; +use GlobalPayments\Api\Entities\Exceptions\UnsupportedTransactionException; use GlobalPayments\Api\Entities\GpApi\AccessTokenInfo; use GlobalPayments\Api\Entities\GpApi\GpApiRequest; use GlobalPayments\Api\Entities\GpApi\GpApiTokenResponse; @@ -21,12 +24,13 @@ use GlobalPayments\Api\Entities\Reporting\DisputeSummary; use GlobalPayments\Api\Entities\Transaction; use GlobalPayments\Api\Entities\Reporting\TransactionSummary; +use GlobalPayments\Api\Entities\User; use GlobalPayments\Api\PaymentMethods\TransactionReference; use GlobalPayments\Api\ServiceConfigs\Gateways\GpApiConfig; use GlobalPayments\Api\Mapping\GpApiMapping; use GlobalPayments\Api\PaymentMethods\AlternativePaymentMethod; -class GpApiConnector extends RestGateway implements IPaymentGateway, ISecure3dProvider +class GpApiConnector extends RestGateway implements IPaymentGateway, ISecure3dProvider, IPayFacProvider { const GP_API_VERSION = '2021-03-22'; const IDEMPOTENCY_HEADER = 'x-gp-idempotency'; @@ -137,6 +141,28 @@ public function processReport(ReportBuilder $builder) return GpApiMapping::mapReportResponse($response, $builder->reportType); } + /** + * @param PayFacBuilder $builder + * @return User + * @throws ApiException + * @throws \GlobalPayments\Api\Entities\Exceptions\UnsupportedTransactionException + */ + public function processBoardingUser(PayFacBuilder $builder) : User + { + if (empty($this->accessToken)) { + $this->signIn(); + } + $response = $this->executeProcess($builder); + + return GpApiMapping::mapMerchantsEndpointResponse($response); + } + + public function processPayFac(PayFacBuilder $builder) + { + throw new UnsupportedTransactionException(sprintf('Method %s not supported by %s', __METHOD__, $this->gpApiConfig->gatewayProvider)); + } + + private function executeProcess($builder) { $processFactory = new RequestBuilderFactory(); diff --git a/src/Gateways/IPayFacProvider.php b/src/Gateways/IPayFacProvider.php index e46ab52c..f41fbaff 100644 --- a/src/Gateways/IPayFacProvider.php +++ b/src/Gateways/IPayFacProvider.php @@ -5,13 +5,19 @@ use GlobalPayments\Api\Builders\PayFacBuilder; use GlobalPayments\Api\Entities\Transaction; use GlobalPayments\Api\Entities\Exceptions\ApiException; +use GlobalPayments\Api\Entities\User; interface IPayFacProvider { - /** * @throws ApiException * @return Transaction */ public function processPayFac(PayFacBuilder $builder); + + /** + * @param PayFacBuilder $builder + * @return User + */ + public function processBoardingUser(PayFacBuilder $builder) : User; } diff --git a/src/Gateways/PorticoConnector.php b/src/Gateways/PorticoConnector.php index c57c3ba9..f32a05ad 100644 --- a/src/Gateways/PorticoConnector.php +++ b/src/Gateways/PorticoConnector.php @@ -16,7 +16,9 @@ use GlobalPayments\Api\Entities\Enums\AliasAction; use GlobalPayments\Api\Entities\Enums\CheckType; use GlobalPayments\Api\Entities\Enums\EntryMethod; +use GlobalPayments\Api\Entities\Enums\MobilePaymentMethodType; use GlobalPayments\Api\Entities\Enums\PaymentMethodType; +use GlobalPayments\Api\Entities\Enums\Secure3dPaymentDataSource; use GlobalPayments\Api\Entities\Enums\TaxType; use GlobalPayments\Api\Entities\Enums\TransactionModifier; use GlobalPayments\Api\Entities\Enums\TransactionType; @@ -141,12 +143,14 @@ public function processAuthorization(AuthorizationBuilder $builder) $transaction = $xml->createElement($this->mapRequestType($builder)); $block1 = $xml->createElement('Block1'); - if ($builder->paymentMethod->paymentMethodType !== PaymentMethodType::GIFT + if ( + $builder->paymentMethod->paymentMethodType !== PaymentMethodType::GIFT && $builder->paymentMethod->paymentMethodType !== PaymentMethodType::ACH && ($builder->transactionType === TransactionType::AUTH || $builder->transactionType === TransactionType::SALE) ) { - if ($builder->paymentMethod->paymentMethodType !== PaymentMethodType::RECURRING + if ( + $builder->paymentMethod->paymentMethodType !== PaymentMethodType::RECURRING || $builder->paymentMethod->paymentType !== 'ACH' ) { $block1->appendChild( @@ -157,7 +161,8 @@ public function processAuthorization(AuthorizationBuilder $builder) ); } - if ($builder->transactionModifier === TransactionModifier::NONE + if ( + $builder->transactionModifier === TransactionModifier::NONE && $builder->paymentMethod->paymentMethodType !== PaymentMethodType::EBT && $builder->paymentMethod->paymentMethodType !== PaymentMethodType::RECURRING ) { @@ -219,7 +224,8 @@ public function processAuthorization(AuthorizationBuilder $builder) && $builder->paymentMethod->paymentType === 'ACH'); $propertyName = $isCheck ? 'checkHolderName' : 'cardHolderName'; - if ($isCheck + if ( + $isCheck || $builder->billingAddress !== null || isset($builder->paymentMethod->{$propertyName}) ) { @@ -255,8 +261,7 @@ public function processAuthorization(AuthorizationBuilder $builder) $hasToken, $tokenValue ) - ); - + ); } elseif ($builder->paymentMethod instanceof ITrackData) { $trackData = $this->hydrateTrackData( $xml, @@ -428,13 +433,15 @@ public function processAuthorization(AuthorizationBuilder $builder) $block1->appendChild($data); } - if ($builder->paymentMethod instanceof IPinProtected + if ( + $builder->paymentMethod instanceof IPinProtected && $builder->transactionType !== TransactionType::REVERSAL ) { $block1->appendChild($xml->createElement('PinBlock', $builder->paymentMethod->pinBlock)); } - if ($builder->paymentMethod instanceof IEncryptable + if ( + $builder->paymentMethod instanceof IEncryptable && isset($builder->paymentMethod->encryptionData) && null !== $builder->paymentMethod->encryptionData ) { @@ -459,10 +466,14 @@ public function processAuthorization(AuthorizationBuilder $builder) if ($cardData->childNodes->length > 0 && $builder->aliasAction !== AliasAction::CREATE) { $block1->appendChild($cardData); } - + //secure 3d - if ($builder->paymentMethod instanceof CreditCardData && !empty($builder->paymentMethod->threeDSecure)) { - $this->hydrateThreeDSecureData($xml, $builder, $block1); + if ($builder->paymentMethod instanceof CreditCardData) { + if (!empty($builder->paymentMethod->threeDSecure)) { + $this->hydrateThreeDSecureData($xml, $builder, $block1); + } else { + $this->hydrateWalletData($xml, $builder, $block1, $cardData); + } } if ($builder->paymentMethod instanceof IBalanceable && $builder->balanceInquiryType !== null) { @@ -473,7 +484,8 @@ public function processAuthorization(AuthorizationBuilder $builder) $block1->appendChild($xml->createElement('CPCReq', 'Y')); } - if ($builder->customerId !== null + if ( + $builder->customerId !== null || $builder->description !== null || $builder->invoiceNumber !== null ) { @@ -497,7 +509,7 @@ public function processAuthorization(AuthorizationBuilder $builder) $direct->appendChild($xml->createElement('DirectMktShipDay', $builder->ecommerceInfo->shipDay)); } $block1->appendChild($direct); - } + } } if ($builder->dynamicDescriptor !== null) { @@ -549,7 +561,7 @@ public function processAuthorization(AuthorizationBuilder $builder) } $transaction->appendChild($block1); - + $response = $this->doTransaction($this->buildEnvelope($xml, $transaction, $builder->clientTransactionId)); return $this->mapResponse($response, $builder, $this->buildEnvelope($xml, $transaction)); } @@ -575,7 +587,8 @@ public function manageTransaction(ManagementBuilder $builder) if ($builder->transactionType !== TransactionType::BATCH_CLOSE) { $root = null; - if ($builder->transactionType === TransactionType::REVERSAL + if ( + $builder->transactionType === TransactionType::REVERSAL || $builder->transactionType === TransactionType::REFUND || $builder->paymentMethod->paymentMethodType === PaymentMethodType::GIFT || $builder->paymentMethod->paymentMethodType === PaymentMethodType::ACH @@ -600,7 +613,8 @@ public function manageTransaction(ManagementBuilder $builder) } // Level II Data - if ($builder->transactionType === TransactionType::EDIT + if ( + $builder->transactionType === TransactionType::EDIT && $builder->transactionModifier === TransactionModifier::LEVEL_II ) { $cpc = $xml->createElement('CPCData'); @@ -656,7 +670,7 @@ public function manageTransaction(ManagementBuilder $builder) if ($builder->cardType == 'Visa') { $visaCorporateDataNode = $xml->createElement('Visa'); - + if (!empty($builder->commercialData->summaryCommodityCode)) { $visaCorporateDataNode->appendChild($xml->createElement('SummaryCommodityCode', $builder->commercialData->summaryCommodityCode)); } @@ -766,7 +780,7 @@ public function manageTransaction(ManagementBuilder $builder) if (!empty($lineItemsNode)) { $visaCorporateDataNode->appendChild($lineItemsNode); } - + $commercialDataNode->appendChild($visaCorporateDataNode); $root->appendChild($commercialDataNode); } elseif ($builder->cardType == 'MC') { @@ -826,7 +840,8 @@ public function manageTransaction(ManagementBuilder $builder) } // Token Management - if ($builder->transactionType === TransactionType::TOKEN_UPDATE + if ( + $builder->transactionType === TransactionType::TOKEN_UPDATE || $builder->transactionType === TransactionType::TOKEN_DELETE ) { $token = $builder->paymentMethod; @@ -860,7 +875,8 @@ public function manageTransaction(ManagementBuilder $builder) $root->appendChild($addons); } - if ($builder->transactionType === TransactionType::REVERSAL + if ( + $builder->transactionType === TransactionType::REVERSAL || $builder->transactionType === TransactionType::REFUND || $builder->paymentMethod->paymentMethodType === PaymentMethodType::GIFT || $builder->paymentMethod->paymentMethodType === PaymentMethodType::ACH @@ -1244,7 +1260,7 @@ protected function mapResponse($rawResponse, BaseBuilder $builder, $request) : $gatewayRspText; if (isset($item) && (isset($item->AuthAmt) || isset($item->SplitTenderCardAmt))) { - $result->authorizedAmount = + $result->authorizedAmount = isset($item->SplitTenderCardAmt) ? (string)$item->SplitTenderCardAmt : (string)$item->AuthAmt; @@ -1359,9 +1375,9 @@ protected function mapResponse($rawResponse, BaseBuilder $builder, $request) if (isset($item) && isset($item->CardBrandTxnId)) { $result->cardBrandTransactionId = (string)$item->CardBrandTxnId; } - - if(!empty($root->PaymentFacilitatorTxnId) || !empty($root->PaymentFacilitatorTxnNbr)){ - $result->payFacData = new PayFacResponseData(); + + if (!empty($root->PaymentFacilitatorTxnId) || !empty($root->PaymentFacilitatorTxnNbr)) { + $result->payFacData = new PayFacResponseData(); $result->payFacData->transactionId = !empty($root->PaymentFacilitatorTxnId) ? (string) $root->PaymentFacilitatorTxnId : ''; $result->payFacData->transactionNumber = !empty($root->PaymentFacilitatorTxnNbr) ? (string) $root->PaymentFacilitatorTxnNbr : ''; } @@ -1375,8 +1391,9 @@ protected function mapReportResponse($rawResponse, ReportBuilder $builder) $doc = $root->Transaction->{$this->mapReportType($builder)}; if ((($builder->reportType === ReportType::ACTIVITY) - || ($builder->reportType === ReportType::FIND_TRANSACTIONS)) - && isset($doc->Transactions)) { + || ($builder->reportType === ReportType::FIND_TRANSACTIONS)) + && isset($doc->Transactions) + ) { $response = []; foreach ($doc->Transactions as $item) { $response[] = $this->hydrateTransactionSummary($item); @@ -1385,7 +1402,7 @@ protected function mapReportResponse($rawResponse, ReportBuilder $builder) } if ($builder->reportType === ReportType::TRANSACTION_DETAIL) { - if(isset($doc->Data)) + if (isset($doc->Data)) return $this->hydrateTransactionSummary($doc->Data); } @@ -1447,9 +1464,7 @@ protected function hydrateTransactionSummary($item) if (isset($item->CardHolderData->CardHolderZip)) { $summary->cardHolderZip = (string)$item->CardHolderData->CardHolderZip; } - } - else - { + } else { if (isset($item->CardHolderFirstName)) { $summary->cardHolderFirstName = (string)$item->CardHolderFirstName; } @@ -1847,9 +1862,9 @@ protected function mapRequestType(BaseBuilder $builder) throw new UnsupportedTransactionException('Transaction not supported for this payment method.'); case TransactionType::EDIT: if ( - $builder->transactionModifier === TransactionModifier::LEVEL_II || - $builder->transactionModifier === TransactionModifier::LEVEL_III - ) { + $builder->transactionModifier === TransactionModifier::LEVEL_II + || $builder->transactionModifier === TransactionModifier::LEVEL_III + ) { return 'CreditCPCEdit'; } else { return 'CreditTxnEdit'; @@ -2040,7 +2055,8 @@ protected function hydrateHolder(DOMDocument $xml, BaseBuilder $builder, $isChec $holder->appendChild($xml->createElement('DLState', $builder->paymentMethod->driversLicenseState)); } - if ($builder->paymentMethod->ssnLast4 !== null + if ( + $builder->paymentMethod->ssnLast4 !== null || $builder->paymentMethod->birthYear !== null ) { $identity = $xml->createElement('IdentityInfo'); @@ -2237,19 +2253,32 @@ public function supportsHostedPayments() { return $this->supportsHostedPayments; } - - protected function hydrateThreeDSecureData(DOMDocument $xml, BaseBuilder $builder, $block1){ + + /** + * To hydrate ThreeDSecure Data + * + * @param DOMDocument $xml XML instance + * @param BaseBuilder $builder Request builder + * @param DOMDocument $block1 + * + * @return DOMElement + */ + protected function hydrateThreeDSecureData(DOMDocument $xml, BaseBuilder $builder, $block1) + { //3dseccure - if (!empty($builder->paymentMethod->threeDSecure->eci)) { + if ( + !empty($builder->paymentMethod->threeDSecure->eci) + && !$this->isAppleOrGooglePay($builder->paymentMethod->threeDSecure->paymentDataSource) + ) { $secure = $xml->createElement('Secure3D'); - + $secure->appendChild( $xml->createElement( 'Version', $this->getSecure3DVersion($builder->paymentMethod->threeDSecure->getVersion()) - ) - ); - + ) + ); + if (!empty($builder->paymentMethod->threeDSecure->cavv)) { $secure->appendChild($xml->createElement('AuthenticationValue', $builder->paymentMethod->threeDSecure->cavv)); } @@ -2258,41 +2287,99 @@ protected function hydrateThreeDSecureData(DOMDocument $xml, BaseBuilder $builde } if (!empty($builder->paymentMethod->threeDSecure->xid)) { $secure->appendChild($xml->createElement('DirectoryServerTxnId', $builder->paymentMethod->threeDSecure->xid)); - } - + } + $block1->appendChild($secure); } - + if ($this->isAppleOrGooglePay($builder->paymentMethod->threeDSecure->paymentDataSource)) { + $secure = $xml->createElement('WalletData'); + + if (!empty($builder->paymentMethod->threeDSecure->cavv)) { + $secure->appendChild($xml->createElement('PaymentSource', $builder->paymentMethod->threeDSecure->paymentDataSource)); + } + if (!empty($builder->paymentMethod->threeDSecure->xid)) { + $secure->appendChild($xml->createElement('Cryptogram', $builder->paymentMethod->threeDSecure->cavv)); + } + if (!empty($builder->paymentMethod->threeDSecure->eci)) { + $secure->appendChild($xml->createElement('ECI', $builder->paymentMethod->threeDSecure->eci)); + } + + $block1->appendChild($secure); + } + } + + /** + * To hydrate Wallet Data + * + * @param DOMDocument $xml XML instance + * @param BaseBuilder $builder Request builder + * @param DOMDocument $block1 + * @param DOMDocument $cardData + * @return DOMElement + */ + private function hydrateWalletData(DOMDocument $xml, BaseBuilder $builder, $block1, $cardData) + { //wallet data - if (!empty($builder->paymentMethod->threeDSecure->paymentDataSource)) { + if ( + $builder->paymentMethod->mobileType == MobilePaymentMethodType::APPLEPAY + || $builder->paymentMethod->mobileType == MobilePaymentMethodType::GOOGLEPAY + && !empty($builder->paymentMethod->threeDSecure->paymentDataSource) + && $this->isAppleOrGooglePay($builder->paymentMethod->threeDSecure->paymentDataSource) + ) { $walletData = $xml->createElement('WalletData'); - - $walletData->appendChild( - $xml->createElement( - 'PaymentSource', - $builder->paymentMethod->threeDSecure->paymentDataSource - ) - ); - + if (!empty($builder->paymentMethod->threeDSecure->cavv)) { $walletData->appendChild($xml->createElement('Cryptogram', $builder->paymentMethod->threeDSecure->cavv)); } if (!empty($builder->paymentMethod->threeDSecure->eci)) { $walletData->appendChild($xml->createElement('ECI', $builder->paymentMethod->threeDSecure->eci)); } - if (!empty($builder->paymentMethod->mobileType)) { - $walletData->appendChild($xml->createElement('DigitalPaymentToken', $builder->paymentMethod->token)); + if (!empty($builder->paymentMethod->paymentSource)) { + $walletData->appendChild($xml->createElement('PaymentSource', $builder->paymentMethod->paymentSource)); + } + + if ($builder->paymentMethod->mobileType) { + $digitalToken = $walletData->appendChild($xml->createElement('DigitalPaymentToken')); + $digitalToken->appendChild($xml->createCDATASection($builder->paymentMethod->token)); + $block1->removeChild($cardData); } - + $block1->appendChild($walletData); - } + } + } + + /** + * To check ApplePay or GooglePay + * + * @param string $paymentDataSource + * @return boolean + */ + private function isAppleOrGooglePay($paymentDataSource) + { + if ( + $paymentDataSource == Secure3dPaymentDataSource::APPLEPAY + || $paymentDataSource == Secure3dPaymentDataSource::APPLEPAYAPP + || $paymentDataSource == Secure3dPaymentDataSource::APPLEPAYWEB + || $paymentDataSource == Secure3dPaymentDataSource::GOOGLEPAYAPP + || $paymentDataSource == Secure3dPaymentDataSource::GOOGLEPAYWEB + ) { + return true; + } + return false; } - - private function getSecure3DVersion($version){ - if($version == null){ + + /** + * To get Secure3dVersion + * + * @param string $version + * @return int + */ + private function getSecure3DVersion($version) + { + if ($version == null) { return 1; } - switch ($version){ + switch ($version) { case 'TWO': return 2; case 'ONE': diff --git a/src/Gateways/ProPayConnector.php b/src/Gateways/ProPayConnector.php index 6b1cbd0b..5efef5e1 100644 --- a/src/Gateways/ProPayConnector.php +++ b/src/Gateways/ProPayConnector.php @@ -18,6 +18,7 @@ use GlobalPayments\Api\Entities\PayFac\SingleSignOnData; use GlobalPayments\Api\Entities\PayFac\OwnerDetailsResponseData; use GlobalPayments\Api\Entities\PayFac\DeviceDetails; +use GlobalPayments\Api\Entities\User; class ProPayConnector extends XmlGateway implements IPayFacProvider { @@ -662,4 +663,9 @@ private function hydrateDeviceQuantity($xml, $xmlTrans, DeviceDetails $deviceDet $xmlTrans->appendChild($xml->createElement('TimeZone', $deviceDetails->timezone)); } + + public function processBoardingUser(PayFacBuilder $builder) : User + { + throw new UnsupportedTransactionException(sprintf('Method %s not supported', __METHOD__)); + } } diff --git a/src/Mapping/GpApiMapping.php b/src/Mapping/GpApiMapping.php index e1192aab..2eff5691 100644 --- a/src/Mapping/GpApiMapping.php +++ b/src/Mapping/GpApiMapping.php @@ -2,6 +2,7 @@ namespace GlobalPayments\Api\Mapping; +use GlobalPayments\Api\Entities\Address; use GlobalPayments\Api\Entities\AlternativePaymentResponse; use GlobalPayments\Api\Entities\BatchSummary; use GlobalPayments\Api\Entities\CardIssuerResponse; @@ -12,6 +13,7 @@ use GlobalPayments\Api\Entities\Enums\FraudFilterResult; use GlobalPayments\Api\Entities\Enums\PaymentMethodName; use GlobalPayments\Api\Entities\Enums\PaymentMethodType; +use GlobalPayments\Api\Entities\Enums\PhoneNumberType; use GlobalPayments\Api\Entities\Enums\ReportType; use GlobalPayments\Api\Entities\Enums\Secure3dStatus; use GlobalPayments\Api\Entities\Enums\Secure3dVersion; @@ -21,24 +23,38 @@ use GlobalPayments\Api\Entities\FraudRule; use GlobalPayments\Api\Entities\GpApi\DTO\PaymentMethod; use GlobalPayments\Api\Entities\GpApi\PagedResult; -use GlobalPayments\Api\Entities\PayLinkData; use GlobalPayments\Api\Entities\PayLinkResponse; +use GlobalPayments\Api\Entities\PaymentMethodList; +use GlobalPayments\Api\Entities\Person; +use GlobalPayments\Api\Entities\PersonList; +use GlobalPayments\Api\Entities\PhoneNumber; use GlobalPayments\Api\Entities\Reporting\ActionSummary; use GlobalPayments\Api\Entities\Reporting\DepositSummary; use GlobalPayments\Api\Entities\Reporting\DisputeSummary; +use GlobalPayments\Api\Entities\Reporting\MerchantSummary; use GlobalPayments\Api\Entities\Reporting\PayLinkSummary; use GlobalPayments\Api\Entities\Reporting\StoredPaymentMethodSummary; use GlobalPayments\Api\Entities\Reporting\TransactionSummary; use GlobalPayments\Api\Entities\ThreeDSecure; use GlobalPayments\Api\Entities\Transaction; +use GlobalPayments\Api\Entities\User; +use GlobalPayments\Api\Entities\UserLinks; +use GlobalPayments\Api\PaymentMethods\CreditCardData; +use GlobalPayments\Api\PaymentMethods\ECheck; use GlobalPayments\Api\Utils\StringUtils; use GlobalPayments\Api\Entities\MessageExtension; +use GlobalPayments\Api\Entities\Exceptions\UnsupportedTransactionException; class GpApiMapping { const DCC_RESPONSE = 'RATE_LOOKUP'; const LINK_CREATE = "LINK_CREATE"; const LINK_EDIT = "LINK_EDIT"; + const MERCHANT_CREATE = 'MERCHANT_CREATE'; + const MERCHANT_LIST = 'MERCHANT_LIST'; + const MERCHANT_SINGLE = 'MERCHANT_SINGLE'; + const MERCHANT_EDIT = 'MERCHANT_EDIT'; + const MERCHANT_EDIT_INITIATED = 'MERCHANT_EDIT_INITIATED'; /** * Map a response to a Transaction object for further chaining * @@ -285,6 +301,12 @@ public static function mapReportResponse($response, $reportType) array_push($report->result, self::mapPayLinkSummary($link)); } break; + case ReportType::FIND_MERCHANTS_PAGED: + $report = self::setPagingInfo($response); + foreach ($response->merchants as $merchant) { + array_push($report->result, self::mapMerchantSummary($merchant)); + } + return $report; default: throw new ApiException("Report type not supported!"); } @@ -627,8 +649,7 @@ public static function mapResponseSecure3D($response) $response->three_ds->liability_shift : null; $threeDSecure->authenticationType = !empty($response->three_ds->authentication_request_type) ? $response->three_ds->authentication_request_type : null; - $threeDSecure->acsInfoIndicator = !empty($response->three_ds->acs_decoupled_response_indicator) ? - $response->three_ds->acs_decoupled_response_indicator : null; + $threeDSecure->decoupledResponseIndicator = $response->three_ds->acs_decoupled_response_indicator ?? null; $threeDSecure->whitelistStatus = !empty($response->three_ds->whitelist_status) ? $response->three_ds->whitelist_status : null; if (!empty($response->three_ds->message_extension)) { @@ -810,7 +831,152 @@ private static function createTransactionSummary($response) return $transaction; } - private static function validateStringDate($date) + private static function mapMerchantSummary($merchant): MerchantSummary + { + $merchantInfo = new MerchantSummary(); + $merchantInfo->id = $merchant->id; + $merchantInfo->name = $merchant->name; + $merchantInfo->status = $merchant->status ?? ''; + if (!empty($merchant->links)) { + foreach ($merchant->links as $link) { + $userLink = new UserLinks(); + $userLink->rel = $link->rel ?? null; + $userLink->href = $link->href ?? null; + $merchantInfo->links[] = $userLink; + } + } + + return $merchantInfo; + } + + public static function mapMerchantsEndpointResponse($response): User + { + if (empty($response->action->type)) { + throw new UnsupportedTransactionException(sprintf("Empty action type response!")); + } + + switch ($response->action->type) { + case self::MERCHANT_CREATE: + case self::MERCHANT_EDIT: + case self::MERCHANT_EDIT_INITIATED: + case self::MERCHANT_SINGLE: + $user = new User(); + $user->userId = $response->id; + $user->name = $response->name ?? null; + $user->userStatus = $response->status; + $user->userType = $response->type; + $user->timeCreate = !empty($response->time_created) ? new \DateTime($response->time_created) : null; + $user->timeLastUpdated = !empty($response->time_last_updated) ? + new \DateTime($response->time_last_updated) : null; + $user->responseCode = $response->action->result_code ?? null; + $user->statusDescription = $response->status_description ?? null; + $user->email = $response->email ?? null; + if (!empty($response->address)) { + foreach ($response->address as $address) { + $user->addresses[] = self::mapAddressObject($address); + } + } + if ( + !empty($response->contact_phone->country_code) && + !empty($response->contact_phone->subscriber_number) + ) { + $user->contactPhone = new PhoneNumber( + $response->contact_phone->country_code, + $response->contact_phone->subscriber_number, + PhoneNumberType::WORK + ); + } + if (!empty($response->persons)) { + self::mapMerchantPersonList($response->persons, $user); + } + if (!empty($response->payment_methods)) { + self::mapMerchantPaymentMethods($response->payment_methods,$user); + } + return $user; + default: + throw new UnsupportedTransactionException(sprintf("Unknown action type %s", $response->action->type)); + } + } + + /** + * @param $paymentMethods + * @param User $user + */ + private static function mapMerchantPaymentMethods($paymentMethods, &$user) + { + $pmList = new PaymentMethodList(); + foreach ($paymentMethods as $paymentMethod) { + if (isset($paymentMethod->bank_transfer)) { + $bankTransfer = $paymentMethod->bank_transfer; + $pm = new ECheck(); + $pm->checkType = $bankTransfer->account_holder_type ?? null; + $pm->accountNumber = $bankTransfer->account_number ?? null; + $pm->accountType = $bankTransfer->account_type ?? null; + if (isset($bankTransfer->bank)) { + $pm->routingNumber = $bankTransfer->bank->code ?? null; + $pm->bankName = $bankTransfer->bank->name ?? null; + } + $pm->checkHolderName = $paymentMethod->name ?? null; + } + if (isset($paymentMethod->card)) { + $card = $paymentMethod->card; + $pm = new CreditCardData(); + $pm->cardHolderName = $card->name ?? null; + $pm->number = $card->number ?? null; + $pm->expYear = $card->expiry_year ?? null; + } + $functions = $paymentMethod->functions ?? null; + $pmList->append(['functions' => $functions, 'payment_method' => $pm]); + } + $user->paymentMethodList = $pmList; + } + + private static function mapAddressObject() + { + $userAddress = new Address(); + $userAddress->streetAddress1 = $address->line_1 ?? null; + $userAddress->streetAddress2 = $address->line_2 ?? null; + $userAddress->streetAddress3 = $address->line_3 ?? null; + $userAddress->city = $address->city ?? null; + $userAddress->state = $address->state ?? null; + $userAddress->postalCode = $address->postal_code ?? null; + $userAddress->countryCode = $address->country ?? null; + $userAddress->type = !empty($address->functions) ? $address->functions[0] : null; + + return $userAddress; + } + + private static function mapMerchantPersonList($persons, &$user) + { + $personList = new PersonList(); + foreach ($persons as $person) { + $newPerson = new Person(); + $newPerson->functions = $person->functions; + $newPerson->firstName = $person->first_name; + $newPerson->middleName = $person->middle_name; + $newPerson->lastName = $person->last_name; + $newPerson->email = $person->email; + if (!empty($person->address)) { + $newPerson->address = new Address(); + $newPerson->address->streetAddress1 = $person->address->line_1 ?? null; + $newPerson->address->streetAddress2 = $person->address->line_2 ?? null; + $newPerson->address->streetAddress3 = $person->address->line_3 ?? null; + $newPerson->address->city = $person->address->city ?? null; + $newPerson->address->state = $person->address->state ?? null; + $newPerson->address->postalCode = $person->address->postal_code ?? null; + $newPerson->address->country = $person->address->country ?? null; + } + + $newPerson->workPhone = !empty($person->work_phone) ? + new PhoneNumber('', $person->work_phone->subscriber_number, PhoneNumberType::WORK) : null; + $newPerson->homePhone = !empty($person->contact_phone) ? + new PhoneNumber('', $person->contact_phone->subscriber_number, PhoneNumberType::HOME) : null; + $personList->append($newPerson); + } + $user->personList = $personList; + } + + private static function validateStringDate($date): string { try { new \DateTime($date); diff --git a/src/ServiceConfigs/Gateways/GpApiConfig.php b/src/ServiceConfigs/Gateways/GpApiConfig.php index 98dd42a6..749ff24f 100644 --- a/src/ServiceConfigs/Gateways/GpApiConfig.php +++ b/src/ServiceConfigs/Gateways/GpApiConfig.php @@ -96,6 +96,7 @@ public function configureContainer(ConfiguredServices $services) $services->gatewayConnector = $gateway; $services->reportingService = $gateway; + $services->setPayFacProvider($gateway); $services->setSecure3dProvider(Secure3dVersion::ONE, $gateway); $services->setSecure3dProvider(Secure3dVersion::TWO, $gateway); } diff --git a/src/Services/PayFacService.php b/src/Services/PayFacService.php index 8933a11d..e60d8b9b 100644 --- a/src/Services/PayFacService.php +++ b/src/Services/PayFacService.php @@ -3,7 +3,10 @@ namespace GlobalPayments\Api\Services; use GlobalPayments\Api\Builders\PayFacBuilder; +use GlobalPayments\Api\Entities\Enums\TransactionModifier; use GlobalPayments\Api\Entities\Enums\TransactionType; +use GlobalPayments\Api\Entities\Enums\UserType; +use GlobalPayments\Api\Entities\PayFac\UserReference; class PayFacService { @@ -65,7 +68,7 @@ public static function disownAccount() } /* * This method can be used to send an image file to ProPay, and is specifically designed to support the documents - * you use to dispute a credit card chargeback. This version of document upload has you “tag” the + * you use to dispute a credit card chargeback. This version of document upload has you "tag" the * document to a specific transaction that has been charged-back * */ @@ -76,7 +79,7 @@ public static function uploadDocumentChargeback() /* * This method can be used to send an image file to ProPay. The ProPay Risk team may request that you perform this * action to underwrite an account that was denied via automated boarding, to increase the processing limit on - * accounts, or to provide data when we’ve had to put an accounts ability to process on hold. + * accounts, or to provide data when we've had to put an accounts ability to process on hold. * */ public static function UploadDocument() @@ -143,4 +146,21 @@ public static function getAccountBalance() { return new PayFacBuilder(TransactionType::GET_ACCOUNT_BALANCE); } + + public static function createMerchant() + { + return (new PayFacBuilder(TransactionType::CREATE)) + ->withModifier(TransactionModifier::MERCHANT); + } + + public static function getMerchantInfo($merchantId) + { + $userReference = new UserReference(); + $userReference->userId = $merchantId; + $userReference->userType = UserType::MERCHANT; + + return (new PayFacBuilder(TransactionType::FETCH)) + ->withModifier(TransactionModifier::MERCHANT) + ->withUserReference($userReference); + } } diff --git a/src/Services/ReportingService.php b/src/Services/ReportingService.php index 36c4370e..b8a7b79c 100644 --- a/src/Services/ReportingService.php +++ b/src/Services/ReportingService.php @@ -3,8 +3,11 @@ namespace GlobalPayments\Api\Services; use GlobalPayments\Api\Builders\BankPaymentBuilder; +use GlobalPayments\Api\Builders\PayFacBuilder; use GlobalPayments\Api\Builders\TransactionReportBuilder; +use GlobalPayments\Api\Builders\UserReportBuilder; use GlobalPayments\Api\Entities\Enums\ReportType; +use GlobalPayments\Api\Entities\Enums\TransactionModifier; use GlobalPayments\Api\Entities\Enums\TransactionType; class ReportingService @@ -137,4 +140,11 @@ public static function findBankPaymentTransactions($page, $pageSize) return (new TransactionReportBuilder(ReportType::FIND_BANK_PAYMENT)) ->withPaging($page, $pageSize); } + + public static function findMerchants($page, $pageSize) + { + return (new UserReportBuilder(ReportType::FIND_MERCHANTS_PAGED)) + ->withModifier(TransactionModifier::MERCHANT) + ->withPaging($page, $pageSize); + } } \ No newline at end of file diff --git a/src/ServicesContainer.php b/src/ServicesContainer.php index bb9f3778..b5a55ce7 100644 --- a/src/ServicesContainer.php +++ b/src/ServicesContainer.php @@ -203,4 +203,11 @@ public function getOpenBanking($configName) throw new ApiException("The specified configuration has not been added for open banking."); } + + public static function removeConfiguration($configName = 'default') + { + if (array_key_exists($configName, static::$configurations)) { + unset(self::$configurations[$configName]); + } + } } diff --git a/test/Data/BaseGpApiTestConfig.php b/test/Data/BaseGpApiTestConfig.php index a77f52b7..953cabc1 100644 --- a/test/Data/BaseGpApiTestConfig.php +++ b/test/Data/BaseGpApiTestConfig.php @@ -5,14 +5,17 @@ use GlobalPayments\Api\Entities\CustomWebProxy; use GlobalPayments\Api\Entities\Enums\Environment; use GlobalPayments\Api\ServiceConfigs\Gateways\GpApiConfig; +use GlobalPayments\Api\ServicesContainer; use GlobalPayments\Api\Utils\Logging\Logger; use GlobalPayments\Api\Utils\Logging\SampleRequestLogger; class BaseGpApiTestConfig { + const APP_ID = '4gPqnGBkppGYvoE5UX9EWQlotTxGUDbs'; + const APP_KEY = 'FQyJA5VuEQfcji2M'; - public static $appId = '4gPqnGBkppGYvoE5UX9EWQlotTxGUDbs'; - public static $appKey = 'FQyJA5VuEQfcji2M'; + public static $appId = self::APP_ID; + public static $appKey = self::APP_KEY; private static $logEnabled = true; private static $dynamicHeaderEnabled = false; @@ -54,4 +57,10 @@ public static function gpApiSetupConfig($channel): GpApiConfig return $config; } + static function resetGpApiConfig() + { + ServicesContainer::removeConfiguration(); + self::$appId = self::APP_ID; + self::$appKey = self::APP_KEY; + } } \ No newline at end of file diff --git a/test/Integration/Gateways/GpApiConnector/AccessTokenTest.php b/test/Integration/Gateways/GpApiConnector/AccessTokenTest.php index b90b1115..1ff2d0ca 100644 --- a/test/Integration/Gateways/GpApiConnector/AccessTokenTest.php +++ b/test/Integration/Gateways/GpApiConnector/AccessTokenTest.php @@ -25,6 +25,11 @@ public function setUp(): void $this->setUpConfig(); } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function testGenerateAccessToken() { $accessTokenInfo = GpApiService::generateTransactionKey($this->config); diff --git a/test/Integration/Gateways/GpApiConnector/Certifications/CapabilitiesCardPresentTest.php b/test/Integration/Gateways/GpApiConnector/Certifications/CapabilitiesCardPresentTest.php index a6af754e..c5bbed71 100644 --- a/test/Integration/Gateways/GpApiConnector/Certifications/CapabilitiesCardPresentTest.php +++ b/test/Integration/Gateways/GpApiConnector/Certifications/CapabilitiesCardPresentTest.php @@ -33,6 +33,11 @@ public function setUpConfig() return BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardPresent); } + public static function tearDownAfterClass() + { + ServicesContainer::removeConfiguration(); + } + public function testDebitSaleWithChipCondition() { $debitCard = new DebitTrackData(); diff --git a/test/Integration/Gateways/GpApiConnector/Certifications/GpApiSdkCertificationTest.php b/test/Integration/Gateways/GpApiConnector/Certifications/GpApiSdkCertificationTest.php index d68dc2fe..bf9c4362 100644 --- a/test/Integration/Gateways/GpApiConnector/Certifications/GpApiSdkCertificationTest.php +++ b/test/Integration/Gateways/GpApiConnector/Certifications/GpApiSdkCertificationTest.php @@ -34,6 +34,11 @@ public function setUpConfig() return BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardNotPresent); } + public static function tearDownAfterClass() + { + ServicesContainer::removeConfiguration(); + } + public function testCreditCard_Visa_Success() { $this->card->number = "4263970000005262"; diff --git a/test/Integration/Gateways/GpApiConnector/CreditCardNotPresentTest.php b/test/Integration/Gateways/GpApiConnector/CreditCardNotPresentTest.php index e09d5c5e..dc9237c9 100644 --- a/test/Integration/Gateways/GpApiConnector/CreditCardNotPresentTest.php +++ b/test/Integration/Gateways/GpApiConnector/CreditCardNotPresentTest.php @@ -56,6 +56,11 @@ public function setup(): void $this->idempotencyKey = GenerationUtils::getGuid(); } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function testCreditSale() { $address = new Address(); diff --git a/test/Integration/Gateways/GpApiConnector/CreditCardPresentTest.php b/test/Integration/Gateways/GpApiConnector/CreditCardPresentTest.php index 722cab56..8a907ae6 100644 --- a/test/Integration/Gateways/GpApiConnector/CreditCardPresentTest.php +++ b/test/Integration/Gateways/GpApiConnector/CreditCardPresentTest.php @@ -35,6 +35,11 @@ public function setup(): void ServicesContainer::configureService($this->setUpConfig()); } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function setUpConfig() { return BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardPresent); diff --git a/test/Integration/Gateways/GpApiConnector/DccCardNotPresentTest.php b/test/Integration/Gateways/GpApiConnector/DccCardNotPresentTest.php index df005290..c4d82e0d 100644 --- a/test/Integration/Gateways/GpApiConnector/DccCardNotPresentTest.php +++ b/test/Integration/Gateways/GpApiConnector/DccCardNotPresentTest.php @@ -29,6 +29,11 @@ public function setup(): void $this->card->cardHolderName = "James Mason"; } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function setUpConfig() { $config = BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardNotPresent); diff --git a/test/Integration/Gateways/GpApiConnector/DccCardPresentTest.php b/test/Integration/Gateways/GpApiConnector/DccCardPresentTest.php index 8af25aec..77b43ef7 100644 --- a/test/Integration/Gateways/GpApiConnector/DccCardPresentTest.php +++ b/test/Integration/Gateways/GpApiConnector/DccCardPresentTest.php @@ -45,6 +45,11 @@ public function setup(): void $this->card->cardPresent = true; } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function setUpConfig() { $config = BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardPresent); diff --git a/test/Integration/Gateways/GpApiConnector/DebitCardTest.php b/test/Integration/Gateways/GpApiConnector/DebitCardTest.php index cf714375..ddea524c 100644 --- a/test/Integration/Gateways/GpApiConnector/DebitCardTest.php +++ b/test/Integration/Gateways/GpApiConnector/DebitCardTest.php @@ -19,6 +19,11 @@ public function setup(): void ServicesContainer::configureService($this->setUpConfig()); } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function testDebitSaleSwipe() { $debitCard = new DebitTrackData(); diff --git a/test/Integration/Gateways/GpApiConnector/EbtCardTest.php b/test/Integration/Gateways/GpApiConnector/EbtCardTest.php index 9c5fa483..9665e01f 100644 --- a/test/Integration/Gateways/GpApiConnector/EbtCardTest.php +++ b/test/Integration/Gateways/GpApiConnector/EbtCardTest.php @@ -25,6 +25,11 @@ public function setup(): void $this->track = TestCards::asEBTTrack(TestCards::visaSwipe(), '32539F50C245A6A93D123412324000AA'); } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function setUpConfig() { return BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardPresent); diff --git a/test/Integration/Gateways/GpApiConnector/FraudManagementTest.php b/test/Integration/Gateways/GpApiConnector/FraudManagementTest.php index aa3e1c1b..ffb6ea7d 100644 --- a/test/Integration/Gateways/GpApiConnector/FraudManagementTest.php +++ b/test/Integration/Gateways/GpApiConnector/FraudManagementTest.php @@ -22,6 +22,7 @@ use GlobalPayments\Api\ServiceConfigs\Gateways\GpApiConfig; use GlobalPayments\Api\Services\ReportingService; use GlobalPayments\Api\ServicesContainer; +use GlobalPayments\Api\Tests\Data\BaseGpApiTestConfig; use GlobalPayments\Api\Utils\GenerationUtils; use GlobalPayments\Api\Utils\Logging\Logger; use GlobalPayments\Api\Utils\Logging\SampleRequestLogger; @@ -54,6 +55,11 @@ public function setup(): void $this->address->postalCode = "12345"; } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + private function setUpConfig() { $config = new GpApiConfig(); diff --git a/test/Integration/Gateways/GpApiConnector/GpApi3DS1Test.php b/test/Integration/Gateways/GpApiConnector/GpApi3DS1Test.php index 22b48d95..fd3fd407 100644 --- a/test/Integration/Gateways/GpApiConnector/GpApi3DS1Test.php +++ b/test/Integration/Gateways/GpApiConnector/GpApi3DS1Test.php @@ -58,6 +58,11 @@ public function setup(): void $this->card->cardHolderName = "James Mason"; } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function setUpConfig() { return BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardNotPresent); diff --git a/test/Integration/Gateways/GpApiConnector/GpApi3DS2Test.php b/test/Integration/Gateways/GpApiConnector/GpApi3DS2Test.php index 21e25499..f9e3b9f8 100644 --- a/test/Integration/Gateways/GpApiConnector/GpApi3DS2Test.php +++ b/test/Integration/Gateways/GpApiConnector/GpApi3DS2Test.php @@ -102,6 +102,11 @@ public function setup(): void $this->browserData->userAgent = "Mozilla/5.0 (Windows NT 6.1; Win64, x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/70.0.3538.110 Safari/537.36"; } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function setUpConfig() { return BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardNotPresent); diff --git a/test/Integration/Gateways/GpApiConnector/GpApi3DSecureTest.php b/test/Integration/Gateways/GpApiConnector/GpApi3DSecureTest.php index f975aca0..9f3322a3 100644 --- a/test/Integration/Gateways/GpApiConnector/GpApi3DSecureTest.php +++ b/test/Integration/Gateways/GpApiConnector/GpApi3DSecureTest.php @@ -68,6 +68,7 @@ public function setup(): void { $config = $this->setUpConfig(); ServicesContainer::configureService($config); + $this->gatewayProvider = $config->getGatewayProvider(); $this->currency = 'GBP'; $this->amount = '10.01'; @@ -100,6 +101,11 @@ public function setup(): void $this->browserData->userAgent = "Mozilla/5.0 (Windows NT 6.1; Win64, x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/70.0.3538.110 Safari/537.36"; } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function setUpConfig() { return BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardNotPresent); @@ -206,8 +212,7 @@ public function testCardHolderEnrolled_ChallengeRequired_AuthenticationFailed_v1 ->execute(); $this->card->threeDSecure = $secureEcom; $this->assertEquals($status, $secureEcom->status); - $liabilityShift = $status == Secure3dStatus::SUCCESS_ATTEMPT_MADE ? 'YES' : 'NO'; - $this->assertEquals($liabilityShift, $secureEcom->liabilityShift); + $this->assertEquals("NO", $secureEcom->liabilityShift); $response = $this->card->charge($this->amount)->withCurrency($this->currency)->execute(); $this->assertNotNull($response); @@ -822,4 +827,56 @@ private function assertCheckEnrollmentCardNotEnrolledV1(ThreeDSecure $secureEcom $this->assertEquals('NO', $secureEcom->liabilityShift); } + public function testDecoupledAuth() + { + $this->card->number = GpApi3DSTestCards::CARD_AUTH_SUCCESSFUL_V2_1; + + $response = $this->card->tokenize()->execute(); + $tokenId = $response->token; + + $tokenizedCard = new CreditCardData(); + $tokenizedCard->token = $tokenId; + $tokenizedCard->cardHolderName = "James Mason"; + + $secureEcom = Secure3dService::checkEnrollment($tokenizedCard) + ->withCurrency($this->currency) + ->withAmount($this->amount) + ->withDecoupledFlowRequest('https://www.example.com/decoupledNotification') + ->execute(); + + $this->assertNotNull($secureEcom); + $this->assertEquals(Secure3dStatus::ENROLLED, $secureEcom->enrolled); + $this->assertEquals(Secure3dVersion::TWO, $secureEcom->getVersion()); + $this->assertEquals(Secure3dStatus::AVAILABLE, $secureEcom->status); + + $initAuth = Secure3dService::initiateAuthentication($tokenizedCard, $secureEcom) + ->withAmount($this->amount) + ->withCurrency($this->currency) + ->withAuthenticationSource(AuthenticationSource::BROWSER) + ->withMethodUrlCompletion(MethodUrlCompletion::YES) + ->withOrderCreateDate(date('Y-m-d H:i:s')) + ->withAddress($this->shippingAddress, AddressType::SHIPPING) + ->withBrowserData($this->browserData) + ->withDecoupledFlowRequest(true) + ->withDecoupledFlowTimeout('9001') + ->withDecoupledFlowRequest('https://www.example.com/decoupledNotification') + ->execute(); + + $this->assertNotNull($initAuth); + $this->assertEquals(Secure3dStatus::SUCCESS_AUTHENTICATED, $secureEcom->status); + $this->assertEquals('YES', $secureEcom->liabilityShift); + + $secureEcom = Secure3dService::getAuthenticationData() + ->withServerTransactionId($secureEcom->serverTransactionId) + ->execute(); + + $this->assertEquals(Secure3dStatus::SUCCESS_AUTHENTICATED, $secureEcom->status); + $this->assertEquals('YES', $secureEcom->liabilityShift); + + $tokenizedCard->threeDSecure = $secureEcom; + $response = $tokenizedCard->charge($this->amount)->withCurrency($this->currency)->execute(); + $this->assertNotNull($response); + $this->assertEquals('SUCCESS', $response->responseCode); + $this->assertEquals(TransactionStatus::CAPTURED, $response->responseMessage); + } } \ No newline at end of file diff --git a/test/Integration/Gateways/GpApiConnector/GpApiAchTest.php b/test/Integration/Gateways/GpApiConnector/GpApiAchTest.php index c4759508..43a7112b 100644 --- a/test/Integration/Gateways/GpApiConnector/GpApiAchTest.php +++ b/test/Integration/Gateways/GpApiConnector/GpApiAchTest.php @@ -74,6 +74,11 @@ public function setup(): void $this->customer->homePhone = new PhoneNumber('+1', '12345899', PhoneNumberType::HOME); } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function setUpConfig() { return BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardNotPresent); @@ -145,33 +150,32 @@ public function testCheckReauthorize() $startDate = (new \DateTime())->modify('-1 year'); $endDate = (new \DateTime())->modify('-2 days'); $amount = '1.29'; - try { - $response = ReportingService::findTransactionsPaged(1, 10) - ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) - ->where(SearchCriteria::START_DATE, $startDate) - ->andWith(SearchCriteria::END_DATE, $endDate) - ->andWith(SearchCriteria::PAYMENT_METHOD_NAME, PaymentMethodName::BANK_TRANSFER) - ->andWith(SearchCriteria::PAYMENT_TYPE, PaymentType::SALE) - ->andWith(DataServiceCriteria::AMOUNT, $amount) - ->execute(); - } catch (ApiException $e) { - $this->fail('Find transactions by type failed: ' . $e->getMessage()); - } - $this->assertNotNull($response); - $this->assertNotEmpty($response->result); - /** @var \GlobalPayments\Api\Entities\Reporting\TransactionSummary $transactionSummary */ - $transactionSummary = reset($response->result); - $this->assertNotNull($transactionSummary); - $this->assertEquals($amount, $transactionSummary->amount); - $transaction = Transaction::fromId($transactionSummary->transactionId, null, PaymentMethodType::ACH); - - $response = $transaction->reauthorized() - ->withDescription('Resubmitting ' . $transaction->referenceNumber) - ->withBankTransferData($this->eCheck) + $response = ReportingService::findTransactionsPaged(1, 10) + ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) + ->where(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::END_DATE, $endDate) + ->andWith(SearchCriteria::PAYMENT_METHOD_NAME, PaymentMethodName::BANK_TRANSFER) + ->andWith(SearchCriteria::PAYMENT_TYPE, PaymentType::SALE) + ->andWith(DataServiceCriteria::AMOUNT, $amount) ->execute(); $this->assertNotNull($response); - $this->assertEquals('SUCCESS', $response->responseCode); + if (count($response->result) > 0) { + $this->assertNotEmpty($response->result); + /** @var \GlobalPayments\Api\Entities\Reporting\TransactionSummary $transactionSummary */ + $transactionSummary = reset($response->result); + $this->assertNotNull($transactionSummary); + $this->assertEquals($amount, $transactionSummary->amount); + $transaction = Transaction::fromId($transactionSummary->transactionId, null, PaymentMethodType::ACH); + + $response = $transaction->reauthorized() + ->withDescription('Resubmitting ' . $transaction->referenceNumber) + ->withBankTransferData($this->eCheck) + ->execute(); + + $this->assertNotNull($response); + $this->assertEquals('SUCCESS', $response->responseCode); + } } public function testCheckSaleThenRefund() diff --git a/test/Integration/Gateways/GpApiConnector/GpApiApmTest.php b/test/Integration/Gateways/GpApiConnector/GpApiApmTest.php index 83b0e03d..40cc4aac 100644 --- a/test/Integration/Gateways/GpApiConnector/GpApiApmTest.php +++ b/test/Integration/Gateways/GpApiConnector/GpApiApmTest.php @@ -57,6 +57,11 @@ public function setUpConfig() return BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardNotPresent); } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + /** * How to have a success running test. When you will run the test in the console it will be printed the * paypal redirect url. You need to copy the link and open it in a browser, do the login wih your paypal diff --git a/test/Integration/Gateways/GpApiConnector/GpApiBatchTests.php b/test/Integration/Gateways/GpApiConnector/GpApiBatchTests.php index ccfc5f67..e284026d 100644 --- a/test/Integration/Gateways/GpApiConnector/GpApiBatchTests.php +++ b/test/Integration/Gateways/GpApiConnector/GpApiBatchTests.php @@ -49,6 +49,11 @@ protected function setup() : void $this->creditCardData->cardPresent = true; } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function setUpConfig() { return BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardPresent); diff --git a/test/Integration/Gateways/GpApiConnector/GpApiDigitalWalletTest.php b/test/Integration/Gateways/GpApiConnector/GpApiDigitalWalletTest.php index 56876bb8..66bceebf 100644 --- a/test/Integration/Gateways/GpApiConnector/GpApiDigitalWalletTest.php +++ b/test/Integration/Gateways/GpApiConnector/GpApiDigitalWalletTest.php @@ -26,12 +26,17 @@ public function setup() : void $this->card->expYear = date('Y', strtotime('+1 year')); $this->card->cardHolderName = "James Mason"; $this->googlePayToken = '{ - "signature": "MEYCIQCOGbdnafdPhLr2oMjwsh9nIWb1bBHX6vpKKaaWQVXN3gIhALB3ps64qkerCacD3Lqh4AGRuFW2WO+VzplVohRsT/iu", + "signature": "MEYCIQCmqtWzjV/HvFoTCbydIeFcuKvkLe2JqUOkqqLFxw98agIhAN1fo4hBVyPOfMz+hivwbtCUfsBJX3n5w2Z4V9c0/7gY", "protocolVersion": "ECv1", - "signedMessage": "{\"encryptedMessage\":\"ye3wPMhj0U+B77nyQ1H7EvTWP5xbSAiJ9AXmhvCBZiDuU2hJfVe+q+PkYvzM0o0hGOg+7lzTuBo4jdM9ZSz2EblbN6hCt6Am+Mlfnqsw1vJ0r0Pf710mrmvEl8+6H0Grclb8Aes/73OPGbQgN17nPmgUw6Yv8toE2QkjpTIll8kwV800FLAZU7cQAJhrV7r/ouh4WuEN4g8A6P1yMVf16nbWqoU6KUWdS44eHs6fNwlICA9ezVOYkzdt18J6J8t97LBBcenHqH/pT4ynOD5qZWpYvkrkjqgm2EMfmtErQHCg+wNmQTa9hCQ1l5uI/KAeyeNAtZo/rvwtuIWZ+C7kyA9wWeiTNdCf0xK+iE1q6VZnPHdTb7464D3Z/r7lT6TCPOvkdklVY8T77wthRkguz/HvlwDBc2nodmhs6tnADfMwJ9BX33StEHcDWBYLvAF2nWbx\",\"ephemeralPublicKey\":\"BIelcOVaB1LudeTtBav5gS4tglEUf/UpM5dO01mJEmuJVUX4oAFbTB5YyfaKztVaRKC9HusZ+ydyp24Xjqd9x2s\\u003d\",\"tag\":\"dMS/Yh/W7w3BhwW3kM1BmSbc9DJtap3ILjtdH1sDg2c\\u003d\"}" + "signedMessage": "{\"encryptedMessage\":\"QeiCtyFoWkjtYZl9aXOwh1KofQp0T8NurwZKJnpsPObWXWTkOTceXbTSqv1MvorX9I1qtDO6rrEbEfwzD3VJAl0LP2NePp5O4jTw4rh7qjXIQdskwx1+dEwOJSVFGtq4KU9DGRtnhtENezet08mlNGvOdT9Ufy+rX+pKHA5msMmlsdAREr+Fp2NppQE+IhiQDHVi7oiNMnPQLB9z+hr4f8pEg0gUD9qOUdtCalDBb7jwACXW4MvxtNz0Qin7nLQm/4AcRS8xM07uUeys6Z86v3It3WmOqgPNUERx37DIcUaZ2CcF7Oy7uvxpHCshjvpR/Gc0puRPPi1cDGSnqfMuXfyv15hMP3huYe8IHXPFJ855qhnIIeqKnVf+IcsLSYaX+bUc2niDC+VFmOb8RgGYwXrSNCFF8UXvAdNMxCQ1BulIRDxIseh89iwZKKBX3eNj2yxr\",\"ephemeralPublicKey\":\"BOwa6fGQkkFxxF3VnkZoMGmIebvsJ7KGSYtSE6V3nFcTv7UfQF1Txx/vfuSWPUoSQmVPshJ0S8EHIp4Kyf49ozU\\u003d\",\"tag\":\"zB2Bb1L6rOMKV3AiTrMzS4ZgBoKqDZSpf1jYV/8BDm4\\u003d\"}" }'; } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function setUpConfig() { return BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardNotPresent); diff --git a/test/Integration/Gateways/GpApiConnector/GpApiMerchantsOnboardTest.php b/test/Integration/Gateways/GpApiConnector/GpApiMerchantsOnboardTest.php new file mode 100644 index 00000000..48b4b84b --- /dev/null +++ b/test/Integration/Gateways/GpApiConnector/GpApiMerchantsOnboardTest.php @@ -0,0 +1,803 @@ +setUpConfig()); + } + + public function setUpConfig() + { + $config = new GpApiConfig(); + $config->appId = "A1feRdMmEB6m0Y1aQ65H0bDi9ZeAEB2t"; + $config->appKey = "5jPt1OpB6LLitgi7"; + $config->environment = Environment::TEST; + $config->channel = Channel::CardNotPresent; + $config->requestLogger = new SampleRequestLogger(new Logger("logs")); + + return $config; + } + + public function testBoardMerchant() + { + $merchantData = $this->getMerchantData(); + $products = $this->getProductList(); + $persons = $this->getPersonList(); + $bankAccountInformation = $this->getBankAccountData(); + $paymentStatistics = $this->getPaymentStatistics(); + $creditCardInformation = TestAccountData::getCreditCardData(); + + $idempotencyKey = GenerationUtils::getGuid(); + $merchant = PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withDescription('Merchant Business Description') + ->withProductData($products) + ->withCreditCardData($creditCardInformation, PaymentMethodFunction::PRIMARY_PAYOUT) + ->withBankAccountData($bankAccountInformation, PaymentMethodFunction::SECONDARY_PAYOUT) + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->withIdempotencyKey($idempotencyKey) + ->execute(); + + /** @var User $merchant */ + $this->assertTrue($merchant instanceof User); + $this->assertEquals("SUCCESS", $merchant->responseCode); + $this->assertEquals(UserStatus::UNDER_REVIEW, $merchant->userStatus); + $this->assertNotEmpty($merchant->userId); + } + + public function testBoardMerchant_OnlyMandatory() + { + $merchantData = $this->getMerchantData(); + $products = $this->getProductList(); + $persons = $this->getPersonList(); + $paymentStatistics = $this->getPaymentStatistics(); + + $merchant = PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withDescription('Merchant Business Description') + ->withProductData($products) + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->execute(); + + /** @var User $merchant */ + $this->assertTrue($merchant instanceof User); + $this->assertEquals("SUCCESS", $merchant->responseCode); + $this->assertEquals(UserStatus::UNDER_REVIEW, $merchant->userStatus); + $this->assertEquals($merchantData->userName, $merchant->name); + $this->assertEquals("Merchant Boarding in progress", $merchant->statusDescription); + $this->assertNotEmpty($merchant->userId); + } + + //TODO - add idempotency key on service + public function testBoardMerchant_WithIdempotencyKey() + { + $idempotencyKey = GenerationUtils::getGuid(); + + $merchantData = $this->getMerchantData(); + $products = $this->getProductList(); + $persons = $this->getPersonList(); + $paymentStatistics = $this->getPaymentStatistics(); + + $merchant = PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withDescription('Merchant Business Description') + ->withProductData($products) + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->withIdempotencyKey($idempotencyKey) + ->execute(); + + /** @var User $merchant */ + $this->assertTrue($merchant instanceof User); + $this->assertEquals("SUCCESS", $merchant->responseCode); + $this->assertEquals(UserStatus::UNDER_REVIEW, $merchant->userStatus); + $this->assertEquals($merchantData->userName, $merchant->name); + $this->assertEquals("Merchant Boarding in progress", $merchant->statusDescription); + $this->assertNotEmpty($merchant->userId); + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withDescription('Merchant Business Description') + ->withProductData($products) + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->withIdempotencyKey($idempotencyKey) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertStringContainsString('Idempotency Key seen before', $e->getMessage()); + $this->assertEquals('40039', $e->responseCode); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testGetMerchantInfo() + { + $merchantId = 'MER_98f60f1a397c4dd7b7167bda61520292'; + /** @var User $merchant */ + $merchant = PayFacService::getMerchantInfo($merchantId)->execute(); + $this->assertInstanceOf(User::class, $merchant); + $this->assertNotNull($merchant->paymentMethodList); + $paymentMethodList = $merchant->paymentMethodList->getIterator(); + if($paymentMethodList->valid()) { + $paymentMethodList->seek(1); + $this->assertInstanceOf(\GlobalPayments\Api\PaymentMethods\Interfaces\IPaymentMethod::class, + $paymentMethodList->current()['payment_method'] ); + } + } + + public function testGetMerchantInfo_RandomId() + { + $merchantId = 'MER_' . str_replace('-', '', GenerationUtils::getGuid()); + + $errorFound = false; + try { + PayFacService::getMerchantInfo($merchantId) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals("Status Code: INVALID_REQUEST_DATA - Merchant configuration does not exist for the following combination: MMA_1595ca59906346beae43d92c24863430 , " . $merchantId . "", $e->getMessage()); + $this->assertEquals('40041', $e->responseCode); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testGetMerchantInfo_InvalidId() + { + $errorFound = false; + try { + PayFacService::getMerchantInfo(GenerationUtils::getGuid()) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('Status Code: INVALID_TRANSACTION_ACTION - Retrieve information about this transaction is not supported', $e->getMessage()); + $this->assertEquals('40042', $e->responseCode); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testSearchMerchants() + { + /** @var \GlobalPayments\Api\Entities\GpApi\PagedResult $merchants */ + $merchants = ReportingService::findMerchants(1, 10)->execute(); + + $this->assertGreaterThan(0, $merchants->totalRecordCount); + $this->assertLessThanOrEqual(10, count($merchants->result)); + } + + public function testEditMerchantApplicantInfo() + { + /** @var \GlobalPayments\Api\Entities\GpApi\PagedResult $merchants */ + $merchants = ReportingService::findMerchants(1, 1)->execute(); + + $this->assertGreaterThan(0, $merchants->totalRecordCount); + $this->assertEquals(1, count($merchants->result)); + + $merchant = User::fromId(reset($merchants->result)->id, UserType::MERCHANT); + $persons = $this->getPersonList('Update'); + $response = $merchant->edit() + ->withPersonsData($persons) + ->execute(); + + $this->assertTrue($response instanceof User); + $this->assertEquals("SUCCESS", $response->responseCode); + } + + public function testEditMerchantPaymentProcessing() + { + /** @var \GlobalPayments\Api\Entities\GpApi\PagedResult $merchants */ + $merchants = ReportingService::findMerchants(1, 1)->execute(); + + $this->assertGreaterThan(0, $merchants->totalRecordCount); + $this->assertEquals(1, count($merchants->result)); + $paymentStatistics = new PaymentStatistics(); + $paymentStatistics->totalMonthlySalesAmount = '1111'; + $paymentStatistics->highestTicketSalesAmount = '2222'; + + $merchant = User::fromId(reset($merchants->result)->id, UserType::MERCHANT); + $response = $merchant->edit() + ->withPaymentStatistics($paymentStatistics) + ->withDescription('Update merchant payment processing') + ->execute(); + + $this->assertTrue($response instanceof User); + $this->assertEquals("SUCCESS", $response->responseCode); + } + + public function testEditMerchantBusinessInformation() + { + /** @var \GlobalPayments\Api\Entities\GpApi\PagedResult $merchants */ + $merchants = ReportingService::findMerchants(1, 1)->execute(); + + $this->assertGreaterThan(0, $merchants->totalRecordCount); + $this->assertEquals(1, count($merchants->result)); + + $merchant = User::fromId(reset($merchants->result)->id, UserType::MERCHANT); + $merchant->userStatus = UserStatus::ACTIVE; + + $merchantData = new UserPersonalData(); + $merchantData->userName = 'Username'; + $merchantData->dba = 'Doing Business As'; + $merchantData->website = 'https://abcd.com'; + $merchantData->taxIdReference = '987654321'; + $businessAddress = new Address(); + $businessAddress->streetAddress1 = "Apartment 852"; + $businessAddress->streetAddress2 = "Complex 741"; + $businessAddress->streetAddress3 = "Unit 4"; + $businessAddress->city = "Chicago"; + $businessAddress->state = "IL"; + $businessAddress->postalCode = "50001"; + $businessAddress->countryCode = "840"; + $merchantData->userAddress = $businessAddress; + + /** @var User $response */ + $response = $merchant->edit() + ->withUserPersonalData($merchantData) + ->withDescription('Sample Data for description') + ->execute(); + + $this->assertTrue($response instanceof User); + $this->assertEquals("SUCCESS", $response->responseCode); + $this->assertEquals(UserStatus::ACTIVE, $response->userStatus); + $this->assertEquals($merchantData->userName, $response->name); + } + + public function testEditMerchant_RemoveMerchantFromPartner_FewArguments() + { + /** @var \GlobalPayments\Api\Entities\GpApi\PagedResult $merchants */ + $merchants = ReportingService::findMerchants(1, 1)->execute(); + + $this->assertGreaterThan(0, $merchants->totalRecordCount); + $this->assertEquals(1, count($merchants->result)); + + $merchant = User::fromId(reset($merchants->result)->id, UserType::MERCHANT); + + $errorFound = false; + try { + $merchant->edit() + ->withStatusChangeReason(StatusChangeReason::REMOVE_PARTNERSHIP) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Required field is missing.', $e->getMessage()); + $this->assertEquals('40241', $e->responseCode); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testEditMerchant_RemoveMerchantFromPartner_TooManyArguments() + { + /** @var \GlobalPayments\Api\Entities\GpApi\PagedResult $merchants */ + $merchants = ReportingService::findMerchants(1, 1)->execute(); + + $this->assertGreaterThan(0, $merchants->totalRecordCount); + $this->assertEquals(1, count($merchants->result)); + + $merchant = User::fromId(reset($merchants->result)->id, UserType::MERCHANT); + + $errorFound = false; + try { + $merchant->edit() + ->withUserPersonalData($this->getMerchantData()) + ->withStatusChangeReason(StatusChangeReason::REMOVE_PARTNERSHIP) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('Status Code: INVALID_REQUEST_DATA - Bad Request. The request has extra tags which are not required.', $e->getMessage()); + $this->assertEquals('40268', $e->responseCode); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testBoardMerchant_WithoutMerchantData() + { + $products = $this->getProductList(); + $persons = $this->getPersonList(); + $paymentStatistics = $this->getPaymentStatistics(); + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withDescription('Merchant Business Description') + ->withProductData($products) + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->execute(); + } catch (ArgumentException $e) { + $errorFound = true; + $this->assertEquals('Merchant data is mandatory!', $e->getMessage()); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testBoardMerchant_WithoutUserName() + { + $merchantData = $this->getMerchantData(); + $merchantData->userName = null; + + $products = $this->getProductList(); + $persons = $this->getPersonList(); + $paymentStatistics = $this->getPaymentStatistics(); + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withDescription('Merchant Business Description') + ->withProductData($products) + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following fields name', $e->getMessage()); + $this->assertEquals('40005', $e->responseCode); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testBoardMerchant_WithoutLegalName() + { + $merchantData = $this->getMerchantData(); + $merchantData->legalName = null; + + $products = $this->getProductList(); + $persons = $this->getPersonList(); + $paymentStatistics = $this->getPaymentStatistics(); + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withDescription('Merchant Business Description') + ->withProductData($products) + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following fields legal_name', $e->getMessage()); + $this->assertEquals('40005', $e->responseCode); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testBoardMerchant_WithoutMerchantType() + { + $merchantData = $this->getMerchantData(); + $merchantData->type = null; + + $products = $this->getProductList(); + $persons = $this->getPersonList(); + $paymentStatistics = $this->getPaymentStatistics(); + + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withDescription('Merchant Business Description') + ->withProductData($products) + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following fields type', $e->getMessage()); + $this->assertEquals('40005', $e->responseCode); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testBoardMerchant_WithoutDba() + { + $merchantData = $this->getMerchantData(); + $merchantData->dba = null; + + $products = $this->getProductList(); + $persons = $this->getPersonList(); + $paymentStatistics = $this->getPaymentStatistics(); + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withDescription('Merchant Business Description') + ->withProductData($products) + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following fields dba', $e->getMessage()); + $this->assertEquals('40005', $e->responseCode); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testBoardMerchant_WithoutWebsite() + { + $merchantData = $this->getMerchantData(); + $merchantData->website = null; + + $products = $this->getProductList(); + $persons = $this->getPersonList(); + $paymentStatistics = $this->getPaymentStatistics(); + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withDescription('Merchant Business Description') + ->withProductData($products) + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following fields website', $e->getMessage()); + $this->assertEquals('40005', $e->responseCode); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testBoardMerchant_WithoutTaxIdReference() + { + $merchantData = $this->getMerchantData(); + $merchantData->taxIdReference = null; + + $products = $this->getProductList(); + $persons = $this->getPersonList(); + $paymentStatistics = $this->getPaymentStatistics(); + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withDescription('Merchant Business Description') + ->withProductData($products) + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following fields tax_id_reference', $e->getMessage()); + $this->assertEquals('40005', $e->responseCode); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testBoardMerchant_WithoutNotificationStatusUrl() + { + $merchantData = $this->getMerchantData(); + $merchantData->notificationStatusUrl = null; + + $products = $this->getProductList(); + $persons = $this->getPersonList(); + $paymentStatistics = $this->getPaymentStatistics(); + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withDescription('Merchant Business Description') + ->withProductData($products) + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following fields notifications.status_url', $e->getMessage()); + $this->assertEquals('40005', $e->responseCode); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testBoardMerchant_WithoutPersons() + { + $merchantData = $this->getMerchantData(); + $products = $this->getProductList(); + $paymentStatistics = $this->getPaymentStatistics(); + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withDescription('Merchant Business Description') + ->withProductData($products) + ->withPaymentStatistics($paymentStatistics) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('40005', $e->responseCode); + $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following fields : email', $e->getMessage()); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testBoardMerchant_WithoutPaymentStatistics() + { + $merchantData = $this->getMerchantData(); + $products = $this->getProductList(); + $persons = $this->getPersonList(); + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withDescription('Merchant Business Description') + ->withProductData($products) + ->withPersonsData($persons) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('40005', $e->responseCode); + $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following fields payment_processing_statistics.total_monthly_sales_amount', $e->getMessage()); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testBoardMerchant_WithoutTotalMonthlySalesAmount() + { + $merchantData = $this->getMerchantData(); + $products = $this->getProductList(); + $persons = $this->getPersonList(); + + $paymentStatistics = new PaymentStatistics(); + $paymentStatistics->averageTicketSalesAmount = '50000'; + $paymentStatistics->highestTicketSalesAmount = '60000'; + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withProductData($products) + ->withDescription('Merchant Business Description') + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('40005', $e->responseCode); + $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following fields payment_processing_statistics.total_monthly_sales_amount', $e->getMessage()); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testBoardMerchant_WithoutAverageTicketSalesAmount() + { + $merchantData = $this->getMerchantData(); + $products = $this->getProductList(); + $persons = $this->getPersonList(); + + $paymentStatistics = new PaymentStatistics(); + $paymentStatistics->totalMonthlySalesAmount = '3000000'; + $paymentStatistics->highestTicketSalesAmount = '60000'; + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withProductData($products) + ->withDescription('Merchant Business Description') + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('40005', $e->responseCode); + $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following fields payment_processing_statistics.average_ticket_sales_amount', $e->getMessage()); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testBoardMerchant_WithoutHighestTicketSalesAmount() + { + $merchantData = $this->getMerchantData(); + $products = $this->getProductList(); + $persons = $this->getPersonList(); + + $paymentStatistics = new PaymentStatistics(); + $paymentStatistics->totalMonthlySalesAmount = '3000000'; + $paymentStatistics->averageTicketSalesAmount = '50000'; + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withProductData($products) + ->withDescription('Merchant Business Description') + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('40005', $e->responseCode); + $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following fields payment_processing_statistics.highest_ticket_sales_amount', $e->getMessage()); + } finally { + $this->assertTrue($errorFound); + } + } + + public function testBoardMerchant_WithoutDescription() + { + $merchantData = $this->getMerchantData(); + $products = $this->getProductList(); + $persons = $this->getPersonList(); + $paymentStatistics = $this->getPaymentStatistics(); + + $errorFound = false; + try { + PayFacService::createMerchant() + ->withUserPersonalData($merchantData) + ->withProductData($products) + ->withPersonsData($persons) + ->withPaymentStatistics($paymentStatistics) + ->execute(); + } catch (GatewayException $e) { + $errorFound = true; + $this->assertEquals('40005', $e->responseCode); + $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following fields description', $e->getMessage()); + } finally { + $this->assertTrue($errorFound); + } + } + + private function getMerchantData() + { + $merchantData = new UserPersonalData(); + $merchantData->userName = 'CERT_Propay_' . (new \DateTime())->format("YmdHis"); + $merchantData->legalName = 'Business Legal Name'; + $merchantData->dba = 'Doing Business As'; + $merchantData->merchantCategoryCode = '5999'; + $merchantData->website = 'https://example.com'; + $merchantData->notificationEmail = 'merchant@example.com'; + $merchantData->currencyCode = 'USD'; + $merchantData->taxIdReference = '123456789'; + $merchantData->tier = 'test'; + $merchantData->type = UserType::MERCHANT; + + $businessAddress = new Address(); + $businessAddress->streetAddress1 = "Apartment 852"; + $businessAddress->streetAddress2 = "Complex 741"; + $businessAddress->streetAddress3 = "Unit 4"; + $businessAddress->city = "Chicago"; + $businessAddress->state = "IL"; + $businessAddress->postalCode = "50001"; + $businessAddress->countryCode = "840"; + + $merchantData->userAddress = $businessAddress; + + $shippingAddress = new Address(); + $shippingAddress->streetAddress1 = "Flat 456"; + $shippingAddress->streetAddress2 = "House 789"; + $shippingAddress->streetAddress3 = "Basement Flat"; + $shippingAddress->city = "Halifax"; + $shippingAddress->postalCode = "W5 9HR"; + $shippingAddress->countryCode = "826"; + + $merchantData->mailingAddress = $shippingAddress; + $merchantData->notificationStatusUrl = 'https://www.example.com/notifications/status'; + + return $merchantData; + } + + private function getProductList() + { + $products = [ + [1, 'PRO_TRA_CP-US-CARD-A920_SP'], + [1, 'PRO_FMA_PUSH-FUNDS_PP'] + ]; + foreach ($products as $prod) { + $product = new Product(); + list($product->quantity, $product->productId) = $prod; + $productData[] = $product; + } + + return $productData; + } + + private function getPersonList($type = '') + { + $person = new Person(); + $person->functions = PersonFunctions::APPLICANT; + $person->firstName = 'James ' . $type; + $person->middleName = 'Mason ' . $type; + $person->lastName = 'Doe ' . ' ' . $type; + $person->email = 'uniqueemail@address.com'; + $person->dateOfBirth = date('1982-02-23'); + $person->nationalIdReference = '123456789'; + $person->jobTitle = 'CEO'; + $person->equityPercentage = '25'; + if (empty($type)) { + $person->address = new Address(); + $person->address->streetAddress1 = '1 Business Address'; + $person->address->streetAddress2 = 'Suite 2'; + $person->address->streetAddress3 = '1234'; + $person->address->city = 'Atlanta'; + $person->address->state = 'GA'; + $person->address->postalCode = '30346'; + $person->address->country = 'US'; + } + $person->homePhone = new PhoneNumber('01', '8008675309', PhoneNumberType::HOME); + $person->workPhone = new PhoneNumber('01', '8008675309', PhoneNumberType::WORK); + $persons = new PersonList(); + $persons->append($person); + + return $persons; + } + + private function getBankAccountData() + { + $bankAccountInformation = new BankAccountData(); + $bankAccountInformation->accountHolderName = 'Bank Account Holder Name'; + $bankAccountInformation->accountNumber = '123456788'; + $bankAccountInformation->accountOwnershipType = 'Personal'; + $bankAccountInformation->accountType = AccountType::SAVINGS; + $bankAccountInformation->routingNumber = '102000076'; + + return $bankAccountInformation; + } + + private function getPaymentStatistics() + { + $paymentStatistics = new PaymentStatistics(); + $paymentStatistics->totalMonthlySalesAmount = '3000000'; + $paymentStatistics->averageTicketSalesAmount = '50000'; + $paymentStatistics->highestTicketSalesAmount = '60000'; + + return $paymentStatistics; + } +} \ No newline at end of file diff --git a/test/Integration/Gateways/GpApiConnector/GpApiMultipleConfigTest.php b/test/Integration/Gateways/GpApiConnector/GpApiMultipleConfigTest.php index 898c67a7..0dae79a1 100644 --- a/test/Integration/Gateways/GpApiConnector/GpApiMultipleConfigTest.php +++ b/test/Integration/Gateways/GpApiConnector/GpApiMultipleConfigTest.php @@ -48,5 +48,4 @@ public function testMultipleConfig() $this->assertNotSame($thirdResponse, $secondResponse); $this->assertEquals($firstResponse->result[0]->transactionId, $thirdResponse->result[0]->transactionId); } - } \ No newline at end of file diff --git a/test/Integration/Gateways/GpApiConnector/PartnershipModeTest.php b/test/Integration/Gateways/GpApiConnector/PartnershipModeTest.php index 3bdc7bdb..eb9e54b8 100644 --- a/test/Integration/Gateways/GpApiConnector/PartnershipModeTest.php +++ b/test/Integration/Gateways/GpApiConnector/PartnershipModeTest.php @@ -84,6 +84,11 @@ public function setup() : void $this->browserData->userAgent = "Mozilla/5.0 (Windows NT 6.1; Win64, x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/70.0.3538.110 Safari/537.36"; } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function setUpConfig() { BaseGpApiTestConfig::$appId = 'zKxybfLqH7vAOtBQrApxD5AUpS3ITaPz'; @@ -430,5 +435,4 @@ public function testCreditSaleWithPartnerMode_MissingAccountName() } unset($config); } - } \ No newline at end of file diff --git a/test/Integration/Gateways/GpApiConnector/PayLinkTest.php b/test/Integration/Gateways/GpApiConnector/PayLinkTest.php index a64762ca..62620046 100644 --- a/test/Integration/Gateways/GpApiConnector/PayLinkTest.php +++ b/test/Integration/Gateways/GpApiConnector/PayLinkTest.php @@ -32,6 +32,7 @@ use GlobalPayments\Api\Services\PayLinkService; use GlobalPayments\Api\Services\Secure3dService; use GlobalPayments\Api\ServicesContainer; +use GlobalPayments\Api\Tests\Data\BaseGpApiTestConfig; use GlobalPayments\Api\Tests\Data\GpApi3DSTestCards; use GlobalPayments\Api\Utils\GenerationUtils; use GlobalPayments\Api\Utils\Logging\Logger; @@ -49,6 +50,11 @@ class PayLinkTest extends TestCase private $browserData; private $payLinkId; + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function setup() : void { ServicesContainer::configureService($this->setUpConfig()); @@ -109,6 +115,7 @@ public function setup() : void } } + public function setUpConfig() { $config = new GpApiConfig(); @@ -234,7 +241,7 @@ public function testCreatePayLink_ThenCharge() ->execute(); $this->assertPayLinkResponse($response); - $this->assertEquals("NO", $response->payLinkResponse->isShippable); + $this->assertEquals("YES", $response->payLinkResponse->isShippable); fwrite(STDERR, print_r($response->payLinkResponse->url, TRUE)); @@ -456,6 +463,7 @@ public function testEditPayLink() ->orderBy(PayLinkSortProperty::TIME_CREATED, SortDirection::ASC) ->where(SearchCriteria::START_DATE, $this->startDate) ->andWith(SearchCriteria::END_DATE, $this->endDate) + ->andWith(SearchCriteria::PAYLINK_STATUS, PayLinkStatus::ACTIVE) ->execute(); $this->assertNotNull($response); @@ -648,27 +656,6 @@ public function testEditPayLink_MissingUsageMode() } } - public function testEditPayLink_MissingName() - { - $this->assertNotNull($this->payLinkId); - $this->payLink->name = null; - - $exceptionCaught = false; - try { - PayLinkService::edit($this->payLinkId) - ->withAmount($this->amount) - ->withPayLinkData($this->payLink) - ->withDescription('Update Paylink description') - ->execute(); - } catch (ApiException $e) { - $exceptionCaught = true; - $this->assertEquals('40005', $e->responseCode); - $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following field name', $e->getMessage()); - } finally { - $this->assertTrue($exceptionCaught); - } - } - public function testEditPayLink_MissingType() { $this->assertNotNull($this->payLinkId); @@ -709,24 +696,6 @@ public function testEditPayLink_MissingUsageLimit() } } - public function testEditPayLink_MissingDescription() - { - $this->assertNotNull($this->payLinkId); - $exceptionCaught = false; - try { - PayLinkService::edit($this->payLinkId) - ->withAmount($this->amount) - ->withPayLinkData($this->payLink) - ->execute(); - } catch (ApiException $e) { - $exceptionCaught = true; - $this->assertEquals('Status Code: MANDATORY_DATA_MISSING - Request expects the following field description', $e->getMessage()); - $this->assertEquals('40005', $e->responseCode); - } finally { - $this->assertTrue($exceptionCaught); - } - } - public function testEditPayLink_MissingPayLinkData() { $this->assertNotNull($this->payLinkId); diff --git a/test/Integration/Gateways/GpApiConnector/ReportingActionsTest.php b/test/Integration/Gateways/GpApiConnector/ReportingActionsTest.php index 41036db0..ff4c5f9c 100644 --- a/test/Integration/Gateways/GpApiConnector/ReportingActionsTest.php +++ b/test/Integration/Gateways/GpApiConnector/ReportingActionsTest.php @@ -40,6 +40,11 @@ public function setup() : void } } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function setUpConfig() { return BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardNotPresent); diff --git a/test/Integration/Gateways/GpApiConnector/ReportingDepositsTest.php b/test/Integration/Gateways/GpApiConnector/ReportingDepositsTest.php index d8badb94..3fe325e5 100644 --- a/test/Integration/Gateways/GpApiConnector/ReportingDepositsTest.php +++ b/test/Integration/Gateways/GpApiConnector/ReportingDepositsTest.php @@ -37,6 +37,11 @@ public function setup(): void } } + static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function testReportDepositDetail() { $depositId = !empty($this->depositSummary) ? $this->depositSummary->depositId : 'DEP_2342423443'; diff --git a/test/Integration/Gateways/GpApiConnector/ReportingDisputesTest.php b/test/Integration/Gateways/GpApiConnector/ReportingDisputesTest.php index cb4bbcf1..eb495240 100644 --- a/test/Integration/Gateways/GpApiConnector/ReportingDisputesTest.php +++ b/test/Integration/Gateways/GpApiConnector/ReportingDisputesTest.php @@ -39,6 +39,11 @@ public function setUpConfig() return BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardNotPresent); } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + #region Report Disputes public function testReportDisputeDetail() diff --git a/test/Integration/Gateways/GpApiConnector/ReportingSettlementTransactionsTest.php b/test/Integration/Gateways/GpApiConnector/ReportingSettlementTransactionsTest.php index fa0384df..ef9065be 100644 --- a/test/Integration/Gateways/GpApiConnector/ReportingSettlementTransactionsTest.php +++ b/test/Integration/Gateways/GpApiConnector/ReportingSettlementTransactionsTest.php @@ -27,6 +27,11 @@ public function setup() : void ServicesContainer::configureService($this->setUpConfig()); } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function testReportFindSettlementTransactionsByStartDateAndEndDate() { $startDate = (new \DateTime())->modify('-30 days'); diff --git a/test/Integration/Gateways/GpApiConnector/ReportingStoredPaymentMethodsTest.php b/test/Integration/Gateways/GpApiConnector/ReportingStoredPaymentMethodsTest.php index 8b78db4e..f69ae83d 100644 --- a/test/Integration/Gateways/GpApiConnector/ReportingStoredPaymentMethodsTest.php +++ b/test/Integration/Gateways/GpApiConnector/ReportingStoredPaymentMethodsTest.php @@ -23,6 +23,11 @@ public function setup() : void ServicesContainer::configureService($this->setUpConfig()); } + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); + } + public function setUpConfig() { return BaseGpApiTestConfig::gpApiSetupConfig(Channel::CardNotPresent); diff --git a/test/Integration/Gateways/GpApiConnector/ReportingTransactionsTest.php b/test/Integration/Gateways/GpApiConnector/ReportingTransactionsTest.php index d51bd314..c7f67f45 100644 --- a/test/Integration/Gateways/GpApiConnector/ReportingTransactionsTest.php +++ b/test/Integration/Gateways/GpApiConnector/ReportingTransactionsTest.php @@ -23,9 +23,19 @@ class ReportingTransactionsTest extends TestCase { + private $startDate; + private $endDate; + public function setup() : void { ServicesContainer::configureService($this->setUpConfig()); + $this->startDate = (new \DateTime())->modify('-30 days')->setTime(0, 0, 0); + $this->endDate = (new \DateTime())->modify('-3 days')->setTime(0, 0, 0); + } + + public static function tearDownAfterClass() + { + BaseGpApiTestConfig::resetGpApiConfig(); } public function testTransactionDetailsReport() @@ -56,13 +66,11 @@ public function testTransactionDetailsReport_WrongId() public function testReportFindTransactionsByStartDateAndEndDate() { - $startDate = (new \DateTime())->modify('-30 days'); - $endDate = (new \DateTime())->modify('-3 days'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED) - ->where(SearchCriteria::START_DATE, $startDate) - ->andWith(SearchCriteria::END_DATE, $endDate) + ->where(SearchCriteria::START_DATE, $this->startDate) + ->andWith(SearchCriteria::END_DATE, $this->endDate) ->execute(); } catch (ApiException $e) { $this->fail("Find transactions failed with " . $e->getMessage()); @@ -72,19 +80,18 @@ public function testReportFindTransactionsByStartDateAndEndDate() $this->assertTrue(is_array($response->result)); /** @var TransactionSummary $rs */ foreach ($response->result as $rs) { - $this->assertLessThanOrEqual($endDate->format('Y-m-d'), $rs->transactionDate->format('Y-m-d')); - $this->assertGreaterThanOrEqual($startDate->format('Y-m-d'), $rs->transactionDate->format('Y-m-d')); + $this->assertLessThanOrEqual($this->endDate->format('Y-m-d'), $rs->transactionDate->format('Y-m-d')); + $this->assertGreaterThanOrEqual($this->startDate->format('Y-m-d'), $rs->transactionDate->format('Y-m-d')); } } public function testReportFindTransactionsById() { $transactionId = 'TRN_RyWZELCUbOq12IPDowbOevTC9BZxZi_6827116a3d1b'; - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->withTransactionId($transactionId) - ->where(SearchCriteria::START_DATE, $startDate) + ->where(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail("Find transactions by Id failed: " . $e->getMessage()); @@ -99,11 +106,10 @@ public function testReportFindTransactionsById() public function testReportFindTransactionsById_WrongId() { $transactionId = GenerationUtils::getGuid();; - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->withTransactionId($transactionId) - ->where(SearchCriteria::START_DATE, $startDate) + ->where(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail("Find transactions by Id failed: " . $e->getMessage()); @@ -117,12 +123,12 @@ public function testReportFindTransactionsById_WrongId() public function testReportFindTransactionsByBatchId() { $batchId = 'BAT_870078'; - $startDate = new \DateTime('2020-11-01 midnight'); + try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(SearchCriteria::BATCH_ID, $batchId) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by batch id failed: ' . $e->getMessage()); @@ -139,12 +145,11 @@ public function testReportFindTransactionsByBatchId() public function testReportFindTransactionsByType() { $paymentType = PaymentType::SALE; - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(SearchCriteria::PAYMENT_TYPE, $paymentType) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by type failed: ' . $e->getMessage()); @@ -162,7 +167,7 @@ public function testReportFindTransactionsByType() $responseRefund = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(SearchCriteria::PAYMENT_TYPE, $paymentTypeRefund) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by type failed: ' . $e->getMessage()); @@ -183,12 +188,11 @@ public function testReportFindTransactionsByAmountAndCurrencyAndCountry() $amount = 19.99; $currency = 'USD'; //case sensitive $country = 'US'; //case sensitive - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(DataServiceCriteria::AMOUNT, $amount) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->andWith(DataServiceCriteria::CURRENCY, $currency) ->andWith(DataServiceCriteria::COUNTRY, $country) ->execute(); @@ -209,12 +213,11 @@ public function testReportFindTransactionsByAmountAndCurrencyAndCountry() public function testReportFindTransactionsByChannel() { $channel = Channel::CardNotPresent; - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(SearchCriteria::CHANNEL, $channel) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by channel failed: ' . $e->getMessage()); @@ -232,7 +235,7 @@ public function testReportFindTransactionsByChannel() $responseCP = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(SearchCriteria::CHANNEL, $channelCP) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by channel failed: ' . $e->getMessage()); @@ -251,12 +254,11 @@ public function testReportFindTransactionsByChannel() public function testReportFindTransactionsByStatus() { $transactionStatus = TransactionStatus::CAPTURED; - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(SearchCriteria::TRANSACTION_STATUS, $transactionStatus) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by status failed: ' . $e->getMessage()); @@ -272,8 +274,6 @@ public function testReportFindTransactionsByStatus() public function testReportFindTransactionsBy_AllStatuses() { - $startDate = new \DateTime('2020-11-01 midnight'); - $transactionStatus = new TransactionStatus(); $reflectionClass = new ReflectionClass($transactionStatus); foreach ($reflectionClass->getConstants() as $value) { @@ -281,7 +281,7 @@ public function testReportFindTransactionsBy_AllStatuses() $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(SearchCriteria::TRANSACTION_STATUS, $value) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by status failed: ' . $e->getMessage()); @@ -300,12 +300,11 @@ public function testReportFindTransactionsByCardBrandAndAuthCode() { $cardBrand = 'VISA'; $authCode = '12345'; - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(SearchCriteria::CARD_BRAND, $cardBrand) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->andWith(SearchCriteria::AUTH_CODE, $authCode) ->execute(); } catch (ApiException $e) { @@ -323,8 +322,6 @@ public function testReportFindTransactionsByCardBrandAndAuthCode() public function testReportFindTransactionsBy_AllCardBrands() { - $startDate = new \DateTime('2020-11-01 midnight'); - //"MC", "DINERS", "JCB" not supported in sandbox env $cardBrand = array("VISA", "AMEX", "DISCOVER", "CUP"); foreach ($cardBrand as $value) { @@ -332,7 +329,7 @@ public function testReportFindTransactionsBy_AllCardBrands() $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(SearchCriteria::CARD_BRAND, $value) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by card brand failed: ' . $e->getMessage()); @@ -350,12 +347,11 @@ public function testReportFindTransactionsBy_AllCardBrands() public function testReportFindTransactionsByReference() { $referenceNumber = '1010000158841908572'; - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(SearchCriteria::REFERENCE_NUMBER, $referenceNumber) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by reference number failed: ' . $e->getMessage()); @@ -372,12 +368,11 @@ public function testReportFindTransactionsByReference() public function testReportFindTransactionsBy_WrongReference() { $referenceNumber = GenerationUtils::getGuid();; - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(SearchCriteria::REFERENCE_NUMBER, $referenceNumber) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by reference number failed: ' . $e->getMessage()); @@ -391,12 +386,11 @@ public function testReportFindTransactionsBy_WrongReference() public function testReportFindTransactionsByBrandReference() { $brandReference = 's9RpaDwXq1sPRkbP'; - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(SearchCriteria::BRAND_REFERENCE, $brandReference) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by brand reference failed: ' . $e->getMessage()); @@ -413,12 +407,11 @@ public function testReportFindTransactionsByBrandReference() public function testReportFindTransactionsBy_WrongBrandReference() { $brandReference = GenerationUtils::getGuid();; - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(SearchCriteria::BRAND_REFERENCE, $brandReference) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by brand reference failed: ' . $e->getMessage()); @@ -431,7 +424,6 @@ public function testReportFindTransactionsBy_WrongBrandReference() public function testReportFindTransactionsByEntryMode() { - $startDate = new \DateTime('2020-11-01 midnight'); $entryMode = new PaymentEntryMode(); $reflectionClass = new ReflectionClass($entryMode); foreach ($reflectionClass->getConstants() as $value) { @@ -439,7 +431,7 @@ public function testReportFindTransactionsByEntryMode() $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) ->where(SearchCriteria::PAYMENT_ENTRY_MODE, $value) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by entry mode failed: ' . $e->getMessage()); @@ -459,13 +451,12 @@ public function testReportFindTransactionsBy_NumberFirst6_and_NumberLast4() $numberFirst6 = "411111"; $numberLast4 = "1111"; - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED) ->where(SearchCriteria::CARD_NUMBER_FIRST_SIX, $numberFirst6) ->andWith(SearchCriteria::CARD_NUMBER_LAST_FOUR, $numberLast4) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by first6 and last4 of card number failed: ' . $e->getMessage()); @@ -484,13 +475,12 @@ public function testReportFindTransactionsBy_TokenFirst6_and_TokenLast4() { $tokenFirst6 = "516730"; $tokenLast4 = "5507"; - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED) ->where(SearchCriteria::TOKEN_FIRST_SIX, $tokenFirst6) ->andWith(SearchCriteria::TOKEN_LAST_FOUR, $tokenLast4) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by first6 and last4 of token failed: ' . $e->getMessage()); @@ -508,14 +498,13 @@ public function testReportFindTransactionsBy_TokenFirst6_and_TokenLast4_and_Paym { $tokenFirst6 = "516730"; $tokenLast4 = "5507"; - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED) ->where(SearchCriteria::TOKEN_FIRST_SIX, $tokenFirst6) ->andWith(SearchCriteria::TOKEN_LAST_FOUR, $tokenLast4) ->andWith(SearchCriteria::PAYMENT_METHOD_NAME, PaymentMethodName::DIGITAL_WALLET) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by first6 and last4 of token failed: ' . $e->getMessage()); @@ -533,14 +522,13 @@ public function testReportFindTransactionsBy_TokenFirst6_and_TokenLast4_and_Wron { $tokenFirst6 = "516730"; $tokenLast4 = "5507"; - $startDate = new \DateTime('2020-11-01 midnight'); try { ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED) ->where(SearchCriteria::TOKEN_FIRST_SIX, $tokenFirst6) ->andWith(SearchCriteria::TOKEN_LAST_FOUR, $tokenLast4) ->andWith(SearchCriteria::PAYMENT_METHOD_NAME, PaymentMethodName::CARD) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->assertEquals('40043', $e->responseCode); @@ -553,11 +541,10 @@ public function testReportFindTransactionsBy_PaymentMethod() $paymentMethodName = new PaymentMethodName(); $reflectionClass = new ReflectionClass($paymentMethodName); foreach ($reflectionClass->getConstants() as $value) { - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->where(SearchCriteria::PAYMENT_METHOD, $value) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by payment method failed: ' . $e->getMessage()); @@ -570,11 +557,10 @@ public function testReportFindTransactionsBy_PaymentMethod() public function testReportFindTransactionsBy_Name() { $name = "NAME NOT PROVIDED"; - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->where(SearchCriteria::CARDHOLDER_NAME, $name) - ->andWith(SearchCriteria::START_DATE, $startDate) + ->andWith(SearchCriteria::START_DATE, $this->startDate) ->execute(); } catch (ApiException $e) { $this->fail('Find transactions by name failed: ' . $e->getMessage()); @@ -640,10 +626,9 @@ public function testReportFindTransactions_OrderBy_TimeCreated() public function testReportFindTransactions_InvalidAccountName() { - $startDate = new \DateTime('2020-11-01 midnight'); try { ReportingService::findTransactionsPaged(1, 10) - ->where(SearchCriteria::START_DATE, $startDate) + ->where(SearchCriteria::START_DATE, $this->startDate) ->andWith(SearchCriteria::ACCOUNT_NAME, "12345") ->execute(); } catch (ApiException $e) { @@ -668,11 +653,10 @@ public function testReportFindTransactions_WithoutStartDate() public function testReportFindTransactionsByPaymentMethod() { - $startDate = new \DateTime('2020-11-01 midnight'); try { $response = ReportingService::findTransactionsPaged(1, 10) ->orderBy(TransactionSortProperty::TIME_CREATED, SortDirection::DESC) - ->where(SearchCriteria::START_DATE, $startDate) + ->where(SearchCriteria::START_DATE, $this->startDate) ->andWith(SearchCriteria::PAYMENT_METHOD_NAME, PaymentMethodName::BANK_TRANSFER) ->execute(); } catch (ApiException $e) { diff --git a/test/Integration/Gateways/GpEcomConnector/Secure3DSExemptionsTest.php b/test/Integration/Gateways/GpEcomConnector/Secure3DSExemptionsTest.php index 12285746..42a3769b 100644 --- a/test/Integration/Gateways/GpEcomConnector/Secure3DSExemptionsTest.php +++ b/test/Integration/Gateways/GpEcomConnector/Secure3DSExemptionsTest.php @@ -25,16 +25,11 @@ class Secure3DSExemptionsTest extends TestCase private $shippingAddress; private $billingAddress; private $browserData; - /** - * @var string - */ - private $gatewayProvider; public function setup() : void { $config = $this->getConfig(); ServicesContainer::configureService($config); - $this->gatewayProvider = $config->getGatewayProvider(); // create card data $this->card = new CreditCardData(); diff --git a/test/Integration/Gateways/PorticoConnector/Certifications/EcommerceTest.php b/test/Integration/Gateways/PorticoConnector/Certifications/EcommerceTest.php index 4d159fff..726fb9d1 100644 --- a/test/Integration/Gateways/PorticoConnector/Certifications/EcommerceTest.php +++ b/test/Integration/Gateways/PorticoConnector/Certifications/EcommerceTest.php @@ -34,7 +34,8 @@ public static function validCardExpYear() return intval(date('Y')) + 1; } - public static function expiredCardExpYear() { + public static function expiredCardExpYear() + { return 2012; } @@ -333,12 +334,12 @@ private function config() $config = new PorticoConfig(); $config->secretApiKey = 'skapi_cert_MTyMAQBiHVEAewvIzXVFcmUd2UcyBge_eCpaASUp0A'; $config->serviceUrl = ($this->enableCryptoUrl) ? - 'https://cert.api2-c.heartlandportico.com/': - 'https://cert.api2.heartlandportico.com'; + 'https://cert.api2-c.heartlandportico.com/' : + 'https://cert.api2.heartlandportico.com'; return $config; } - protected function setup() : void + protected function setup(): void { ServicesContainer::configureService($this->config()); $this->publicKey = 'pkapi_cert_jKc1FtuyAydZhZfbB3'; @@ -353,7 +354,8 @@ public function test000CloseBatch() $response = BatchService::closeBatch(); $this->assertNotNull($response); } catch (ApiException $e) { - if (false === strpos($e->getMessage(), static::BATCH_NOT_OPEN) + if ( + false === strpos($e->getMessage(), static::BATCH_NOT_OPEN) && false === strpos($e->getMessage(), static::NO_TRANS_IN_BATCH) ) { $this->fail($e->getMessage()); @@ -1949,63 +1951,64 @@ public function test999CloseBatch() // printf('batch id: %s', $response->id); // printf('sequence number: %s', $response->sequenceNumber); } catch (ApiException $e) { - if (false === strpos($e->getMessage(), static::BATCH_NOT_OPEN) + if ( + false === strpos($e->getMessage(), static::BATCH_NOT_OPEN) && false === strpos($e->getMessage(), static::NO_TRANS_IN_BATCH) ) { $this->fail($e->getMessage()); } } } - + public function test100ChargeVisaEcommerceInfo() { $address = new Address(); $address->streetAddress1 = '6860 Dallas Pkwy'; $address->postalCode = '75024'; - + $secureEcom = new ThreeDSecure(); $secureEcom->cavv = 'AAACBllleHchZTBWIGV4AAAAAAA='; $secureEcom->xid = 'crqAeMwkEL9r4POdxpByWJ1/wYg='; $secureEcom->eci = '5'; $secureEcom->paymentDataSource = Secure3dPaymentDataSource::VISA_3DSECURE; $secureEcom->paymentDataType = '3DSecure'; - + $card = TestCards::visaManual(); $card->threeDSecure = $secureEcom; - + $response = $card->charge() - ->withCurrency('USD') - ->withAmount(13.01) - ->withAddress($address) - // ->withEcommerceInfo($this->ecommerceInfo) - ->withInvoiceNumber('12345') - ->withAllowDuplicates(true) - ->execute(); - + ->withCurrency('USD') + ->withAmount(13.01) + ->withAddress($address) + // ->withEcommerceInfo($this->ecommerceInfo) + ->withInvoiceNumber('12345') + ->withAllowDuplicates(true) + ->execute(); + $this->assertEquals(true, $response != null); $this->assertEquals('00', $response->responseCode); } - - public function testEcomWithWalletData() + + public function testEcomWithoutWalletData() { $secureEcom = new ThreeDSecure(); $secureEcom->cavv = 'XXXXf98AAajXbDRg3HSUMAACAAA='; $secureEcom->paymentDataSource = Secure3dPaymentDataSource::APPLEPAY; $secureEcom->setVersion(Secure3dVersion::ONE); - + $card = TestCards::visaManual(); $card->threeDSecure = $secureEcom; - + $response = $card->charge(10) - ->withCurrency('USD') - ->withInvoiceNumber('12345') - ->withAllowDuplicates(true) - ->execute(); - + ->withCurrency('USD') + ->withInvoiceNumber('12345') + ->withAllowDuplicates(true) + ->execute(); + $this->assertEquals(true, $response != null); $this->assertEquals('00', $response->responseCode); } - + public function testEcomWithSecure3D() { $secureEcom = new ThreeDSecure(); @@ -2013,43 +2016,36 @@ public function testEcomWithSecure3D() $secureEcom->xid = '0l35fwh1sys3ojzyxelu4ddhmnu5zfke5vst'; $secureEcom->eci = '5'; $secureEcom->setVersion(Secure3dVersion::ONE); - + $card = TestCards::visaManual(); $card->threeDSecure = $secureEcom; - + $response = $card->charge(10) - ->withCurrency('USD') - ->withInvoiceNumber('12345') - ->withAllowDuplicates(true) - ->execute(); - + ->withCurrency('USD') + ->withInvoiceNumber('12345') + ->withAllowDuplicates(true) + ->execute(); + $this->assertEquals(true, $response != null); $this->assertEquals('00', $response->responseCode); - } - + } + public function testEcomWithWalletDataMobileType() { - $secureEcom = new ThreeDSecure(); - $secureEcom->cavv = 'XXXXf98AAajXbDRg3HSUMAACAAA='; - $secureEcom->paymentDataSource = Secure3dPaymentDataSource::APPLEPAY; - - $card = TestCards::visaManual(); - $token = $card->tokenize()->execute()->token; - - $this->assertTrue(!empty($token), 'TOKEN COULD NOT BE GENERATED.'); - - $card->threeDSecure = $secureEcom; + $this->markTestSkipped('You need a valid ApplePay token that it is valid only for 60 sec'); + + $card = new CreditCardData(); $card->mobileType = MobilePaymentMethodType::APPLEPAY; - $card->token = $token; - + $card->paymentSource = Secure3dPaymentDataSource::APPLEPAYWEB; + $card->token = "{\"signature\":\"MEYCIQDn1WUTJSbe0HTenhQBanye9MNlEEbJ9nvk2YDE11JO1wIhAOkA99r3sMpuHsQqdR1C8u9R7C7dm9w7wNniXtYr01gv\",\"protocolVersion\":\"ECv1\",\"signedMessage\":\"{\\\"encryptedMessage\\\":\\\"BxaNW7Rxei+P0lBvb2jvE8+HQ04/uAFrHIXynZqsM7p6rxFDmgt7JxE8XnTnGacTyOXAITFlHnqD5eZJ6dQGMn/DHdhjmi/El25J2rpOzZiJPQk394YQLY2xjUm1xIDR3GB1ATfBIRKoqtf2iXiYQ/u50XINut0ivK/u+qc3lbDAC3IrDUq5DED7uPcPhijF2snKL5sROatKiecfTQRzWMJioTZXDaYfQseoWhhFVvO/UpEcK5CZh5b3CQT89yzDPPdwa1XSH+8DYK6UxvBoelaLYIxpLUNBFcUurLukBM24VlzG5Rs8os8hOXXLixcIcDuiFH4MS7wMIAW4DtKvZF7E78xvh2IvlxckoJ6uZsVuyGBgXgjIgbn95lqeMZsR398YcY/lDl5N/HCpxDJbvSQfd7YNf/hEK/NAa15AAScQ6sorFYcFF1W1iU3+gBR+fuIODT/1VQ\\\\u003d\\\\u003d\\\",\\\"ephemeralPublicKey\\\":\\\"BLTKhwsuoS/Izu5fYd08D+HAd2TAc+FTmEpa7L4wo45p3hQbZ3agZ9J60v8agMsXiDIXpbN1VlBpibKezSFxfoU\\\\u003d\\\",\\\"tag\\\":\\\"hbkBnamtgcDYeDrJvY3IKAzOU4E4aFS2cJUK4f5VVxM\\\\u003d\\\"}\"}"; + $response = $card->charge(10) - ->withCurrency('USD') - ->withInvoiceNumber('12345') - ->withAllowDuplicates(true) - ->execute(); - + ->withCurrency('USD') + ->withInvoiceNumber('12345') + ->withAllowDuplicates(true) + ->execute(); + $this->assertEquals(true, $response != null); $this->assertEquals('00', $response->responseCode); - } - + } } diff --git a/test/Integration/Gateways/ProPay/TestData/TestAccountData.php b/test/Integration/Gateways/ProPay/TestData/TestAccountData.php index 2ec1fcdf..57a6c13f 100644 --- a/test/Integration/Gateways/ProPay/TestData/TestAccountData.php +++ b/test/Integration/Gateways/ProPay/TestData/TestAccountData.php @@ -147,7 +147,7 @@ public static function getCreditCardData() $card = new CreditCardData(); $card->number = '4111111111111111'; $card->expMonth = 12; - $card->expYear = 2025; + $card->expYear = date('Y', strtotime('+1 year')); $card->cvn = '123'; $card->cardHolderName = 'Joe Smith';