From 80463749855597316305e3f11d9c372e2123be4e Mon Sep 17 00:00:00 2001 From: Andrenzo17 <83454487+Andrenzo17@users.noreply.github.com> Date: Wed, 18 Aug 2021 14:03:19 +0700 Subject: [PATCH 1/8] Increase version --- composer.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/composer.json b/composer.json index c89bb7f..a8ade36 100644 --- a/composer.json +++ b/composer.json @@ -2,7 +2,7 @@ "name": "midtrans/midtrans-php", "description": "PHP Wrapper for Midtrans Payment API.", "homepage": "https://midtrans.com", - "version": "2.4.4", + "version": "2.5.0", "type": "library", "license":"MIT", "authors": [ From 02f98cb5bab2a9310d2d1c3187af3e133bbd78ca Mon Sep 17 00:00:00 2001 From: Andrenzo17 <83454487+Andrenzo17@users.noreply.github.com> Date: Wed, 18 Aug 2021 14:04:34 +0700 Subject: [PATCH 2/8] Add example gopay tokenization sample page of gopay tokenization --- examples/core-api/tokenization-process.php | 49 ++++++++++++++++++++++ 1 file changed, 49 insertions(+) create mode 100644 examples/core-api/tokenization-process.php diff --git a/examples/core-api/tokenization-process.php b/examples/core-api/tokenization-process.php new file mode 100644 index 0000000..7942c6b --- /dev/null +++ b/examples/core-api/tokenization-process.php @@ -0,0 +1,49 @@ +"; + +// define variables and set to empty values +$number = ""; + +if ($_SERVER["REQUEST_METHOD"] == "POST") { + $number = ($_POST["number"]); +} + +// required +$params = array( + "payment_type" => "gopay", + "gopay_partner" => array( + "phone_number" => $number, + "redirect_url" => "https://www.google.com" + ) +); + +$response = CoreApi::linkPaymentAccount($params); +?> + + + + + + + +

Simple Gopay Tokenization

+
"> + Phone number: +

+ +
+ + +Result get pay account:"; +echo json_encode($response, JSON_UNESCAPED_SLASHES); +echo "
"; +?> + + + + From a6c293e0420cfaa9490129d9d781e476aceeabec Mon Sep 17 00:00:00 2001 From: Andrenzo17 <83454487+Andrenzo17@users.noreply.github.com> Date: Wed, 18 Aug 2021 14:05:40 +0700 Subject: [PATCH 3/8] Update ApiRequestor.php Add http method patch --- Midtrans/ApiRequestor.php | 39 +++++++++++++++++++++++++++++++-------- 1 file changed, 31 insertions(+), 8 deletions(-) diff --git a/Midtrans/ApiRequestor.php b/Midtrans/ApiRequestor.php index cec3e87..5f0b766 100644 --- a/Midtrans/ApiRequestor.php +++ b/Midtrans/ApiRequestor.php @@ -22,7 +22,7 @@ class ApiRequestor */ public static function get($url, $server_key, $data_hash) { - return self::remoteCall($url, $server_key, $data_hash, false); + return self::remoteCall($url, $server_key, $data_hash, 'GET'); } /** @@ -36,7 +36,21 @@ public static function get($url, $server_key, $data_hash) */ public static function post($url, $server_key, $data_hash) { - return self::remoteCall($url, $server_key, $data_hash, true); + return self::remoteCall($url, $server_key, $data_hash, 'POST'); + } + + /** + * Send PATCH request + * + * @param string $url + * @param string $server_key + * @param mixed[] $data_hash + * @return mixed + * @throws Exception + */ + public static function patch($url, $server_key, $data_hash) + { + return self::remoteCall($url, $server_key, $data_hash, 'PATCH'); } /** @@ -49,7 +63,7 @@ public static function post($url, $server_key, $data_hash) * @return mixed * @throws Exception */ - public static function remoteCall($url, $server_key, $data_hash, $post = true) + public static function remoteCall($url, $server_key, $data_hash, $method) { $ch = curl_init(); @@ -84,7 +98,7 @@ public static function remoteCall($url, $server_key, $data_hash, $post = true) CURLOPT_HTTPHEADER => array( 'Content-Type: application/json', 'Accept: application/json', - 'User-Agent: midtrans-php-v2.4.4', + 'User-Agent: midtrans-php-v2.5.0', 'Authorization: Basic ' . base64_encode($server_key . ':') ), CURLOPT_RETURNTRANSFER => 1 @@ -111,9 +125,18 @@ public static function remoteCall($url, $server_key, $data_hash, $post = true) $curl_options = array_replace_recursive($curl_options, Config::$curlOptions, $headerOptions); } - if ($post) { + if ($method == 'POST') { $curl_options[CURLOPT_POST] = 1; + if ($data_hash) { + $body = json_encode($data_hash); + $curl_options[CURLOPT_POSTFIELDS] = $body; + } else { + $curl_options[CURLOPT_POSTFIELDS] = ''; + } + } elseif ($method == 'PATCH') { + curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'PATCH'); + if ($data_hash) { $body = json_encode($data_hash); $curl_options[CURLOPT_POSTFIELDS] = $body; @@ -126,7 +149,7 @@ public static function remoteCall($url, $server_key, $data_hash, $post = true) // For testing purpose if (class_exists('\Midtrans\MT_Tests') && MT_Tests::$stubHttp) { - $result = self::processStubed($curl_options, $url, $server_key, $data_hash, $post); + $result = self::processStubed($curl_options, $url, $server_key, $data_hash, $method); } else { $result = curl_exec($ch); // curl_close($ch); @@ -152,13 +175,13 @@ public static function remoteCall($url, $server_key, $data_hash, $post = true) } } - private static function processStubed($curl, $url, $server_key, $data_hash, $post) + private static function processStubed($curl, $url, $server_key, $data_hash, $method) { MT_Tests::$lastHttpRequest = array( "url" => $url, "server_key" => $server_key, "data_hash" => $data_hash, - "post" => $post, + $method => $method, "curl" => $curl ); From 3217e0812d98717bc38dda64f545df39cb4cf1f7 Mon Sep 17 00:00:00 2001 From: Andrenzo17 <83454487+Andrenzo17@users.noreply.github.com> Date: Wed, 18 Aug 2021 14:06:07 +0700 Subject: [PATCH 4/8] Update Config.php change base url --- Midtrans/Config.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Midtrans/Config.php b/Midtrans/Config.php index d566860..b5caa33 100644 --- a/Midtrans/Config.php +++ b/Midtrans/Config.php @@ -66,8 +66,8 @@ class Config */ public static $curlOptions = array(); - const SANDBOX_BASE_URL = 'https://api.sandbox.midtrans.com/v2'; - const PRODUCTION_BASE_URL = 'https://api.midtrans.com/v2'; + const SANDBOX_BASE_URL = 'https://api.sandbox.midtrans.com'; + const PRODUCTION_BASE_URL = 'https://api.midtrans.com'; const SNAP_SANDBOX_BASE_URL = 'https://app.sandbox.midtrans.com/snap/v1'; const SNAP_PRODUCTION_BASE_URL = 'https://app.midtrans.com/snap/v1'; From f4099dc3be92de53299f3962f51886249c17bcb9 Mon Sep 17 00:00:00 2001 From: Andrenzo17 <83454487+Andrenzo17@users.noreply.github.com> Date: Wed, 18 Aug 2021 14:07:51 +0700 Subject: [PATCH 5/8] Update CoreApi.php - add gopay tokenization and API subscription - update getBaseurl --- Midtrans/CoreApi.php | 145 ++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 137 insertions(+), 8 deletions(-) diff --git a/Midtrans/CoreApi.php b/Midtrans/CoreApi.php index ce2cd34..9e93a2e 100644 --- a/Midtrans/CoreApi.php +++ b/Midtrans/CoreApi.php @@ -3,6 +3,7 @@ namespace Midtrans; use Exception; + /** * Provide charge and capture functions for Core API */ @@ -36,7 +37,7 @@ public static function charge($params) } return ApiRequestor::post( - Config::getBaseUrl() . '/charge', + Config::getBaseUrl() . '/v2/charge', Config::$serverKey, $payloads ); @@ -56,14 +57,14 @@ public static function capture($param) ); return ApiRequestor::post( - Config::getBaseUrl() . '/capture', + Config::getBaseUrl() . '/v2/capture', Config::$serverKey, $payloads ); } /** - * Do `/card/register` API request to Core API + * Do `/v2/card/register` API request to Core API * * @param $cardNumber * @param $expMoth @@ -79,14 +80,14 @@ public static function cardRegister($cardNumber, $expMoth, $expYear) . "&client_key=" . Config::$clientKey; return ApiRequestor::get( - Config::getBaseUrl() . $path, + Config::getBaseUrl() . "/v2" . $path, Config::$clientKey, false ); } /** - * Do `/token` API request to Core API + * Do `/v2/token` API request to Core API * * @param $cardNumber * @param $expMoth @@ -104,14 +105,14 @@ public static function cardToken($cardNumber, $expMoth, $expYear, $cvv) . "&client_key=" . Config::$clientKey; return ApiRequestor::get( - Config::getBaseUrl() . $path, + Config::getBaseUrl() . "/v2" . $path, Config::$clientKey, false ); } /** - * Do `/point_inquiry/` API request to Core API + * Do `/v2/point_inquiry/` API request to Core API * * @param string tokenId - tokenId of credit card (more params detail refer to: https://api-docs.midtrans.com) * @return mixed @@ -120,9 +121,137 @@ public static function cardToken($cardNumber, $expMoth, $expYear, $cvv) public static function cardPointInquiry($tokenId) { return ApiRequestor::get( - Config::getBaseUrl() . '/point_inquiry/' . $tokenId, + Config::getBaseUrl() . '/v2/point_inquiry/' . $tokenId, + Config::$serverKey, + false + ); + } + + /** + * Create `/v2/pay/account` API request to Core API + * + * @param string create pay account request (more params detail refer to: https://api-docs.midtrans.com/#create-pay-account) + * @return mixed + * @throws Exception + */ + public static function linkPaymentAccount($param) + { + return ApiRequestor::post( + Config::getBaseUrl() . '/v2/pay/account', + Config::$serverKey, + $param + ); + } + + /** + * Do `/v2/pay/account/` API request to Core API + * + * @param string accountId (more params detail refer to: https://api-docs.midtrans.com/#get-pay-account) + * @return mixed + * @throws Exception + */ + public static function getPaymentAccount($accountId) + { + return ApiRequestor::get( + Config::getBaseUrl() . '/v2/pay/account/' . $accountId, Config::$serverKey, false ); } + + /** + * Unbind `/v2/pay/account//unbind` API request to Core API + * + * @param string accountId (more params detail refer to: https://api-docs.midtrans.com/#unbind-pay-account) + * @return mixed + * @throws Exception + */ + public static function unlinkPaymentAccount($accountId) + { + return ApiRequestor::post( + Config::getBaseUrl() . '/v2/pay/account/' . $accountId . '/unbind', + Config::$serverKey, + false + ); + } + + /** + * Create `/v1/subscription` API request to Core API + * + * @param string create subscription request (more params detail refer to: https://api-docs.midtrans.com/#create-subscription) + * @return mixed + * @throws Exception + */ + public static function createSubscription($param) + { + return ApiRequestor::post( + Config::getBaseUrl() . '/v1/subscriptions', + Config::$serverKey, + $param + ); + } + + /** + * Do `/v1/subscription/{subscription_id}` API request to Core API + * + * @param string get subscription request (more params detail refer to: https://api-docs.midtrans.com/#get-subscription) + * @return mixed + * @throws Exception + */ + public static function getSubscription($SubscriptionId) + { + return ApiRequestor::get( + Config::getBaseUrl() . '/v1/subscriptions/' . $SubscriptionId, + Config::$serverKey, + false + ); + } + + /** + * Do disable `/v1/subscription/{subscription_id}/disable` API request to Core API + * + * @param string disable subscription request (more params detail refer to: https://api-docs.midtrans.com/#disable-subscription) + * @return mixed + * @throws Exception + */ + public static function disableSubscription($SubscriptionId) + { + return ApiRequestor::post( + Config::getBaseUrl() . '/v1/subscriptions/' . $SubscriptionId . '/disable', + Config::$serverKey, + false + ); + } + + /** + * Do enable `/v1/subscription/{subscription_id}/enable` API request to Core API + * + * @param string enable subscription request (more params detail refer to: https://api-docs.midtrans.com/#enable-subscription) + * @return mixed + * @throws Exception + */ + public static function enableSubscription($SubscriptionId) + { + return ApiRequestor::post( + Config::getBaseUrl() . '/v1/subscriptions/' . $SubscriptionId . '/enable', + Config::$serverKey, + false + ); + } + + /** + * Do update subscription `/v1/subscription/{subscription_id}` API request to Core API + * + * @param string update subscription request (more params detail refer to: https://api-docs.midtrans.com/#update-subscription) + * @return mixed + * @throws Exception + */ + public static function updateSubscription($SubscriptionId, $param) + { + return ApiRequestor::patch( + Config::getBaseUrl() . '/v1/subscriptions/' . $SubscriptionId, + Config::$serverKey, + $param + ); + } } From 1fb71997d90abca7e876fac78f83d9e8ffe633c8 Mon Sep 17 00:00:00 2001 From: Andrenzo17 <83454487+Andrenzo17@users.noreply.github.com> Date: Wed, 18 Aug 2021 14:08:23 +0700 Subject: [PATCH 6/8] Update CoreApiIntegrationTest.php add unit test for gopay tokenization and API subscription --- tests/integration/CoreApiIntegrationTest.php | 107 +++++++++++++++++++ 1 file changed, 107 insertions(+) diff --git a/tests/integration/CoreApiIntegrationTest.php b/tests/integration/CoreApiIntegrationTest.php index ef3120b..ee1b95a 100644 --- a/tests/integration/CoreApiIntegrationTest.php +++ b/tests/integration/CoreApiIntegrationTest.php @@ -112,4 +112,111 @@ public function testChargeGopay() $this->assertEquals('201', $this->charge_response->status_code); $this->assertEquals('pending', $this->charge_response->transaction_status); } + + public function testCreatePayAccount() + { + $params = array( + "payment_type" => "gopay", + "gopay_partner" => array( + "phone_number" => 874567446788, + "redirect_url" => "https://www.google.com" + ) + ); + $this->charge_response = CoreApi::linkPaymentAccount($params); + $this->assertEquals('201', $this->charge_response->status_code); + $this->assertEquals('PENDING', $this->charge_response->account_status); + } + + public function testGetPaymentAccount() + { + try { + $this->charge_response = CoreApi::getPaymentAccount("dummy"); + } catch (\Exception $e) { + $this->assertContains("Midtrans API is returning API error.", $e->getMessage()); + } + } + + public function testUnlinkPaymentAccount() + { + try { + $this->charge_response = CoreApi::unlinkPaymentAccount("dummy"); + } catch (\Exception $e) { + $this->assertContains("Account doesn't exist.", $e->getMessage()); + } + } + + public function testCreateSubscription() + { + $param = array( + "name" => "Monthly_2021", + "amount" => "10000", + "currency" => "IDR", + "payment_type" => "credit_card", + "token" => "dummy", + "schedule" => array( + "interval" => 1, + "interval_unit" => "month", + "max_interval" => "12", + "start_time" => "2022-08-17 10:00:01 +0700" + ), + "metadata" => array( + "description" => "Recurring payment for user a" + ), + "customer_details" => array( + "first_name" => "John", + "last_name" => "Doe", + "email" => "johndoe@gmail.com", + "phone_number" => "+628987654321" + ) + ); + $this->charge_response = CoreApi::createSubscription($param); + $this->assertEquals('active', $this->charge_response->status); + $this->subscriptionId = $this->charge_response->id; + } + + public function testGetSubscription() + { + try { + $this->charge_response = CoreApi::getSubscription("dummy"); + } catch (\Exception $e) { + $this->assertContains("Subscription doesn't exist.", $e->getMessage()); + } + } + + public function testDisableSubscription() + { + try { + $this->charge_response = CoreApi::disableSubscription("dummy"); + } catch (\Exception $e) { + $this->assertContains("Subscription doesn't exist.", $e->getMessage()); + } + } + + public function testEnableSubscription() + { + try { + $this->charge_response = CoreApi::enableSubscription("dummy"); + } catch (\Exception $e) { + $this->assertContains("Subscription doesn't exist.", $e->getMessage()); + } + } + + public function testUpdateSubscription() + { + $param = array( + "name" => "Monthly_2021", + "amount" => "25000", + "currency" => "IDR", + "token" => "dummy", + "schedule" => array( + "interval" => 1 + ) + ); + + try { + $this->charge_response = CoreApi::updateSubscription("dummy", $param); + } catch (\Exception $e) { + $this->assertContains("Subscription doesn't exist.", $e->getMessage()); + } + } } From 90b20dc62207d248ce3d3e8a446fcdb2daec5580 Mon Sep 17 00:00:00 2001 From: Andrenzo17 <83454487+Andrenzo17@users.noreply.github.com> Date: Fri, 20 Aug 2021 10:06:53 +0700 Subject: [PATCH 7/8] Update ApiRequestor.php simplify http method post and patch --- Midtrans/ApiRequestor.php | 14 +++++--------- 1 file changed, 5 insertions(+), 9 deletions(-) diff --git a/Midtrans/ApiRequestor.php b/Midtrans/ApiRequestor.php index 5f0b766..a97fee3 100644 --- a/Midtrans/ApiRequestor.php +++ b/Midtrans/ApiRequestor.php @@ -125,8 +125,7 @@ public static function remoteCall($url, $server_key, $data_hash, $method) $curl_options = array_replace_recursive($curl_options, Config::$curlOptions, $headerOptions); } - if ($method == 'POST') { - $curl_options[CURLOPT_POST] = 1; + if ($method != 'GET') { if ($data_hash) { $body = json_encode($data_hash); @@ -134,14 +133,11 @@ public static function remoteCall($url, $server_key, $data_hash, $method) } else { $curl_options[CURLOPT_POSTFIELDS] = ''; } - } elseif ($method == 'PATCH') { - curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'PATCH'); - if ($data_hash) { - $body = json_encode($data_hash); - $curl_options[CURLOPT_POSTFIELDS] = $body; - } else { - $curl_options[CURLOPT_POSTFIELDS] = ''; + if ($method == 'POST') { + $curl_options[CURLOPT_POST] = 1; + } elseif ($method == 'PATCH') { + curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'PATCH'); } } From dc886bf623b004d3e64c9560e460ba4888042a83 Mon Sep 17 00:00:00 2001 From: Andrenzo17 <83454487+Andrenzo17@users.noreply.github.com> Date: Fri, 20 Aug 2021 10:07:26 +0700 Subject: [PATCH 8/8] Update CoreApiIntegrationTest.php add more test with positive-scenario --- tests/integration/CoreApiIntegrationTest.php | 76 +++++++++++++++++--- 1 file changed, 68 insertions(+), 8 deletions(-) diff --git a/tests/integration/CoreApiIntegrationTest.php b/tests/integration/CoreApiIntegrationTest.php index ee1b95a..1b936da 100644 --- a/tests/integration/CoreApiIntegrationTest.php +++ b/tests/integration/CoreApiIntegrationTest.php @@ -125,9 +125,22 @@ public function testCreatePayAccount() $this->charge_response = CoreApi::linkPaymentAccount($params); $this->assertEquals('201', $this->charge_response->status_code); $this->assertEquals('PENDING', $this->charge_response->account_status); + $account_id = $this->charge_response->account_id; + return $account_id; } - public function testGetPaymentAccount() + /** + * @depends testCreatePayAccount + */ + public function testGetPaymentAccount($account_id) + { + $this->charge_response = CoreApi::getPaymentAccount($account_id); + $this->assertEquals('201', $this->charge_response->status_code); + $this->assertEquals('PENDING', $this->charge_response->account_status); + } + + + public function testGetPaymentAccountWithNonExistAccount() { try { $this->charge_response = CoreApi::getPaymentAccount("dummy"); @@ -136,7 +149,7 @@ public function testGetPaymentAccount() } } - public function testUnlinkPaymentAccount() + public function testUnlinkPaymentAccountWithNonExistAccount() { try { $this->charge_response = CoreApi::unlinkPaymentAccount("dummy"); @@ -171,10 +184,20 @@ public function testCreateSubscription() ); $this->charge_response = CoreApi::createSubscription($param); $this->assertEquals('active', $this->charge_response->status); - $this->subscriptionId = $this->charge_response->id; + $subscription_id = $this->charge_response->id; + return $subscription_id; } - public function testGetSubscription() + /** + * @depends testCreateSubscription + */ + public function testGetSubscription($subscription_id) + { + $this->charge_response = CoreApi::getSubscription($subscription_id); + $this->assertEquals('active', $this->charge_response->status); + } + + public function testGetSubscriptionWithNonExistAccount() { try { $this->charge_response = CoreApi::getSubscription("dummy"); @@ -183,7 +206,16 @@ public function testGetSubscription() } } - public function testDisableSubscription() + /** + * @depends testCreateSubscription + */ + public function testDisableSubscription($subscription_id) + { + $this->charge_response = CoreApi::disableSubscription($subscription_id); + $this->assertContains('Subscription is updated.', $this->charge_response->status_message); + } + + public function testDisableSubscriptionWithNonExistAccount() { try { $this->charge_response = CoreApi::disableSubscription("dummy"); @@ -192,7 +224,16 @@ public function testDisableSubscription() } } - public function testEnableSubscription() + /** + * @depends testCreateSubscription + */ + public function testEnableSubscription($subscription_id) + { + $this->charge_response = CoreApi::enableSubscription($subscription_id); + $this->assertContains('Subscription is updated.', $this->charge_response->status_message); + } + + public function testEnableSubscriptionWithNonExistAccount() { try { $this->charge_response = CoreApi::enableSubscription("dummy"); @@ -201,7 +242,26 @@ public function testEnableSubscription() } } - public function testUpdateSubscription() + /** + * @depends testCreateSubscription + */ + public function testUpdateSubscription($subscription_id) + { + $param = array( + "name" => "Monthly_2021", + "amount" => "25000", + "currency" => "IDR", + "token" => "dummy", + "schedule" => array( + "interval" => 1 + ) + ); + + $this->charge_response = CoreApi::updateSubscription($subscription_id, $param); + $this->assertContains('Subscription is updated.', $this->charge_response->status_message); + } + + public function testUpdateSubscriptionWithNonExistAccount() { $param = array( "name" => "Monthly_2021", @@ -219,4 +279,4 @@ public function testUpdateSubscription() $this->assertContains("Subscription doesn't exist.", $e->getMessage()); } } -} +} \ No newline at end of file