From 8106b7e6f35efd05fc20fe920dc22bb699f81a90 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Tue, 24 Oct 2023 18:04:17 +0300 Subject: [PATCH 01/37] update OrderItemsGenerator::generate_shipping_item --- tests/helpers/OrderItemsGenerator.php | 21 ++++----------------- 1 file changed, 4 insertions(+), 17 deletions(-) diff --git a/tests/helpers/OrderItemsGenerator.php b/tests/helpers/OrderItemsGenerator.php index 130e6d5c..8ad86563 100644 --- a/tests/helpers/OrderItemsGenerator.php +++ b/tests/helpers/OrderItemsGenerator.php @@ -95,30 +95,17 @@ public function generate_line_item( array $options = array() ) { } /** - * @todo complete function + * @todo add tax */ public function generate_shipping_item( array $options = array() ) { $options = wp_parse_args( $options, array( 'name' => 'Shipping #' . rand( 1000000, 9999999 ), 'price' => rand( 1, 99999 ) / 100, - 'tax' => rand( 0, 9999 ) / 100, ) ); - if ( ! $this->include_tax ) { - $options['tax'] = 0; - } - - if ( ! empty( $options['tax'] ) ) { - $this->order_generator->add_tax( $options['tax'] ); - } - $order_item_id = $this->order_generator->add_shipping( array( 'method_title' => $options['name'], - 'total' => $options['price'], - 'taxes' => array( - 'total' => [ $options['tax'] ], - 'subtotal' => [ $options['tax'] ] - ) + 'total' => $options['price'] ) ); $order_item = $this->order_generator->order()->get_item( $order_item_id, false ); @@ -128,10 +115,10 @@ public function generate_shipping_item( array $options = array() ) { 'ordertext' => $options['name'], 'quantity' => 1, 'amount' => rp_prepare_amount( - $options['price'] + $options['tax'], + $options['price'], $this->order_generator->order()->get_currency() ), - 'vat' => round( $options['tax'] / $options['price'], 2 ), + 'vat' => .0, 'amount_incl_vat' => $this->include_tax ); } From 0eb137a79884217c442dd2fcec3382d13d2c11d7 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Tue, 24 Oct 2023 18:04:26 +0300 Subject: [PATCH 02/37] update ReepayGatewayTest --- .../unit/gatewaysTests/ReepayGatewayTest.php | 34 +++++++++---------- 1 file changed, 16 insertions(+), 18 deletions(-) diff --git a/tests/unit/gatewaysTests/ReepayGatewayTest.php b/tests/unit/gatewaysTests/ReepayGatewayTest.php index f61f15d9..4a2800cd 100644 --- a/tests/unit/gatewaysTests/ReepayGatewayTest.php +++ b/tests/unit/gatewaysTests/ReepayGatewayTest.php @@ -44,7 +44,7 @@ public static function tear_down_after_class() { * [true, false] * [true, true] */ - public function test_get_order_items_line_items( bool $include_tax = false, bool $only_not_settled = false ) { + public function test_get_order_items_line_items( bool $include_tax, bool $only_not_settled ) { $order_items_generator = new OrderItemsGenerator( $this->order_generator, array( @@ -75,12 +75,8 @@ public function test_get_order_items_line_items( bool $include_tax = false, bool * [false, true] * [true, false] * [true, true] - * - * @todo complete test */ - public function test_get_order_items_shipping_items( bool $include_tax = true, bool $only_not_settled = true ) { - $this->markTestSkipped(); - + public function test_get_order_items_shipping_items( bool $include_tax, bool $only_not_settled ) { $order_items_generator = new OrderItemsGenerator( $this->order_generator, array( @@ -89,20 +85,22 @@ public function test_get_order_items_shipping_items( bool $include_tax = true, b ) ); -// $order_items_generator->generate_line_item([ -// 'price' => 200, -// 'quantity' => 3, -// 'tax' => 5 -// ]); - $order_items_generator->generate_shipping_item([ - 'price' => 300, + $order_items_generator->generate_line_item([ + 'price' => 200, + 'quantity' => 3, 'tax' => 5 ]); -// $order_items_generator->generate_shipping_item( array( -// 'meta' => array( -// 'settled' => true -// ) -// ) ); + + $order_items_generator->generate_shipping_item([ + 'price' => 300 + ]); + + $order_items_generator->generate_shipping_item( array( + 'price' => 300, + 'meta' => array( + 'settled' => true + ) + ) ); $this->assertSame( $order_items_generator->get_order_items(), From 4967d48743549467a8ebda0e8c2b0da61b0741df Mon Sep 17 00:00:00 2001 From: "dimaspolohov@yandex.ru" Date: Fri, 27 Oct 2023 16:56:22 +0300 Subject: [PATCH 03/37] Fix analytics order complete --- includes/OrderFlow/Webhook.php | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/includes/OrderFlow/Webhook.php b/includes/OrderFlow/Webhook.php index b40cb98a..b266d183 100644 --- a/includes/OrderFlow/Webhook.php +++ b/includes/OrderFlow/Webhook.php @@ -169,6 +169,9 @@ public function process( array $data ) { $data['order_id'] = $order->get_id(); do_action( 'reepay_webhook_invoice_authorized', $data ); + //Need for analytics + $order->set_date_paid( time() ); + $this->log( sprintf( 'WebHook: Success event type: %s', $data['event_type'] ) ); if ( ! empty( $invoice_data['order_lines'] ) ) { @@ -266,6 +269,8 @@ public function process( array $data ) { $data['order_id'] = $order->get_id(); do_action( 'reepay_webhook_invoice_settled', $data ); + //Need for analytics + $order->set_date_paid( time() ); $this->log( sprintf( 'WebHook: Success event type: %s', $data['event_type'] ) ); break; case 'invoice_cancelled': From 239d7205f66f2719fc9688bc08005b8d5d80c608 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Sun, 29 Oct 2023 18:11:46 +0300 Subject: [PATCH 04/37] update $order param type at some function in ReepayGateway --- includes/Gateways/ReepayGateway.php | 19 +++++++++++++------ 1 file changed, 13 insertions(+), 6 deletions(-) diff --git a/includes/Gateways/ReepayGateway.php b/includes/Gateways/ReepayGateway.php index c09db5b9..fdf0b948 100644 --- a/includes/Gateways/ReepayGateway.php +++ b/includes/Gateways/ReepayGateway.php @@ -582,47 +582,52 @@ public function generate_gateway_status_html( string $key, array $data ): string /** * Check if order can be captured * - * @param WC_Order|int $order order to check. + * @param mixed $order order to check. * @param float|false $amount amount to capture. * * @return bool */ public function can_capture( $order, $amount = false ): bool { + $order = wc_get_order( $order ); return reepay()->api( $this )->can_capture( $order, $amount ); } /** * Check if order can be cancelled * - * @param WC_Order|int $order order to check. + * @param mixed $order order to check. * * @return bool */ public function can_cancel( $order ): bool { + $order = wc_get_order( $order ); return reepay()->api( $this )->can_cancel( $order ); } /** * Check if order can be refunded * - * @param WC_Order $order order to check. + * @param mixed $order order to check. * * @return bool */ - public function can_refund( WC_Order $order ): bool { + public function can_refund( $order ): bool { + $order = wc_get_order( $order ); return reepay()->api( $this )->can_refund( $order ); } /** * Capture order payment * - * @param WC_Order|int $order order to capture. + * @param mixed $order order to capture. * @param float|null $amount amount to capture. Null to capture order total. * * @return void * @throws Exception If capture error. */ public function capture_payment( $order, $amount = null ) { + $order = wc_get_order( $order ); + if ( '1' === $order->get_meta( '_reepay_order_cancelled' ) ) { throw new Exception( __( 'Order is canceled', 'reepay-checkout-gateway' ) ); } @@ -637,11 +642,13 @@ public function capture_payment( $order, $amount = null ) { /** * Cancel order payment * - * @param WC_Order|int $order order to cancel. + * @param mixed $order order to cancel. * * @throws Exception If cancellation error. */ public function cancel_payment( $order ) { + $order = wc_get_order( $order ); + if ( '1' === $order->get_meta( '_reepay_order_cancelled' ) ) { throw new Exception( 'Order is already canceled' ); } From 9433b2e0990bed6073694066c40ae957dfdce76c Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Sun, 29 Oct 2023 18:12:01 +0300 Subject: [PATCH 05/37] fix ReepayGateway::get_order_items --- includes/Gateways/ReepayGateway.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/includes/Gateways/ReepayGateway.php b/includes/Gateways/ReepayGateway.php index fdf0b948..046e5dc8 100644 --- a/includes/Gateways/ReepayGateway.php +++ b/includes/Gateways/ReepayGateway.php @@ -1485,7 +1485,7 @@ public function get_order_items( WC_Order $order, $only_not_settled = false ): a $price = $order->get_line_subtotal( $order_item, false, false ); $price_with_tax = $order->get_line_subtotal( $order_item, true, false ); $tax = $price_with_tax - $price; - $tax_percent = ( $tax > 0 ) ? round( 100 / ( $price / $tax ) ) : 0; + $tax_percent = ( $tax > 0 && $price > 0) ? round( 100 / ( $price / $tax ) ) : 0; $unit_price = round( ( $prices_incl_tax ? $price_with_tax : $price ) / $order_item->get_quantity(), 2 ); if ( $only_not_settled && ! empty( $order_item->get_meta( 'settled' ) ) ) { From f16cb12b6f9066c89966190dfd202f215fff4438 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Sun, 29 Oct 2023 18:12:21 +0300 Subject: [PATCH 06/37] fix ReepayGateway::refund_payment --- includes/Gateways/ReepayGateway.php | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/includes/Gateways/ReepayGateway.php b/includes/Gateways/ReepayGateway.php index 046e5dc8..81d8ff95 100644 --- a/includes/Gateways/ReepayGateway.php +++ b/includes/Gateways/ReepayGateway.php @@ -673,9 +673,7 @@ public function cancel_payment( $order ) { * @throws Exception If already refunded or refund error. */ public function refund_payment( $order, $amount = null, $reason = '' ) { - if ( is_int( $order ) ) { - $order = wc_get_order( $order ); - } + $order = wc_get_order( $order ); if ( '1' === $order->get_meta( '_reepay_order_cancelled' ) ) { throw new Exception( 'Order is already canceled' ); @@ -685,7 +683,7 @@ public function refund_payment( $order, $amount = null, $reason = '' ) { throw new Exception( 'Payment can\'t be refunded.' ); } - if ( .0 === (float) $amount ) { + if ( ! is_null( $amount ) && $amount <= 0 ) { throw new Exception( 'Refund amount must be greater than 0.' ); } From d7fba96de0504c67731675f947839325240549d7 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Sun, 29 Oct 2023 18:12:36 +0300 Subject: [PATCH 07/37] update OrderGenerator --- tests/helpers/OrderGenerator.php | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/tests/helpers/OrderGenerator.php b/tests/helpers/OrderGenerator.php index 239b516e..d9ebd2ed 100644 --- a/tests/helpers/OrderGenerator.php +++ b/tests/helpers/OrderGenerator.php @@ -171,10 +171,11 @@ private function generate_woo_subscription( $product ) { * Add fee to order * * @param array $data optional. Fee data. + * @param array $order_item_data optional. order item meta data. * * @return int order item id */ - public function add_fee( array $data = array() ): int { + public function add_fee( array $data = array(), array $order_item_data = array() ): int { $item = new WC_Order_Item_Fee(); $item->save(); @@ -190,6 +191,8 @@ public function add_fee( array $data = array() ): int { ) ); + $this->add_data_to_order_item( $item, $order_item_data ); + $this->order->add_item( $item ); return $item->get_id(); @@ -199,10 +202,11 @@ public function add_fee( array $data = array() ): int { * Add shipping to order * * @param array $data optional. Shipping data. + * @param array $order_item_data optional. order item meta data. * * @return int order item id */ - public function add_shipping( array $data = array() ): int { + public function add_shipping( array $data = array(), array $order_item_data = array() ): int { $item = new WC_Order_Item_Shipping(); $item->save(); @@ -217,6 +221,8 @@ public function add_shipping( array $data = array() ): int { ) ); + $this->add_data_to_order_item( $item, $order_item_data ); + $this->order->add_item( $item ); $this->order->calculate_shipping(); From ed17c095835b9fadc4dc77a544f3b32e8c4fe989 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Sun, 29 Oct 2023 18:12:49 +0300 Subject: [PATCH 08/37] update OrderItemsGenerator --- tests/helpers/OrderItemsGenerator.php | 82 +++++++++++++++++++++++++-- 1 file changed, 77 insertions(+), 5 deletions(-) diff --git a/tests/helpers/OrderItemsGenerator.php b/tests/helpers/OrderItemsGenerator.php index 8ad86563..e6d0c334 100644 --- a/tests/helpers/OrderItemsGenerator.php +++ b/tests/helpers/OrderItemsGenerator.php @@ -29,6 +29,10 @@ public function get_order_items(): array { return $this->order_items; } + public function add_order_item( array $order_item ) { + $this->order_items[] = $order_item; + } + public function set_options( array $options ) { $options = wp_parse_args( $options, array( 'include_tax' => false, @@ -80,7 +84,9 @@ public function generate_line_item( array $options = array() ) { $order_item = $this->order_generator->order()->get_item( $order_item_id, false ); - if ( ! $this->only_not_settled || empty( $order_item->get_meta( 'settled' ) ) ) { + if ( 'rp_sub' !== $options['type'] && + ( ! $this->only_not_settled || empty( $order_item->get_meta( 'settled' ) ) ) + ) { $this->order_items[] = array( 'ordertext' => $options['name'], 'quantity' => $options['quantity'], @@ -101,12 +107,16 @@ public function generate_shipping_item( array $options = array() ) { $options = wp_parse_args( $options, array( 'name' => 'Shipping #' . rand( 1000000, 9999999 ), 'price' => rand( 1, 99999 ) / 100, + 'meta' => array() ) ); - $order_item_id = $this->order_generator->add_shipping( array( - 'method_title' => $options['name'], - 'total' => $options['price'] - ) ); + $order_item_id = $this->order_generator->add_shipping( + array( + 'method_title' => $options['name'], + 'total' => $options['price'] + ), + $options['meta'] + ); $order_item = $this->order_generator->order()->get_item( $order_item_id, false ); @@ -123,4 +133,66 @@ public function generate_shipping_item( array $options = array() ) { ); } } + + public function generate_fee_item( array $options = array() ) { + $options = wp_parse_args( $options, array( + 'name' => 'Fee #' . rand( 1000000, 9999999 ), + 'price' => rand( 1, 99999 ) / 100, + 'tax' => rand( 0, 9999 ) / 100, + 'meta' => array() + ) ); + + if ( ! $this->include_tax ) { + $options['tax'] = 0; + } + + $order_item_id = $this->order_generator->add_fee( + array( + 'name' => $options['name'], + 'total' => $options['price'], + 'total_tax' => $options['tax'] + ), + $options['meta'] + ); + + $order_item = $this->order_generator->order()->get_item( $order_item_id, false ); + + if ( ! $this->only_not_settled || empty( $order_item->get_meta( 'settled' ) ) ) { + $this->order_items[] = array( + 'ordertext' => $options['name'], + 'quantity' => 1, + 'amount' => rp_prepare_amount( + $options['price'] + $options['tax'], + $this->order_generator->order()->get_currency() + ), + 'vat' => round( $options['tax'] / $options['price'], 2 ), + 'amount_incl_vat' => $this->include_tax + ); + } + } + + public function add_total_discount( array $options = array() ) { + $options = wp_parse_args( $options, array( + 'amount' => rand(20, 100), + 'tax' => rand( 10, 20 ) + ) ); + + if ( ! $this->include_tax ) { + $options['tax'] = 0; + } + + $this->order_generator->order()->set_discount_total( $options['amount'] ); + $this->order_generator->order()->set_discount_tax( $options['tax'] ); + + $this->order_items[] = array( + 'ordertext' => __( 'Discount', 'reepay-checkout-gateway' ), + 'quantity' => 1, + 'amount' => -1 * rp_prepare_amount( + $options['amount'] + $options['tax'], + $this->order_generator->order()->get_currency() + ), + 'vat' => round( $options['tax'] / $options['amount'], 2 ), + 'amount_incl_vat' => $this->include_tax + ); + } } From a5cc1bd1dd31d162c78cf3310084673ce882caf9 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Sun, 29 Oct 2023 18:12:58 +0300 Subject: [PATCH 09/37] add tests to ReepayGatewayTest --- .../unit/gatewaysTests/ReepayGatewayTest.php | 329 +++++++++++++++++- 1 file changed, 327 insertions(+), 2 deletions(-) diff --git a/tests/unit/gatewaysTests/ReepayGatewayTest.php b/tests/unit/gatewaysTests/ReepayGatewayTest.php index 4a2800cd..7e1e38f0 100644 --- a/tests/unit/gatewaysTests/ReepayGatewayTest.php +++ b/tests/unit/gatewaysTests/ReepayGatewayTest.php @@ -8,6 +8,7 @@ use Reepay\Checkout\Gateways\ReepayCheckout; use Reepay\Checkout\Gateways\ReepayGateway; use Reepay\Checkout\Tests\Helpers\OrderItemsGenerator; +use Reepay\Checkout\Tests\Helpers\PLUGINS_STATE; use Reepay\Checkout\Tests\Helpers\Reepay_UnitTestCase; class ReepayGatewayTestChild extends ReepayGateway { @@ -15,7 +16,7 @@ class ReepayGatewayTestChild extends ReepayGateway { } /** - * AnydayTest. + * ReepayGatewayTest. */ class ReepayGatewayTest extends Reepay_UnitTestCase { @@ -34,6 +35,135 @@ public static function tear_down_after_class() { update_option( 'woocommerce_prices_include_tax', 'no' ); } + /** + * @testWith + * [true] + * [false] + */ + public function test_can_capture( bool $result ) { + $this->api_mock->method( 'can_capture' )->willReturn( $result ); + + $this->assertSame( + $result, + self::$gateway->can_capture( $this->order_generator->order() ) + ); + } + + /** + * @testWith + * [true] + * [false] + */ + public function test_can_cancel( bool $result ) { + $this->api_mock->method( 'can_cancel' )->willReturn( $result ); + + $this->assertSame( + $result, + self::$gateway->can_cancel( $this->order_generator->order() ) + ); + } + + public function test_capture_payment_with_cancelled_order() { + $this->order_generator->set_meta( '_reepay_order_cancelled', '1' ); + + $this->expectException(Exception::class); + + self::$gateway->capture_payment( $this->order_generator->order() ); + } + + public function test_capture_payment_with_api_error() { + $this->api_mock->method( 'capture_payment' )->willReturn( new WP_Error() ); + + $this->expectException(Exception::class); + + self::$gateway->capture_payment( $this->order_generator->order() ); + } + + public function test_cancel_payment_with_cancelled_order() { + $this->order_generator->set_meta( '_reepay_order_cancelled', '1' ); + + $this->expectException(Exception::class); + + self::$gateway->cancel_payment( $this->order_generator->order() ); + } + + public function test_cancel_payment_with_api_error() { + $this->api_mock->method( 'cancel_payment' )->willReturn( new WP_Error() ); + + $this->expectException(Exception::class); + + self::$gateway->cancel_payment( $this->order_generator->order() ); + } + + public function test_refund_payment_with_cancelled_order() { + $this->order_generator->set_meta( '_reepay_order_cancelled', '1' ); + + $this->expectException(Exception::class); + $this->expectExceptionMessage('Order is already canceled'); + + self::$gateway->refund_payment( $this->order_generator->order() ); + } + + public function test_refund_payment_with_impossible_to_cancel_order() { + $this->expectException(Exception::class); + $this->expectExceptionMessage('Payment can\'t be refunded.'); + + self::$gateway->refund_payment( $this->order_generator->order() ); + } + + /** + * @param $amount + * + * @testWith + * [ -100.1, true ] + * [ -100.0, true ] + * [ -100, true ] + * [ -0, true ] + * [ 0, true ] + * [ 100, false ] + * [ 100.0, false ] + * [ 100.1, false ] + * [ null, false ] + */ + public function test_refund_payment_with_different_amounts( $amount, bool $expect_error ) { + $this->api_mock->method( 'can_refund' )->willReturn( true ); + + if ( $expect_error ) { + $this->expectException(Exception::class); + $this->expectExceptionMessage('Refund amount must be greater than 0.'); + } else { + $this->expectNotToPerformAssertions(); + } + + self::$gateway->refund_payment( $this->order_generator->order(), $amount ); + } + + public function test_refund_payment_with_api_error() { + $error_message = 'refund api error'; + + $this->api_mock->method( 'can_refund' )->willReturn( true ); + $this->api_mock->method( 'refund' )->willReturn( new WP_Error( 10, $error_message ) ); + + $this->expectException( Exception::class ); + $this->expectExceptionMessage( $error_message ); + + self::$gateway->refund_payment( $this->order_generator->order() ); + } + + /** + * @testWith + * [true] + * [false] + */ + public function test_can_refund( bool $result ) { + $this->api_mock->method( 'can_refund' )->willReturn( $result ); + + $this->assertSame( + $result, + self::$gateway->can_refund( $this->order_generator->order() ) + ); + } + /** * @param bool $include_tax * @param bool $only_not_settled @@ -44,7 +174,7 @@ public static function tear_down_after_class() { * [true, false] * [true, true] */ - public function test_get_order_items_line_items( bool $include_tax, bool $only_not_settled ) { + public function test_get_order_items_line_items_simple( bool $include_tax, bool $only_not_settled ) { $order_items_generator = new OrderItemsGenerator( $this->order_generator, array( @@ -66,6 +196,70 @@ public function test_get_order_items_line_items( bool $include_tax, bool $only_n ); } + /** + * @param bool $include_tax + * @param bool $only_not_settled + * + * @testWith + * [false, false] + * [false, true] + * [true, false] + * [true, true] + */ + public function test_get_order_items_line_items_reepay_subscription( bool $include_tax, bool $only_not_settled ) { + PLUGINS_STATE::maybe_skip_test_by_product_type( 'rp_sub' ); + + $order_items_generator = new OrderItemsGenerator( + $this->order_generator, + array( + 'include_tax' => $include_tax, + 'only_not_settled' => $only_not_settled, + ) + ); + + $order_items_generator->generate_line_item(array( + 'type' => 'rp_sub' + )); + $order_items_generator->generate_line_item( array( + 'type' => 'rp_sub', + 'order_item_meta' => array( + 'settled' => true + ) + ) ); + $order_items_generator->generate_line_item(array( + 'type' => 'rp_sub', + 'product_meta' => array( + '_reepay_subscription_fee' => array( + 'enabled' => 'yes', + 'text' => 'test' + ), + '_line_discount' => 10 + ) + )); + $order_items_generator->generate_line_item( array( + 'type' => 'rp_sub', + 'product_meta' => array( + 'name' => 'Product #-1', + '_reepay_subscription_fee' => array( + 'enabled' => 'yes', + 'text' => 'test' + ), + '_line_discount' => 10 + ), + 'order_item_meta' => array( + 'settled' => true + ) + ) ); + $order_items_generator->generate_fee_item(array( + 'name' => 'Product #-1 - test' + )); + + $this->assertSame( + array(), + self::$gateway->get_order_items( $this->order_generator->order(), $only_not_settled ) + ); + } + /** * @param bool $include_tax * @param bool $only_not_settled @@ -108,6 +302,137 @@ public function test_get_order_items_shipping_items( bool $include_tax, bool $on ); } + /** + * @param bool $include_tax + * @param bool $only_not_settled + * + * @testWith + * [false, false] + * [false, true] + * [true, false] + * [true, true] + */ + public function test_get_order_items_fee_items( bool $include_tax, bool $only_not_settled ) { + $order_items_generator = new OrderItemsGenerator( + $this->order_generator, + array( + 'include_tax' => $include_tax, + 'only_not_settled' => $only_not_settled, + ) + ); + + $order_items_generator->generate_fee_item(); + $order_items_generator->generate_fee_item( array( + 'meta' => array( + 'settled' => true + ) + ) ); + + $this->assertSame( + $order_items_generator->get_order_items(), + self::$gateway->get_order_items( $this->order_generator->order(), $only_not_settled ) + ); + } + + /** + * @param bool $include_tax + * @param bool $only_not_settled + * + * @testWith + * [false, false] + * [false, true] + * [true, false] + * [true, true] + */ + public function test_get_order_reepay_subscription_with_fee( bool $include_tax, bool $only_not_settled ) { + PLUGINS_STATE::maybe_skip_test_by_product_type( 'rp_sub' ); + + $order_items_generator = new OrderItemsGenerator( + $this->order_generator, + array( + 'include_tax' => $include_tax, + 'only_not_settled' => $only_not_settled, + ) + ); + + $order_items_generator->generate_line_item(array( + 'type' => 'rp_sub' + )); + $order_items_generator->generate_fee_item(); + $order_items_generator->generate_fee_item( array( + 'meta' => array( + 'settled' => true + ) + ) ); + + $this->assertSame( + $order_items_generator->get_order_items(), + self::$gateway->get_order_items( $this->order_generator->order(), $only_not_settled ) + ); + } + + /** + * @param bool $include_tax + * @param bool $only_not_settled + * + * @testWith + * [false, false] + * [false, true] + * [true, false] + * [true, true] + */ + public function test_get_order_items_total_discount( bool $include_tax, bool $only_not_settled ) { + $order_items_generator = new OrderItemsGenerator( + $this->order_generator, + array( + 'include_tax' => $include_tax, + 'only_not_settled' => $only_not_settled, + ) + ); + + $order_items_generator->generate_line_item(array( + 'price' => 99 + )); + + $order_items_generator->add_total_discount( array( + 'amount' => 15, + 'tax' => 7 + ) ); + + $this->assertSame( + $order_items_generator->get_order_items(), + self::$gateway->get_order_items( $this->order_generator->order(), $only_not_settled ) + ); + } + + /** + * @param bool $include_tax + * @param bool $only_not_settled + * + * @testWith + * [false, false] + * [false, true] + * [true, false] + * [true, true] + */ + public function test_get_order_items_pw_gift_card( bool $include_tax, bool $only_not_settled ) { + $this->markTestIncomplete(); + } + + /** + * @param bool $include_tax + * @param bool $only_not_settled + * + * @testWith + * [false, false] + * [false, true] + * [true, false] + * [true, true] + */ + public function test_get_order_items_giftup( bool $include_tax, bool $only_not_settled ) { + $this->markTestIncomplete(); + } + /** * @param $card_type * @param $result From 2abb66a9ed44072afa4ce640a9ead04d916d2feb Mon Sep 17 00:00:00 2001 From: "dimaspolohov@yandex.ru" Date: Mon, 30 Oct 2023 18:38:20 +0300 Subject: [PATCH 10/37] Line discount display fixes --- includes/OrderFlow/OrderCapture.php | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/includes/OrderFlow/OrderCapture.php b/includes/OrderFlow/OrderCapture.php index 3877baaf..506f0dc2 100644 --- a/includes/OrderFlow/OrderCapture.php +++ b/includes/OrderFlow/OrderCapture.php @@ -55,9 +55,16 @@ public function __construct() { public function unset_specific_order_item_meta_data( array $formatted_meta, WC_Order_Item $item ): array { // Only on emails notifications. if ( is_admin() && isset( $_GET['post'] ) ) { - foreach ( $formatted_meta as $meta ) { + foreach ( $formatted_meta as $i => $meta ) { if ( in_array( $meta->key, array( 'settled' ), true ) ) { - $meta->display_key = 'Settle'; + $meta->display_key = 'Settled'; + } + if ( in_array( $meta->key, array( '_line_discount' ), true )) { + if (intval($meta->value) == 0){ + unset($formatted_meta[$i]); + }else{ + $meta->display_key = 'Line discount'; + } } } From bb8a24ed22a267bb590daa11c67c286b599acb67 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Tue, 31 Oct 2023 20:13:32 +0300 Subject: [PATCH 11/37] fix ReepayCheckoutTest::test_rp_finalize --- tests/unit/gatewaysTests/ReepayCheckoutTest.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/unit/gatewaysTests/ReepayCheckoutTest.php b/tests/unit/gatewaysTests/ReepayCheckoutTest.php index 68c0faec..7aa030e0 100644 --- a/tests/unit/gatewaysTests/ReepayCheckoutTest.php +++ b/tests/unit/gatewaysTests/ReepayCheckoutTest.php @@ -81,7 +81,7 @@ public function test_rp_finalize( string $token, string $exp_date, string $maske $_GET['key'] = $this->order_generator->order()->get_order_key(); - $this->expectError(); + $this->expectException(Exception::class); self::$gateway->reepay_finalize(); } From 308fa9aec2e29f258ff117ad44a6089fec9fe442 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Tue, 31 Oct 2023 20:19:09 +0300 Subject: [PATCH 12/37] remove ReepayCheckoutTest::test_rp_finalize --- .../unit/gatewaysTests/ReepayCheckoutTest.php | 32 ------------------- 1 file changed, 32 deletions(-) diff --git a/tests/unit/gatewaysTests/ReepayCheckoutTest.php b/tests/unit/gatewaysTests/ReepayCheckoutTest.php index 7aa030e0..0725bfd9 100644 --- a/tests/unit/gatewaysTests/ReepayCheckoutTest.php +++ b/tests/unit/gatewaysTests/ReepayCheckoutTest.php @@ -54,38 +54,6 @@ public function tear_down() { $this->user->delete( true ); } - /** - * Test function test_rp_finalize - * - * @param string $token card token. - * @param string $exp_date card expiry date. - * @param string $masked_card card number. - * @param string $card_type card type. - * - * @testWith - * ["ca_f73e13e5784a5dff32f2f93be7a8130f", "05-43", "411111XXXXXX1111", "Visa"] - */ - public function test_rp_finalize( string $token, string $exp_date, string $masked_card, string $card_type ) { - $_GET['payment_method'] = $token; - - $this->order_generator->set_prop( 'payment_method', reepay()->gateways()->checkout() ); - - $this->api_mock->method( 'get_reepay_cards' )->willReturn( - array( - 'id' => $token, - 'exp_date' => $exp_date, - 'masked_card' => $masked_card, - 'card_type' => $card_type, - ) - ); - - $_GET['key'] = $this->order_generator->order()->get_order_key(); - - $this->expectException(Exception::class); - - self::$gateway->reepay_finalize(); - } - /** * Test function rp_check_is_active * From b63e5bbac494ba1ebdb3df97360eaad3d6e03c07 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Tue, 31 Oct 2023 20:47:43 +0300 Subject: [PATCH 13/37] replace and remove actions from ReepayGateway --- includes/Actions/Admin.php | 40 +++++++++ includes/Actions/Checkout.php | 34 ++++++++ includes/Actions/Main.php | 2 + includes/Gateways/ReepayGateway.php | 125 ---------------------------- 4 files changed, 76 insertions(+), 125 deletions(-) create mode 100644 includes/Actions/Admin.php create mode 100644 includes/Actions/Checkout.php diff --git a/includes/Actions/Admin.php b/includes/Actions/Admin.php new file mode 100644 index 00000000..8b392c87 --- /dev/null +++ b/includes/Actions/Admin.php @@ -0,0 +1,40 @@ + +
+

+
+ +
+

+
+ update_meta_data( '_line_discount', $line_discount + $line_discount_tax ); + } +} \ No newline at end of file diff --git a/includes/Actions/Main.php b/includes/Actions/Main.php index eb0d89c5..3197fe2f 100644 --- a/includes/Actions/Main.php +++ b/includes/Actions/Main.php @@ -20,6 +20,8 @@ class Main { */ public function __construct() { if ( ! apply_filters( 'reepay_running_tests', false ) ) { + new Admin(); + new Checkout(); new ReepayCustomer(); new Subscriptions(); } diff --git a/includes/Gateways/ReepayGateway.php b/includes/Gateways/ReepayGateway.php index c09db5b9..afcedc22 100644 --- a/includes/Gateways/ReepayGateway.php +++ b/includes/Gateways/ReepayGateway.php @@ -179,16 +179,7 @@ public function __construct() { $this->title = $this->settings['title'] ?? 'no'; $this->description = $this->settings['description'] ?? 'no'; - add_action( 'admin_notices', array( $this, 'admin_notice_api_action' ) ); - - add_action( 'the_post', array( $this, 'payment_confirm' ) ); - - add_action( 'wp_ajax_reepay_cancel_payment', array( $this, 'reepay_cancel_payment' ) ); - add_action( 'wp_ajax_nopriv_reepay_cancel_payment', array( $this, 'reepay_cancel_payment' ) ); - add_action( 'woocommerce_checkout_create_order_line_item', array( $this, 'action_checkout_create_order_line_item' ), 10, 4 ); - add_action( 'woocommerce_update_options_payment_gateways_' . $this->id, array( $this, 'process_admin_options' ) ); - } /** @@ -651,8 +642,6 @@ public function cancel_payment( $order ) { if ( is_wp_error( $result ) ) { throw new Exception( $result->get_error_message() ); } - - add_action( 'the_post', array( $this, 'payment_confirm' ) ); } /** @@ -689,34 +678,6 @@ public function refund_payment( $order, $amount = null, $reason = '' ) { } } - /** - * Add notifications in admin for api actions. - */ - public function admin_notice_api_action() { - if ( 'yes' === $this->enabled ) { - $error = get_transient( 'reepay_api_action_error' ); - $success = get_transient( 'reepay_api_action_success' ); - - if ( ! empty( $error ) ) : - ?> -
-

-
- -
-

-
- get_payment_method() !== $this->id ) { - return; - } - - $this->log( - array( - 'source' => 'payment_confirm incoming data', - '$_GET' => $_GET, - ) - ); - - if ( ! empty( $_GET['payment_method'] ) ) { - // Save Payment Method. - $maybe_save_card = $order->get_meta( '_reepay_maybe_save_card' ); - - try { - if ( $maybe_save_card || order_contains_subscription( $order ) ) { - ReepayTokens::reepay_save_token( $order, wc_clean( $_GET['payment_method'] ) ); - } - } catch ( Exception $e ) { - $this->log( 'Card saving error: ' . $e->getMessage() ); - } - } - - $invoice_data = reepay()->api( $this->id )->get_invoice_data( $order ); - - $this->log( - array( - 'source' => 'ReepayGateway::payment_confirm', - 'invoice_data' => $invoice_data, - ) - ); - - if ( ! is_wp_error( $invoice_data ) && ! empty( $invoice_data['transactions'] ) && - ! empty( $invoice_data['transactions'][0] ) && - ! empty( $invoice_data['transactions'][0]['card_transaction'] ) && - ! empty( $invoice_data['transactions'][0]['card_transaction'] ) - ) { - $card_info = $invoice_data['transactions'][0]['card_transaction']; - - update_post_meta( $order->get_id(), 'reepay_masked_card', $card_info['masked_card'] ); - update_post_meta( $order->get_id(), 'reepay_card_type', $card_info['card_type'] ); - } - } - /** * Apply settings from Reepay Checkout Gateway to other gateways. Use it in constructor */ @@ -1428,23 +1320,6 @@ public function process_refund( $order_id, $amount = null, $reason = '' ) { } } - /** - * Count line item discount - * - * @param WC_Order_Item_Product $item created order item. - * @param string $cart_item_key order item key in cart. - * @param array $values values from cart item. - * @param WC_Order $order new order. - * - * @see WC_Checkout::create_order_line_items - */ - public function action_checkout_create_order_line_item( WC_Order_Item_Product $item, string $cart_item_key, array $values, WC_Order $order ) { - $line_discount = $values['line_subtotal'] - $values['line_total']; - $line_discount_tax = $values['line_subtotal_tax'] - $values['line_tax']; - - $item->update_meta_data( '_line_discount', $line_discount + $line_discount_tax ); - } - /** * Get Order lines. * From 91e7dfda34db3b2b4b6feb7571bdbf4d87697e5a Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Tue, 31 Oct 2023 21:20:40 +0300 Subject: [PATCH 14/37] replace tests from ReepayCheckoutTest to ReepayGatewayTest --- .../unit/gatewaysTests/ReepayCheckoutTest.php | 121 ------------------ .../unit/gatewaysTests/ReepayGatewayTest.php | 103 +++++++++++++++ 2 files changed, 103 insertions(+), 121 deletions(-) diff --git a/tests/unit/gatewaysTests/ReepayCheckoutTest.php b/tests/unit/gatewaysTests/ReepayCheckoutTest.php index 0725bfd9..dff52cce 100644 --- a/tests/unit/gatewaysTests/ReepayCheckoutTest.php +++ b/tests/unit/gatewaysTests/ReepayCheckoutTest.php @@ -19,13 +19,6 @@ class ReepayCheckoutTest extends Reepay_UnitTestCase { */ private static ReepayCheckout $gateway; - /** - * WC_Order instance - * - * @var WP_User - */ - private WP_User $user; - /** * Runs the routine before setting up all tests. */ @@ -34,118 +27,4 @@ public static function set_up_before_class() { self::$gateway = new ReepayCheckout(); } - - /** - * Runs the routine before each test is executed. - */ - public function set_up() { - parent::set_up(); - - $user_id = wc_create_new_customer( 'test@test.com', 'test_case_user', 'test_case_user' ); - $this->user = get_user_by( 'id', $user_id ); - } - - /** - * After a test method runs, resets any state in WordPress the test method might have changed. - */ - public function tear_down() { - parent::tear_down(); - - $this->user->delete( true ); - } - - /** - * Test function rp_check_is_active - * - * Test @param string $gateway gateway id. - * - * @testWith - * ["anyday"] - * ["applepay"] - * ["googlepay"] - * ["klarna_pay_later"] - * ["klarna_pay_now"] - * ["klarna_slice_it"] - * ["mobilepay"] - * ["mobilepay_subscriptions"] - * ["paypal"] - * ["checkout"] - * ["resurs"] - * ["swish"] - * ["viabill"] - * ["vipps"] - * @see ReepayGateway::check_is_active - */ - public function test_rp_check_is_active( string $gateway ) { - self::$gateway->id = 'reepay_' . $gateway; - - $this->api_mock->method( 'request' )->willReturn( - array( - array( - 'type' => $gateway, - ), - ) - ); - - $this->assertTrue( self::$gateway->check_is_active() ); - } - - /** - * Test function is_gateway_settings_page - * - * Test @param string $gateway gateway id. - * - * @testWith - * ["anyday"] - * ["applepay"] - * ["googlepay"] - * ["klarna_pay_later"] - * ["klarna_pay_now"] - * ["klarna_slice_it"] - * ["mobilepay"] - * ["mobilepay_subscriptions"] - * ["paypal"] - * ["checkout"] - * ["resurs"] - * ["swish"] - * ["viabill"] - * ["vipps"] - */ - public function test_rp_is_gateway_settings_page( string $gateway ) { - $_GET['tab'] = 'checkout'; - $_GET['section'] = $gateway; - self::$gateway->id = $gateway; - - $this->assertTrue( self::$gateway->is_gateway_settings_page() ); - } - - /** - * Test function rp_get_account_info - * - * Test @param bool $is_test use test or live reepay api keys. - * Test @param string $handle handle of account. - * - * @testWith - * [true, "test-account-handle"] - * [false, "live-account-handle"] - * @see ReepayGateway::get_account_info - */ - public function test_rp_get_account_info( bool $is_test, string $handle ) { - $_GET['tab'] = 'checkout'; - $_GET['section'] = 'checkout'; - self::$gateway->id = 'checkout'; - - $result = array( - 'handle' => $handle, - ); - - $this->api_mock->method( 'request' )->willReturn( - $result - ); - - $this->assertSame( - $result, - self::$gateway->get_account_info( $is_test ) - ); - } } diff --git a/tests/unit/gatewaysTests/ReepayGatewayTest.php b/tests/unit/gatewaysTests/ReepayGatewayTest.php index 7e1e38f0..a25a6333 100644 --- a/tests/unit/gatewaysTests/ReepayGatewayTest.php +++ b/tests/unit/gatewaysTests/ReepayGatewayTest.php @@ -35,6 +35,109 @@ public static function tear_down_after_class() { update_option( 'woocommerce_prices_include_tax', 'no' ); } + /** + * @param string $gateway gateway id. + * + * @testWith + * ["anyday"] + * ["applepay"] + * ["googlepay"] + * ["klarna_pay_later"] + * ["klarna_pay_now"] + * ["klarna_slice_it"] + * ["mobilepay"] + * ["mobilepay_subscriptions"] + * ["paypal"] + * ["checkout"] + * ["resurs"] + * ["swish"] + * ["viabill"] + * ["vipps"] + * + */ + public function test_check_is_active( string $gateway ) { + self::$gateway->id = 'reepay_' . $gateway; + + $this->api_mock->method( 'request' )->willReturn( + array( + array( + 'type' => $gateway, + ), + ) + ); + + $this->assertTrue( self::$gateway->check_is_active() ); + } + + /** + * @param string $gateway gateway id. + * + * @testWith + * ["anyday"] + * ["applepay"] + * ["googlepay"] + * ["klarna_pay_later"] + * ["klarna_pay_now"] + * ["klarna_slice_it"] + * ["mobilepay"] + * ["mobilepay_subscriptions"] + * ["paypal"] + * ["checkout"] + * ["resurs"] + * ["swish"] + * ["viabill"] + * ["vipps"] + */ + public function test_is_gateway_settings_page( string $gateway ) { + $_GET['tab'] = 'checkout'; + $_GET['section'] = $gateway; + self::$gateway->id = $gateway; + + $this->assertTrue( self::$gateway->is_gateway_settings_page() ); + } + + /** + * @param bool $is_test use test or live reepay api keys. + * + * @testWith + * [true] + * [false] + */ + public function test_get_account_info_not_on_settings_page( bool $is_test ) { + $this->assertFalse( self::$gateway->is_gateway_settings_page() ); + $this->assertEmpty( self::$gateway->get_account_info( $is_test ) ); + } + + /** + * @param bool $is_test use test or live reepay api keys. + * + * @testWith + * [true] + * [false] + */ + public function test_get_account_info( bool $is_test ) { + $_GET['tab'] = 'checkout'; + $_GET['section'] = 'checkout'; + self::$gateway->id = 'checkout'; + + $result = array( + 'handle' => 'test_1234', + ); + + $this->api_mock->method( 'request' )->willReturn( $result ); + $this->assertSame( + $result, + self::$gateway->get_account_info( $is_test ) + ); + + $this->api_mock->method( 'request' )->willReturn( 'unused' ); + $this->assertSame( + $result, + self::$gateway->get_account_info( $is_test ), + 'transient cache error' + ); + } + /** * @testWith * [true] From dc79aaa05630ad4a5b4f0a06c9f5abbe908d3541 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Tue, 31 Oct 2023 22:18:47 +0300 Subject: [PATCH 15/37] update LoggingTrait for usage without WooCommerce --- includes/LoggingTrait.php | 23 ++++++++++++----------- 1 file changed, 12 insertions(+), 11 deletions(-) diff --git a/includes/LoggingTrait.php b/includes/LoggingTrait.php index 04d55161..667d45c6 100644 --- a/includes/LoggingTrait.php +++ b/includes/LoggingTrait.php @@ -19,20 +19,21 @@ trait LoggingTrait { * @see WC_Log_Levels */ public function log( $message ) { - // Get Logger instance. - $logger = wc_get_logger(); - - // Write message to log. if ( ! is_string( $message ) ) { $message = print_r( $message, true ); //phpcs:ignore WordPress.PHP.DevelopmentFunctions.error_log_print_r } - $logger->debug( - $message, - array( - 'source' => $this->logging_source, - '_legacy' => true, - ) - ); + if ( function_exists('wc_get_logger' ) ) { + wc_get_logger()->debug( + $message, + array( + 'source' => $this->logging_source, + '_legacy' => true, + ) + ); + } else { + // if Woocommerce disabled. + error_log( print_r( $message, true ) ); + } } } From 54cb4460cd020d9bc5346d497f9bd1b28a5af203 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Tue, 31 Oct 2023 22:19:23 +0300 Subject: [PATCH 16/37] fix WoocommerceExists --- includes/Plugin/WoocommerceExists.php | 27 +++++++++++--- .../admin/notices/woocommerce-missed.php | 36 ------------------- 2 files changed, 23 insertions(+), 40 deletions(-) delete mode 100644 templates/admin/notices/woocommerce-missed.php diff --git a/includes/Plugin/WoocommerceExists.php b/includes/Plugin/WoocommerceExists.php index 7469694f..fb12d8b1 100644 --- a/includes/Plugin/WoocommerceExists.php +++ b/includes/Plugin/WoocommerceExists.php @@ -30,7 +30,6 @@ public function __construct() { public function maybe_deactivate() { if ( ! self::woo_activated() ) { add_action( 'admin_notices', array( $this, 'missing_woocommerce_notice' ) ); - deactivate_plugins( reepay()->get_setting( 'plugin_basename' ), true ); } } @@ -38,9 +37,29 @@ public function maybe_deactivate() { * Show notice in admin */ public function missing_woocommerce_notice() { - reepay()->get_template( - 'admin/notices/woocommerce-missed.php', - array() + $template = << +

+ %s +

+

%s
%s

+ +OUTPUT; + + echo sprintf( + $template, + esc_html__( + 'WooCommerce is inactive or missing.', + 'reepay-checkout-gateway' + ), + __( + 'WooCommerce plugin is inactive or missing. Please install and active it.', + 'reepay-checkout-gateway' + ), + __( + 'WooCommerce Billwerk+ Payments Gateway isn\'t active now.', + 'reepay-checkout-gateway' + ) ); } diff --git a/templates/admin/notices/woocommerce-missed.php b/templates/admin/notices/woocommerce-missed.php deleted file mode 100644 index 0971b94f..00000000 --- a/templates/admin/notices/woocommerce-missed.php +++ /dev/null @@ -1,36 +0,0 @@ - -
-

- - - -

-

- -
- -

-
From 71aa7f94d4fd8bf726baa1fd275cb000f3da294e Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Tue, 31 Oct 2023 22:19:38 +0300 Subject: [PATCH 17/37] update WoocommerceExists usage --- reepay-woocommerce-payment.php | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/reepay-woocommerce-payment.php b/reepay-woocommerce-payment.php index b9b2859c..9c7ca887 100755 --- a/reepay-woocommerce-payment.php +++ b/reepay-woocommerce-payment.php @@ -256,6 +256,10 @@ public function di(): DIContainer { * @return void */ public function include_classes() { + if ( ! WoocommerceExists::woo_activated() ) { + return; + } + new Reepay\Checkout\Admin\Main(); new Reepay\Checkout\Tokens\Main(); From 3115438024506fd86d7c91a8a815f1a8072aaf37 Mon Sep 17 00:00:00 2001 From: "dimaspolohov@yandex.ru" Date: Mon, 6 Nov 2023 12:25:24 +0300 Subject: [PATCH 18/37] Fix hpos class checker --- includes/Functions/hpos.php | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/includes/Functions/hpos.php b/includes/Functions/hpos.php index 4ceac910..578d5808 100644 --- a/includes/Functions/hpos.php +++ b/includes/Functions/hpos.php @@ -15,7 +15,10 @@ * @return bool */ function rp_hpos_enabled(): bool { - return OrderUtil::custom_orders_table_usage_is_enabled(); + if(class_exists(OrderUtil::class)){ + return OrderUtil::custom_orders_table_usage_is_enabled(); + } + return false; } /** From 70220e170026da6214d0b816b58b8141943fea7d Mon Sep 17 00:00:00 2001 From: "dimaspolohov@yandex.ru" Date: Mon, 13 Nov 2023 15:12:22 +0300 Subject: [PATCH 19/37] Show methods for 100% discount --- includes/Actions/Checkout.php | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/includes/Actions/Checkout.php b/includes/Actions/Checkout.php index 2f125386..0de0986a 100644 --- a/includes/Actions/Checkout.php +++ b/includes/Actions/Checkout.php @@ -13,6 +13,24 @@ class Checkout { public function __construct() { add_action( 'woocommerce_checkout_create_order_line_item', array( $this, 'action_checkout_create_order_line_item' ), 10, 4 ); + add_filter( 'woocommerce_cart_needs_payment', array( $this, 'check_need_payment' ), 10 ); + } + + /** + * Count line item discount + * + * @param bool $need_payment need payment marker. + * + * @see WC_Cart::needs_payment + * + * @return bool + */ + public function check_need_payment( bool $need_payment ): bool { + if ( wcs_cart_have_subscription() ) { + return true; + } + + return $need_payment; } /** From efe6ae6295df00619d50386e5447d2393f3f47dd Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Wed, 15 Nov 2023 12:51:06 +0300 Subject: [PATCH 20/37] refactor changing payment method in ReepayGateway class --- includes/Gateways/ReepayGateway.php | 204 +++++++++++++++------------- 1 file changed, 110 insertions(+), 94 deletions(-) diff --git a/includes/Gateways/ReepayGateway.php b/includes/Gateways/ReepayGateway.php index 2387872f..2505ef0a 100644 --- a/includes/Gateways/ReepayGateway.php +++ b/includes/Gateways/ReepayGateway.php @@ -781,99 +781,7 @@ public function process_payment( $order_id ) { } if ( wcs_is_payment_change() ) { - $customer_handle = reepay()->api( $this )->get_customer_handle_by_order( $order_id ); - - if ( absint( $token_id ) > 0 ) { - $token = new TokenReepay( $token_id ); - if ( ! $token->get_id() ) { - wc_add_notice( __( 'Failed to load token.', 'reepay-checkout-gateway' ), 'error' ); - - return false; - } - - if ( $token->get_user_id() !== $order->get_user_id() ) { - wc_add_notice( __( 'Access denied.', 'reepay-checkout-gateway' ), 'error' ); - - return false; - } - - try { - ReepayTokens::assign_payment_token( $order, $token ); - } catch ( Exception $e ) { - $order->add_order_note( $e->getMessage() ); - - return array( - 'result' => 'failure', - 'message' => $e->getMessage(), - ); - } - - $order->add_order_note( - sprintf( - // translators: %s payment method name. - __( 'Payment method changed to "%s"', 'reepay-checkout-gateway' ), - $token->get_display_name() - ) - ); - - return array( - 'result' => 'success', - 'redirect' => $this->get_return_url( $order ), - ); - } else { - // Add new Card. - $params = array( - 'locale' => $this->get_language(), - 'button_text' => __( 'Add card', 'reepay-checkout-gateway' ), - 'create_customer' => array( - 'test' => 'yes' === $this->test_mode, - 'handle' => $customer_handle, - 'email' => $order->get_billing_email(), - 'address' => $order->get_billing_address_1(), - 'address2' => $order->get_billing_address_2(), - 'city' => $order->get_billing_city(), - 'phone' => $order->get_billing_phone(), - 'company' => $order->get_billing_company(), - 'vat' => '', - 'first_name' => $order->get_billing_first_name(), - 'last_name' => $order->get_billing_last_name(), - 'postal_code' => $order->get_billing_postcode(), - ), - 'accept_url' => add_query_arg( - array( - 'action' => 'reepay_finalize', - 'key' => $order->get_order_key(), - ), - admin_url( 'admin-ajax.php' ) - ), - 'cancel_url' => $order->get_cancel_order_url(), - ); - - if ( ! empty( $country ) ) { - $params['create_customer']['country'] = $country; - } - - if ( $this->payment_methods && count( $this->payment_methods ) > 0 ) { - $params['payment_methods'] = $this->payment_methods; - } - - $result = reepay()->api( $this )->request( - 'POST', - 'https://checkout-api.reepay.com/v1/session/recurring', - $params - ); - if ( is_wp_error( $result ) ) { - return array( - 'result' => 'failure', - 'message' => $result->get_error_message(), - ); - } - - return array( - 'result' => 'success', - 'redirect' => $result['url'], - ); - } + return $this->change_payment_method( $order, $token_id ); } $customer_handle = reepay()->api( $this )->get_customer_handle_by_order( $order_id ); @@ -893,7 +801,7 @@ public function process_payment( $order_id ) { 'locale' => $this->get_language(), 'recurring' => apply_filters( 'order_contains_reepay_subscription', - $maybe_save_card || order_contains_subscription( $order ) || wcs_is_payment_change(), + $maybe_save_card || order_contains_subscription( $order ), $order ), 'order' => array( @@ -1144,6 +1052,114 @@ public function process_payment( $order_id ) { return $this->process_session_charge( $params, $order ); } + /** + * @param mixed $order param to get order. + * @param string $token_id optional. Existed payment method to add. + * + * @return array|false + */ + public function change_payment_method( $order, $token_id = '' ) { + $order = wc_get_order( $order ); + + if( empty( $order ) ) { + return false; + } + + $customer_handle = reepay()->api( $this )->get_customer_handle_by_order( $order->get_id() ); + + if ( absint( $token_id ) > 0 ) { + $token = new TokenReepay( $token_id ); + if ( ! $token->get_id() ) { + wc_add_notice( __( 'Failed to load token.', 'reepay-checkout-gateway' ), 'error' ); + + return false; + } + + if ( $token->get_user_id() !== $order->get_user_id() ) { + wc_add_notice( __( 'Access denied.', 'reepay-checkout-gateway' ), 'error' ); + + return false; + } + + try { + ReepayTokens::assign_payment_token( $order, $token ); + } catch ( Exception $e ) { + $order->add_order_note( $e->getMessage() ); + + return array( + 'result' => 'failure', + 'message' => $e->getMessage(), + ); + } + + $order->add_order_note( + sprintf( + // translators: %s payment method name. + __( 'Payment method changed to "%s"', 'reepay-checkout-gateway' ), + $token->get_display_name() + ) + ); + + return array( + 'result' => 'success', + 'redirect' => $this->get_return_url( $order ), + ); + } else { + // Add new Card. + $params = array( + 'locale' => $this->get_language(), + 'button_text' => __( 'Add card', 'reepay-checkout-gateway' ), + 'create_customer' => array( + 'test' => 'yes' === $this->test_mode, + 'handle' => $customer_handle, + 'email' => $order->get_billing_email(), + 'address' => $order->get_billing_address_1(), + 'address2' => $order->get_billing_address_2(), + 'city' => $order->get_billing_city(), + 'phone' => $order->get_billing_phone(), + 'company' => $order->get_billing_company(), + 'vat' => '', + 'first_name' => $order->get_billing_first_name(), + 'last_name' => $order->get_billing_last_name(), + 'postal_code' => $order->get_billing_postcode(), + ), + 'accept_url' => add_query_arg( + array( + 'action' => 'reepay_finalize', + 'key' => $order->get_order_key(), + ), + admin_url( 'admin-ajax.php' ) + ), + 'cancel_url' => $order->get_cancel_order_url(), + ); + + if ( ! empty( $country ) ) { + $params['create_customer']['country'] = $country; + } + + if ( $this->payment_methods && count( $this->payment_methods ) > 0 ) { + $params['payment_methods'] = $this->payment_methods; + } + + $result = reepay()->api( $this )->request( + 'POST', + 'https://checkout-api.reepay.com/v1/session/recurring', + $params + ); + if ( is_wp_error( $result ) ) { + return array( + 'result' => 'failure', + 'message' => $result->get_error_message(), + ); + } + + return array( + 'result' => 'success', + 'redirect' => $result['url'], + ); + } + } + /** * Process session charge * From 6e282e903cc9ed3fb3ad8fce5fa8a8664fae8aa4 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Wed, 15 Nov 2023 12:51:27 +0300 Subject: [PATCH 21/37] add reepay domains to allowed redirect hosts --- includes/Actions/Main.php | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/includes/Actions/Main.php b/includes/Actions/Main.php index 3197fe2f..30d4509b 100644 --- a/includes/Actions/Main.php +++ b/includes/Actions/Main.php @@ -24,6 +24,15 @@ public function __construct() { new Checkout(); new ReepayCustomer(); new Subscriptions(); + + add_filter( 'allowed_redirect_hosts', array( $this, 'add_allowed_redirect_hosts' ) ); } } + + public function add_allowed_redirect_hosts( $hosts ) { + $hosts[] = 'reepay.com'; + $hosts[] = 'checkout.reepay.com'; + + return $hosts; + } } From 991d6ca36e1afde26ba63ba983b8e7958a122b7f Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Wed, 15 Nov 2023 12:52:29 +0300 Subject: [PATCH 22/37] Fix ReepayCheckout::reepay_finalize --- includes/Gateways/ReepayCheckout.php | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/includes/Gateways/ReepayCheckout.php b/includes/Gateways/ReepayCheckout.php index acb2e07b..a3a4df94 100644 --- a/includes/Gateways/ReepayCheckout.php +++ b/includes/Gateways/ReepayCheckout.php @@ -633,7 +633,9 @@ public function payment_fields() { } /** - * Ajax: Finalize Payment + * Ajax: Finalize Payment. Used only to change the payment method + * + * @see ReepayGateway::change_payment_method * * @throws Exception If wrong request data. */ @@ -725,7 +727,11 @@ public function reepay_finalize() { } } - wp_safe_redirect( $this->get_return_url( $order ) ); + $subscription = wcs_get_subscription( $order->get_id() ); + + $redirect_url = ! empty( $subscription ) ? $subscription->get_view_order_url() : $this->get_return_url( $order ); + + wp_safe_redirect( $redirect_url ); } catch ( Exception $e ) { wc_add_notice( $e->getMessage(), 'error' ); wp_safe_redirect( $this->get_return_url() ); From 30e3717c2c5ce893a3fa4759cef32ccd18ce2b09 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Wed, 15 Nov 2023 13:05:20 +0300 Subject: [PATCH 23/37] refactor ReepayGateway::change_payment_method --- includes/Gateways/ReepayGateway.php | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/includes/Gateways/ReepayGateway.php b/includes/Gateways/ReepayGateway.php index 2505ef0a..27328dbd 100644 --- a/includes/Gateways/ReepayGateway.php +++ b/includes/Gateways/ReepayGateway.php @@ -781,7 +781,7 @@ public function process_payment( $order_id ) { } if ( wcs_is_payment_change() ) { - return $this->change_payment_method( $order, $token_id ); + return $this->wcs_change_payment_method( $order, $token_id ); } $customer_handle = reepay()->api( $this )->get_customer_handle_by_order( $order_id ); @@ -1053,12 +1053,14 @@ public function process_payment( $order_id ) { } /** + * Handle WooCommerce subscription changing or adding payment method. + * * @param mixed $order param to get order. * @param string $token_id optional. Existed payment method to add. * * @return array|false */ - public function change_payment_method( $order, $token_id = '' ) { + public function wcs_change_payment_method( $order, $token_id = '' ) { $order = wc_get_order( $order ); if( empty( $order ) ) { From 88e73ccd5dece1bee5e27749ad47acce98fe20d7 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Wed, 15 Nov 2023 13:06:56 +0300 Subject: [PATCH 24/37] phpcs autofix --- includes/Actions/Admin.php | 2 +- includes/Actions/Checkout.php | 2 +- includes/Gateways/ReepayGateway.php | 14 +++++++------- includes/LoggingTrait.php | 2 +- includes/OrderFlow/OrderCapture.php | 8 ++++---- includes/OrderFlow/Webhook.php | 4 ++-- 6 files changed, 16 insertions(+), 16 deletions(-) diff --git a/includes/Actions/Admin.php b/includes/Actions/Admin.php index 8b392c87..fe2ea196 100644 --- a/includes/Actions/Admin.php +++ b/includes/Actions/Admin.php @@ -37,4 +37,4 @@ public function admin_notice_api_action() { set_transient( 'reepay_api_action_success', null, 1 ); endif; } -} \ No newline at end of file +} diff --git a/includes/Actions/Checkout.php b/includes/Actions/Checkout.php index 2f125386..1909eadc 100644 --- a/includes/Actions/Checkout.php +++ b/includes/Actions/Checkout.php @@ -31,4 +31,4 @@ public function action_checkout_create_order_line_item( WC_Order_Item_Product $i $item->update_meta_data( '_line_discount', $line_discount + $line_discount_tax ); } -} \ No newline at end of file +} diff --git a/includes/Gateways/ReepayGateway.php b/includes/Gateways/ReepayGateway.php index 27328dbd..91b2e03b 100644 --- a/includes/Gateways/ReepayGateway.php +++ b/includes/Gateways/ReepayGateway.php @@ -573,8 +573,8 @@ public function generate_gateway_status_html( string $key, array $data ): string /** * Check if order can be captured * - * @param mixed $order order to check. - * @param float|false $amount amount to capture. + * @param mixed $order order to check. + * @param float|false $amount amount to capture. * * @return bool */ @@ -610,8 +610,8 @@ public function can_refund( $order ): bool { /** * Capture order payment * - * @param mixed $order order to capture. - * @param float|null $amount amount to capture. Null to capture order total. + * @param mixed $order order to capture. + * @param float|null $amount amount to capture. Null to capture order total. * * @return void * @throws Exception If capture error. @@ -1055,7 +1055,7 @@ public function process_payment( $order_id ) { /** * Handle WooCommerce subscription changing or adding payment method. * - * @param mixed $order param to get order. + * @param mixed $order param to get order. * @param string $token_id optional. Existed payment method to add. * * @return array|false @@ -1063,7 +1063,7 @@ public function process_payment( $order_id ) { public function wcs_change_payment_method( $order, $token_id = '' ) { $order = wc_get_order( $order ); - if( empty( $order ) ) { + if ( empty( $order ) ) { return false; } @@ -1376,7 +1376,7 @@ public function get_order_items( WC_Order $order, $only_not_settled = false ): a $price = $order->get_line_subtotal( $order_item, false, false ); $price_with_tax = $order->get_line_subtotal( $order_item, true, false ); $tax = $price_with_tax - $price; - $tax_percent = ( $tax > 0 && $price > 0) ? round( 100 / ( $price / $tax ) ) : 0; + $tax_percent = ( $tax > 0 && $price > 0 ) ? round( 100 / ( $price / $tax ) ) : 0; $unit_price = round( ( $prices_incl_tax ? $price_with_tax : $price ) / $order_item->get_quantity(), 2 ); if ( $only_not_settled && ! empty( $order_item->get_meta( 'settled' ) ) ) { diff --git a/includes/LoggingTrait.php b/includes/LoggingTrait.php index 667d45c6..c57a137e 100644 --- a/includes/LoggingTrait.php +++ b/includes/LoggingTrait.php @@ -23,7 +23,7 @@ public function log( $message ) { $message = print_r( $message, true ); //phpcs:ignore WordPress.PHP.DevelopmentFunctions.error_log_print_r } - if ( function_exists('wc_get_logger' ) ) { + if ( function_exists( 'wc_get_logger' ) ) { wc_get_logger()->debug( $message, array( diff --git a/includes/OrderFlow/OrderCapture.php b/includes/OrderFlow/OrderCapture.php index 506f0dc2..2a6ae21d 100644 --- a/includes/OrderFlow/OrderCapture.php +++ b/includes/OrderFlow/OrderCapture.php @@ -59,10 +59,10 @@ public function unset_specific_order_item_meta_data( array $formatted_meta, WC_O if ( in_array( $meta->key, array( 'settled' ), true ) ) { $meta->display_key = 'Settled'; } - if ( in_array( $meta->key, array( '_line_discount' ), true )) { - if (intval($meta->value) == 0){ - unset($formatted_meta[$i]); - }else{ + if ( in_array( $meta->key, array( '_line_discount' ), true ) ) { + if ( intval( $meta->value ) == 0 ) { + unset( $formatted_meta[ $i ] ); + } else { $meta->display_key = 'Line discount'; } } diff --git a/includes/OrderFlow/Webhook.php b/includes/OrderFlow/Webhook.php index b266d183..984f421d 100644 --- a/includes/OrderFlow/Webhook.php +++ b/includes/OrderFlow/Webhook.php @@ -169,7 +169,7 @@ public function process( array $data ) { $data['order_id'] = $order->get_id(); do_action( 'reepay_webhook_invoice_authorized', $data ); - //Need for analytics + // Need for analytics $order->set_date_paid( time() ); $this->log( sprintf( 'WebHook: Success event type: %s', $data['event_type'] ) ); @@ -269,7 +269,7 @@ public function process( array $data ) { $data['order_id'] = $order->get_id(); do_action( 'reepay_webhook_invoice_settled', $data ); - //Need for analytics + // Need for analytics $order->set_date_paid( time() ); $this->log( sprintf( 'WebHook: Success event type: %s', $data['event_type'] ) ); break; From 1ea92f5480b5a8a4545af73aa3f2a123a401dcac Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Wed, 15 Nov 2023 13:10:03 +0300 Subject: [PATCH 25/37] phpcs fixes --- includes/Actions/Admin.php | 8 ++++++++ includes/Actions/Checkout.php | 8 ++++++++ includes/Actions/Main.php | 9 ++++++++- includes/LoggingTrait.php | 2 +- includes/OrderFlow/OrderCapture.php | 2 +- includes/OrderFlow/Webhook.php | 4 ++-- 6 files changed, 28 insertions(+), 5 deletions(-) diff --git a/includes/Actions/Admin.php b/includes/Actions/Admin.php index fe2ea196..9e2fa961 100644 --- a/includes/Actions/Admin.php +++ b/includes/Actions/Admin.php @@ -7,7 +7,15 @@ namespace Reepay\Checkout\Actions; +/** + * Class Admin + * + * @package Reepay\Checkout + */ class Admin { + /** + * Admin constructor. + */ public function __construct() { add_action( 'admin_notices', array( $this, 'admin_notice_api_action' ) ); } diff --git a/includes/Actions/Checkout.php b/includes/Actions/Checkout.php index 1909eadc..0e78c251 100644 --- a/includes/Actions/Checkout.php +++ b/includes/Actions/Checkout.php @@ -10,7 +10,15 @@ use WC_Order; use WC_Order_Item_Product; +/** + * Class Checkout + * + * @package Reepay\Checkout + */ class Checkout { + /** + * Checkout constructor. + */ public function __construct() { add_action( 'woocommerce_checkout_create_order_line_item', array( $this, 'action_checkout_create_order_line_item' ), 10, 4 ); } diff --git a/includes/Actions/Main.php b/includes/Actions/Main.php index 30d4509b..67149b49 100644 --- a/includes/Actions/Main.php +++ b/includes/Actions/Main.php @@ -29,7 +29,14 @@ public function __construct() { } } - public function add_allowed_redirect_hosts( $hosts ) { + /** + * Add reepay domains to allowed hosts list. + * + * @param array $hosts array of allowed hosts. + * + * @return mixed + */ + public function add_allowed_redirect_hosts( array $hosts ) { $hosts[] = 'reepay.com'; $hosts[] = 'checkout.reepay.com'; diff --git a/includes/LoggingTrait.php b/includes/LoggingTrait.php index c57a137e..e5b180e0 100644 --- a/includes/LoggingTrait.php +++ b/includes/LoggingTrait.php @@ -33,7 +33,7 @@ public function log( $message ) { ); } else { // if Woocommerce disabled. - error_log( print_r( $message, true ) ); + error_log( print_r( $message, true ) ); //phpcs:ignore } } } diff --git a/includes/OrderFlow/OrderCapture.php b/includes/OrderFlow/OrderCapture.php index 2a6ae21d..4161b190 100644 --- a/includes/OrderFlow/OrderCapture.php +++ b/includes/OrderFlow/OrderCapture.php @@ -60,7 +60,7 @@ public function unset_specific_order_item_meta_data( array $formatted_meta, WC_O $meta->display_key = 'Settled'; } if ( in_array( $meta->key, array( '_line_discount' ), true ) ) { - if ( intval( $meta->value ) == 0 ) { + if ( intval( $meta->value ) === 0 ) { unset( $formatted_meta[ $i ] ); } else { $meta->display_key = 'Line discount'; diff --git a/includes/OrderFlow/Webhook.php b/includes/OrderFlow/Webhook.php index 984f421d..9e9b5372 100644 --- a/includes/OrderFlow/Webhook.php +++ b/includes/OrderFlow/Webhook.php @@ -169,7 +169,7 @@ public function process( array $data ) { $data['order_id'] = $order->get_id(); do_action( 'reepay_webhook_invoice_authorized', $data ); - // Need for analytics + // Need for analytics. $order->set_date_paid( time() ); $this->log( sprintf( 'WebHook: Success event type: %s', $data['event_type'] ) ); @@ -269,7 +269,7 @@ public function process( array $data ) { $data['order_id'] = $order->get_id(); do_action( 'reepay_webhook_invoice_settled', $data ); - // Need for analytics + // Need for analytics. $order->set_date_paid( time() ); $this->log( sprintf( 'WebHook: Success event type: %s', $data['event_type'] ) ); break; From 4ccb14aedeccafeb8980aeca31c00b3f12def889 Mon Sep 17 00:00:00 2001 From: "dimaspolohov@yandex.ru" Date: Wed, 15 Nov 2023 14:46:50 +0300 Subject: [PATCH 26/37] Reepay add extra check for exist customer --- includes/Actions/ReepayCustomer.php | 24 ++++++++++++++++++++++++ includes/Api.php | 24 ++++++++++++------------ includes/Functions/customer.php | 8 ++++++++ includes/Gateways/ReepayGateway.php | 3 ++- 4 files changed, 46 insertions(+), 13 deletions(-) diff --git a/includes/Actions/ReepayCustomer.php b/includes/Actions/ReepayCustomer.php index 16c3a32f..35d97c3b 100644 --- a/includes/Actions/ReepayCustomer.php +++ b/includes/Actions/ReepayCustomer.php @@ -58,4 +58,28 @@ public static function set_reepay_handle( int $user_id ): string { return $customer_handle; } + + /** + * Check exist customer in reepay with same handle but another data + * + * @param int $user_id user id to set handle. + * @param string $handle user id to set handle. + */ + public static function have_same_handle( int $user_id, string $handle ): bool { + $user_reepay = reepay()->api( 'reepay_user_register' )->request( + 'GET', + 'https://api.reepay.com/v1/customer/' . $handle, + ); + + if( !empty( $user_reepay ) ){ + $customer = new WC_Customer( $user_id ); + $email = $customer->get_email() ?: $customer->get_billing_email(); + + if($user_reepay['email'] !== $email){ + return true; + } + } + + return false; + } } diff --git a/includes/Api.php b/includes/Api.php index 7fa049ab..39fd593b 100644 --- a/includes/Api.php +++ b/includes/Api.php @@ -11,6 +11,7 @@ use Reepay\Checkout\Gateways\ReepayGateway; use Reepay\Checkout\OrderFlow\InstantSettle; use Reepay\Checkout\OrderFlow\OrderCapture; +use Reepay\Checkout\Actions\ReepayCustomer; use WC_Order; use Reepay\Checkout\OrderFlow\OrderStatuses; use WC_Order_Item; @@ -1079,22 +1080,13 @@ public function get_customer_handle_by_order( $order ) { $order = wc_get_order( $order ); $handle = $this->get_customer_handle( $order ); - if ( ! empty( $handle ) ) { - return $handle; - } - if ( $order->get_customer_id() === 0 ) { + if ( $order->get_customer_id() === 0 && empty( $handle )) { $handle = $order->get_meta( '_reepay_customer' ); - if ( ! empty( $handle ) ) { - return $handle; - } } - $handle = rp_get_customer_handle( $order->get_customer_id() ); - if ( ! empty( $handle ) ) { - $order->add_meta_data( '_reepay_customer', $handle ); - $order->save_meta_data(); - return $handle; + if( empty( $handle ) ){ + $handle = rp_get_customer_handle( $order->get_customer_id() ); } if ( empty( $handle ) ) { @@ -1105,6 +1097,14 @@ public function get_customer_handle_by_order( $order ) { } } + if( ReepayCustomer::have_same_handle( $order->get_customer_id(), $handle ) ){ + $handle = 'cust-' . time(); + $order->add_meta_data( '_reepay_customer', $handle ); + $order->save_meta_data(); + + return $this->get_customer_handle_by_order( $order ); + } + $order->add_meta_data( '_reepay_customer', $handle ); $order->save_meta_data(); diff --git a/includes/Functions/customer.php b/includes/Functions/customer.php index d1c24ce2..1e46702c 100644 --- a/includes/Functions/customer.php +++ b/includes/Functions/customer.php @@ -35,6 +35,14 @@ function rp_get_customer_handle( int $user_id ): string { } } + if( ReepayCustomer::have_same_handle( $user_id, $handle ) ){ + $handle = 'cust-' . time(); + update_user_meta( $user_id, 'reepay_customer_id', $handle ); + + return rp_get_customer_handle( $user_id ); + } + + return $handle; } } diff --git a/includes/Gateways/ReepayGateway.php b/includes/Gateways/ReepayGateway.php index 2387872f..89f901a2 100644 --- a/includes/Gateways/ReepayGateway.php +++ b/includes/Gateways/ReepayGateway.php @@ -1111,7 +1111,8 @@ public function process_payment( $order_id ) { // If here's Subscription or zero payment. if ( ( $have_sub ) && ( abs( $order->get_total() ) < 0.01 || empty( $only_items_lines ) ) ) { - +var_dump($data); +exit; $result = reepay()->api( $this )->recurring( $this->payment_methods, $order, $data, false, $params['button_text'] ); if ( is_wp_error( $result ) ) { From 164accd69c2477e03d33df64c3bed4639259d17a Mon Sep 17 00:00:00 2001 From: "dimaspolohov@yandex.ru" Date: Wed, 15 Nov 2023 14:46:50 +0300 Subject: [PATCH 27/37] Reepay add extra check for exist customer --- includes/Actions/ReepayCustomer.php | 24 ++++++++++++++++++++++++ includes/Api.php | 24 ++++++++++++------------ includes/Functions/customer.php | 8 ++++++++ 3 files changed, 44 insertions(+), 12 deletions(-) diff --git a/includes/Actions/ReepayCustomer.php b/includes/Actions/ReepayCustomer.php index 16c3a32f..35d97c3b 100644 --- a/includes/Actions/ReepayCustomer.php +++ b/includes/Actions/ReepayCustomer.php @@ -58,4 +58,28 @@ public static function set_reepay_handle( int $user_id ): string { return $customer_handle; } + + /** + * Check exist customer in reepay with same handle but another data + * + * @param int $user_id user id to set handle. + * @param string $handle user id to set handle. + */ + public static function have_same_handle( int $user_id, string $handle ): bool { + $user_reepay = reepay()->api( 'reepay_user_register' )->request( + 'GET', + 'https://api.reepay.com/v1/customer/' . $handle, + ); + + if( !empty( $user_reepay ) ){ + $customer = new WC_Customer( $user_id ); + $email = $customer->get_email() ?: $customer->get_billing_email(); + + if($user_reepay['email'] !== $email){ + return true; + } + } + + return false; + } } diff --git a/includes/Api.php b/includes/Api.php index 7fa049ab..39fd593b 100644 --- a/includes/Api.php +++ b/includes/Api.php @@ -11,6 +11,7 @@ use Reepay\Checkout\Gateways\ReepayGateway; use Reepay\Checkout\OrderFlow\InstantSettle; use Reepay\Checkout\OrderFlow\OrderCapture; +use Reepay\Checkout\Actions\ReepayCustomer; use WC_Order; use Reepay\Checkout\OrderFlow\OrderStatuses; use WC_Order_Item; @@ -1079,22 +1080,13 @@ public function get_customer_handle_by_order( $order ) { $order = wc_get_order( $order ); $handle = $this->get_customer_handle( $order ); - if ( ! empty( $handle ) ) { - return $handle; - } - if ( $order->get_customer_id() === 0 ) { + if ( $order->get_customer_id() === 0 && empty( $handle )) { $handle = $order->get_meta( '_reepay_customer' ); - if ( ! empty( $handle ) ) { - return $handle; - } } - $handle = rp_get_customer_handle( $order->get_customer_id() ); - if ( ! empty( $handle ) ) { - $order->add_meta_data( '_reepay_customer', $handle ); - $order->save_meta_data(); - return $handle; + if( empty( $handle ) ){ + $handle = rp_get_customer_handle( $order->get_customer_id() ); } if ( empty( $handle ) ) { @@ -1105,6 +1097,14 @@ public function get_customer_handle_by_order( $order ) { } } + if( ReepayCustomer::have_same_handle( $order->get_customer_id(), $handle ) ){ + $handle = 'cust-' . time(); + $order->add_meta_data( '_reepay_customer', $handle ); + $order->save_meta_data(); + + return $this->get_customer_handle_by_order( $order ); + } + $order->add_meta_data( '_reepay_customer', $handle ); $order->save_meta_data(); diff --git a/includes/Functions/customer.php b/includes/Functions/customer.php index d1c24ce2..1e46702c 100644 --- a/includes/Functions/customer.php +++ b/includes/Functions/customer.php @@ -35,6 +35,14 @@ function rp_get_customer_handle( int $user_id ): string { } } + if( ReepayCustomer::have_same_handle( $user_id, $handle ) ){ + $handle = 'cust-' . time(); + update_user_meta( $user_id, 'reepay_customer_id', $handle ); + + return rp_get_customer_handle( $user_id ); + } + + return $handle; } } From 86d5b6d9c6990bad291534f84109d243d846e162 Mon Sep 17 00:00:00 2001 From: "dimaspolohov@yandex.ru" Date: Wed, 15 Nov 2023 15:35:38 +0300 Subject: [PATCH 28/37] Reepay add extra check for exist customer --- includes/Actions/ReepayCustomer.php | 4 ++-- includes/Functions/customer.php | 7 ------- includes/Gateways/ReepayGateway.php | 3 +-- 3 files changed, 3 insertions(+), 11 deletions(-) diff --git a/includes/Actions/ReepayCustomer.php b/includes/Actions/ReepayCustomer.php index 35d97c3b..22736f72 100644 --- a/includes/Actions/ReepayCustomer.php +++ b/includes/Actions/ReepayCustomer.php @@ -71,9 +71,9 @@ public static function have_same_handle( int $user_id, string $handle ): bool { 'https://api.reepay.com/v1/customer/' . $handle, ); - if( !empty( $user_reepay ) ){ + if( !empty( $user_reepay ) && !is_wp_error( $user_reepay ) ){ $customer = new WC_Customer( $user_id ); - $email = $customer->get_email() ?: $customer->get_billing_email(); + $email = $customer->get_billing_email(); if($user_reepay['email'] !== $email){ return true; diff --git a/includes/Functions/customer.php b/includes/Functions/customer.php index 1e46702c..69b60798 100644 --- a/includes/Functions/customer.php +++ b/includes/Functions/customer.php @@ -35,13 +35,6 @@ function rp_get_customer_handle( int $user_id ): string { } } - if( ReepayCustomer::have_same_handle( $user_id, $handle ) ){ - $handle = 'cust-' . time(); - update_user_meta( $user_id, 'reepay_customer_id', $handle ); - - return rp_get_customer_handle( $user_id ); - } - return $handle; } diff --git a/includes/Gateways/ReepayGateway.php b/includes/Gateways/ReepayGateway.php index 903b7f5d..91b2e03b 100644 --- a/includes/Gateways/ReepayGateway.php +++ b/includes/Gateways/ReepayGateway.php @@ -1019,8 +1019,7 @@ public function process_payment( $order_id ) { // If here's Subscription or zero payment. if ( ( $have_sub ) && ( abs( $order->get_total() ) < 0.01 || empty( $only_items_lines ) ) ) { -var_dump($data); -exit; + $result = reepay()->api( $this )->recurring( $this->payment_methods, $order, $data, false, $params['button_text'] ); if ( is_wp_error( $result ) ) { From 164e82aaf2b01b039fe33d05354adf50f425cbd7 Mon Sep 17 00:00:00 2001 From: "dimaspolohov@yandex.ru" Date: Wed, 15 Nov 2023 15:50:26 +0300 Subject: [PATCH 29/37] Reepay add extra check for exist customer --- includes/Actions/ReepayCustomer.php | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/includes/Actions/ReepayCustomer.php b/includes/Actions/ReepayCustomer.php index 22736f72..14f53806 100644 --- a/includes/Actions/ReepayCustomer.php +++ b/includes/Actions/ReepayCustomer.php @@ -40,7 +40,10 @@ public function user_register( int $user_id ) { public static function set_reepay_handle( int $user_id ): string { $customer = new WC_Customer( $user_id ); - $email = $customer->get_email() ?: $customer->get_billing_email(); + $email = $customer->get_billing_email(); + if(empty( $email ) && !empty( $_POST['billing_email'] )){ + $email = $_POST['billing_email']; + } if ( empty( $email ) ) { return ''; @@ -75,7 +78,11 @@ public static function have_same_handle( int $user_id, string $handle ): bool { $customer = new WC_Customer( $user_id ); $email = $customer->get_billing_email(); - if($user_reepay['email'] !== $email){ + if(empty( $email ) && !empty( $_POST['billing_email'] )){ + $email = $_POST['billing_email']; + } + + if(!empty($email) && $user_reepay['email'] !== $email){ return true; } } From 2ea6d6d2b40d7194a33ea554c184b97a4a0f8473 Mon Sep 17 00:00:00 2001 From: "dimaspolohov@yandex.ru" Date: Wed, 15 Nov 2023 16:05:56 +0300 Subject: [PATCH 30/37] Link card to subscription if zero payment --- includes/Gateways/ReepayGateway.php | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/includes/Gateways/ReepayGateway.php b/includes/Gateways/ReepayGateway.php index 91b2e03b..8541fe8b 100644 --- a/includes/Gateways/ReepayGateway.php +++ b/includes/Gateways/ReepayGateway.php @@ -917,6 +917,18 @@ public function process_payment( $order_id ) { if ( is_wp_error( $result ) ) { throw new Exception( $result->get_error_message(), $result->get_error_code() ); } + + try { + ReepayTokens::assign_payment_token( $order, $token ); + ReepayTokens::save_card_info_to_order( $order, $token->get_token() ); + } catch ( Exception $e ) { + $order->add_order_note( $e->getMessage() ); + + return array( + 'result' => 'failure', + 'message' => $e->getMessage(), + ); + } } $order->payment_complete(); From 4901871408adbb3dc178a64ec03ebeb7f9737072 Mon Sep 17 00:00:00 2001 From: "dimaspolohov@yandex.ru" Date: Thu, 16 Nov 2023 13:51:05 +0300 Subject: [PATCH 31/37] Remove token validation --- includes/Actions/Subscriptions.php | 3 --- 1 file changed, 3 deletions(-) diff --git a/includes/Actions/Subscriptions.php b/includes/Actions/Subscriptions.php index c28bf62b..0118c9b9 100644 --- a/includes/Actions/Subscriptions.php +++ b/includes/Actions/Subscriptions.php @@ -222,9 +222,6 @@ public function add_subscription_payment_meta( array $payment_meta, WC_Subscript */ public function validate_subscription_payment_meta( string $payment_method_id, array $payment_meta, WC_Subscription $subscription ) { if ( in_array( $payment_method_id, self::PAYMENT_METHODS, true ) ) { - if ( empty( $payment_meta['post_meta']['_reepay_token']['value'] ) ) { - throw new Exception( 'A "Billwerk+ Token" value is required.' ); - } $tokens = explode( ',', $payment_meta['post_meta']['_reepay_token']['value'] ); if ( count( $tokens ) > 1 ) { From 6dea2cb44122f470faa7d112330c9aab25913155 Mon Sep 17 00:00:00 2001 From: "dimaspolohov@yandex.ru" Date: Fri, 17 Nov 2023 13:05:46 +0300 Subject: [PATCH 32/37] Remove token validation --- includes/Actions/Subscriptions.php | 2 +- includes/Tokens/ReepayTokens.php | 7 +++++++ 2 files changed, 8 insertions(+), 1 deletion(-) diff --git a/includes/Actions/Subscriptions.php b/includes/Actions/Subscriptions.php index 0118c9b9..ad75a5d3 100644 --- a/includes/Actions/Subscriptions.php +++ b/includes/Actions/Subscriptions.php @@ -221,7 +221,7 @@ public function add_subscription_payment_meta( array $payment_meta, WC_Subscript * @throws Exception If validation error. */ public function validate_subscription_payment_meta( string $payment_method_id, array $payment_meta, WC_Subscription $subscription ) { - if ( in_array( $payment_method_id, self::PAYMENT_METHODS, true ) ) { + if ( in_array( $payment_method_id, self::PAYMENT_METHODS, true ) && !empty( $payment_meta['post_meta']['_reepay_token']['value'] ) ) { $tokens = explode( ',', $payment_meta['post_meta']['_reepay_token']['value'] ); if ( count( $tokens ) > 1 ) { diff --git a/includes/Tokens/ReepayTokens.php b/includes/Tokens/ReepayTokens.php index 4d2a8cdb..3fddf71e 100644 --- a/includes/Tokens/ReepayTokens.php +++ b/includes/Tokens/ReepayTokens.php @@ -147,6 +147,13 @@ public static function add_payment_token_to_order( WC_Order $order, string $reep * @throws Exception If invalid token or order. */ public static function add_payment_token_to_customer( int $customer_id, $card_info ): array { + if(empty($card_info)){ + return array( + 'token' => false, + 'card_info' => $card_info, + ); + } + if ( is_string( $card_info ) ) { $customer_handle = rp_get_customer_handle( $customer_id ); $card_info = reepay()->api( 'tokens' )->get_reepay_cards( $customer_handle, $card_info ); From dd20a709d71fd247aae3001cc09d38d351232a5d Mon Sep 17 00:00:00 2001 From: "dimaspolohov@yandex.ru" Date: Fri, 17 Nov 2023 13:49:12 +0300 Subject: [PATCH 33/37] Fix user handle generation --- includes/Api.php | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/includes/Api.php b/includes/Api.php index 39fd593b..d8a116dc 100644 --- a/includes/Api.php +++ b/includes/Api.php @@ -1085,10 +1085,16 @@ public function get_customer_handle_by_order( $order ) { $handle = $order->get_meta( '_reepay_customer' ); } + if( empty( $handle ) ){ + $handle = get_user_meta( $order->get_customer_id(), 'reepay_customer_id', true ); + return $handle; + } + if( empty( $handle ) ){ $handle = rp_get_customer_handle( $order->get_customer_id() ); } + if ( empty( $handle ) ) { if ( $order->get_customer_id() > 0 ) { $handle = 'customer-' . $order->get_customer_id(); @@ -1099,10 +1105,7 @@ public function get_customer_handle_by_order( $order ) { if( ReepayCustomer::have_same_handle( $order->get_customer_id(), $handle ) ){ $handle = 'cust-' . time(); - $order->add_meta_data( '_reepay_customer', $handle ); - $order->save_meta_data(); - - return $this->get_customer_handle_by_order( $order ); + update_user_meta( $order->get_customer_id(), 'reepay_customer_id', $handle ); } $order->add_meta_data( '_reepay_customer', $handle ); From d0d471359cb053694d7e5106cd32caf9c4956df6 Mon Sep 17 00:00:00 2001 From: "dimaspolohov@yandex.ru" Date: Fri, 17 Nov 2023 14:06:57 +0300 Subject: [PATCH 34/37] v 1.6.1 - Card saving fixes, user creation fixes --- Readme.txt | 1 + reepay-woocommerce-payment.php | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/Readme.txt b/Readme.txt index 1fa45dda..b01d7a3a 100755 --- a/Readme.txt +++ b/Readme.txt @@ -18,6 +18,7 @@ The Billwerk+ Payments plugin extends WooCommerce allowing you to take payments See installation guide right here: https://docu.billwerk.plus/help/en/apps/woocommerce/setup-woocommerce-plugin.html == Changelog == +v 1.6.1 - Card saving fixes, user creation fixes v 1.6.0 - Lots of updates and fixes v 1.5.0 - Billwerk+ version update and thankyou changes v 1.4.73 - Billwerk+ naming changes diff --git a/reepay-woocommerce-payment.php b/reepay-woocommerce-payment.php index 18aff34f..db89dc76 100755 --- a/reepay-woocommerce-payment.php +++ b/reepay-woocommerce-payment.php @@ -4,7 +4,7 @@ * Description: Get a plug-n-play payment solution for WooCommerce, that is easy to use, highly secure and is built to maximize the potential of your e-commerce. * Author: Billwerk+ * Author URI: http://billwerk.plus - * Version: 1.6.0 + * Version: 1.6.1 * Text Domain: reepay-checkout-gateway * Domain Path: /languages * WC requires at least: 3.0.0 From cd2d9b09217bd05fc6bc66eae1e236f0a05381a2 Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Fri, 17 Nov 2023 14:16:04 +0300 Subject: [PATCH 35/37] phpcs autofix --- includes/Actions/ReepayCustomer.php | 12 ++++++------ includes/Actions/Subscriptions.php | 2 +- includes/Api.php | 9 ++++----- includes/Functions/customer.php | 1 - includes/Functions/hpos.php | 2 +- includes/Tokens/ReepayTokens.php | 2 +- 6 files changed, 13 insertions(+), 15 deletions(-) diff --git a/includes/Actions/ReepayCustomer.php b/includes/Actions/ReepayCustomer.php index 14f53806..ded88628 100644 --- a/includes/Actions/ReepayCustomer.php +++ b/includes/Actions/ReepayCustomer.php @@ -41,7 +41,7 @@ public static function set_reepay_handle( int $user_id ): string { $customer = new WC_Customer( $user_id ); $email = $customer->get_billing_email(); - if(empty( $email ) && !empty( $_POST['billing_email'] )){ + if ( empty( $email ) && ! empty( $_POST['billing_email'] ) ) { $email = $_POST['billing_email']; } @@ -65,7 +65,7 @@ public static function set_reepay_handle( int $user_id ): string { /** * Check exist customer in reepay with same handle but another data * - * @param int $user_id user id to set handle. + * @param int $user_id user id to set handle. * @param string $handle user id to set handle. */ public static function have_same_handle( int $user_id, string $handle ): bool { @@ -74,15 +74,15 @@ public static function have_same_handle( int $user_id, string $handle ): bool { 'https://api.reepay.com/v1/customer/' . $handle, ); - if( !empty( $user_reepay ) && !is_wp_error( $user_reepay ) ){ + if ( ! empty( $user_reepay ) && ! is_wp_error( $user_reepay ) ) { $customer = new WC_Customer( $user_id ); - $email = $customer->get_billing_email(); + $email = $customer->get_billing_email(); - if(empty( $email ) && !empty( $_POST['billing_email'] )){ + if ( empty( $email ) && ! empty( $_POST['billing_email'] ) ) { $email = $_POST['billing_email']; } - if(!empty($email) && $user_reepay['email'] !== $email){ + if ( ! empty( $email ) && $user_reepay['email'] !== $email ) { return true; } } diff --git a/includes/Actions/Subscriptions.php b/includes/Actions/Subscriptions.php index ad75a5d3..d279bd80 100644 --- a/includes/Actions/Subscriptions.php +++ b/includes/Actions/Subscriptions.php @@ -221,7 +221,7 @@ public function add_subscription_payment_meta( array $payment_meta, WC_Subscript * @throws Exception If validation error. */ public function validate_subscription_payment_meta( string $payment_method_id, array $payment_meta, WC_Subscription $subscription ) { - if ( in_array( $payment_method_id, self::PAYMENT_METHODS, true ) && !empty( $payment_meta['post_meta']['_reepay_token']['value'] ) ) { + if ( in_array( $payment_method_id, self::PAYMENT_METHODS, true ) && ! empty( $payment_meta['post_meta']['_reepay_token']['value'] ) ) { $tokens = explode( ',', $payment_meta['post_meta']['_reepay_token']['value'] ); if ( count( $tokens ) > 1 ) { diff --git a/includes/Api.php b/includes/Api.php index d8a116dc..2ac2414b 100644 --- a/includes/Api.php +++ b/includes/Api.php @@ -1081,20 +1081,19 @@ public function get_customer_handle_by_order( $order ) { $handle = $this->get_customer_handle( $order ); - if ( $order->get_customer_id() === 0 && empty( $handle )) { + if ( $order->get_customer_id() === 0 && empty( $handle ) ) { $handle = $order->get_meta( '_reepay_customer' ); } - if( empty( $handle ) ){ + if ( empty( $handle ) ) { $handle = get_user_meta( $order->get_customer_id(), 'reepay_customer_id', true ); return $handle; } - if( empty( $handle ) ){ + if ( empty( $handle ) ) { $handle = rp_get_customer_handle( $order->get_customer_id() ); } - if ( empty( $handle ) ) { if ( $order->get_customer_id() > 0 ) { $handle = 'customer-' . $order->get_customer_id(); @@ -1103,7 +1102,7 @@ public function get_customer_handle_by_order( $order ) { } } - if( ReepayCustomer::have_same_handle( $order->get_customer_id(), $handle ) ){ + if ( ReepayCustomer::have_same_handle( $order->get_customer_id(), $handle ) ) { $handle = 'cust-' . time(); update_user_meta( $order->get_customer_id(), 'reepay_customer_id', $handle ); } diff --git a/includes/Functions/customer.php b/includes/Functions/customer.php index 69b60798..d1c24ce2 100644 --- a/includes/Functions/customer.php +++ b/includes/Functions/customer.php @@ -35,7 +35,6 @@ function rp_get_customer_handle( int $user_id ): string { } } - return $handle; } } diff --git a/includes/Functions/hpos.php b/includes/Functions/hpos.php index 578d5808..16a6d7af 100644 --- a/includes/Functions/hpos.php +++ b/includes/Functions/hpos.php @@ -15,7 +15,7 @@ * @return bool */ function rp_hpos_enabled(): bool { - if(class_exists(OrderUtil::class)){ + if ( class_exists( OrderUtil::class ) ) { return OrderUtil::custom_orders_table_usage_is_enabled(); } return false; diff --git a/includes/Tokens/ReepayTokens.php b/includes/Tokens/ReepayTokens.php index 3fddf71e..d40375fd 100644 --- a/includes/Tokens/ReepayTokens.php +++ b/includes/Tokens/ReepayTokens.php @@ -147,7 +147,7 @@ public static function add_payment_token_to_order( WC_Order $order, string $reep * @throws Exception If invalid token or order. */ public static function add_payment_token_to_customer( int $customer_id, $card_info ): array { - if(empty($card_info)){ + if ( empty( $card_info ) ) { return array( 'token' => false, 'card_info' => $card_info, From 9b59c1d98fe3e532490f8d1fac667b7738011d4b Mon Sep 17 00:00:00 2001 From: "dimaspolohov@yandex.ru" Date: Fri, 17 Nov 2023 14:40:51 +0300 Subject: [PATCH 36/37] Testing fixes --- includes/Actions/ReepayCustomer.php | 4 ++++ tests/unit/tokens/ReepayTokensTest.php | 12 +++++++++--- 2 files changed, 13 insertions(+), 3 deletions(-) diff --git a/includes/Actions/ReepayCustomer.php b/includes/Actions/ReepayCustomer.php index 14f53806..4b264b25 100644 --- a/includes/Actions/ReepayCustomer.php +++ b/includes/Actions/ReepayCustomer.php @@ -45,6 +45,10 @@ public static function set_reepay_handle( int $user_id ): string { $email = $_POST['billing_email']; } + if( empty( $email ) ){ + $email = $customer->get_email(); + } + if ( empty( $email ) ) { return ''; } diff --git a/tests/unit/tokens/ReepayTokensTest.php b/tests/unit/tokens/ReepayTokensTest.php index a96c6526..7622b61b 100644 --- a/tests/unit/tokens/ReepayTokensTest.php +++ b/tests/unit/tokens/ReepayTokensTest.php @@ -83,9 +83,15 @@ public function test_add_payment_token_unsaved() { 'masked_card' => '457111XXXXXX2077', 'card_type' => '' // Empty 'card_type' value cause an exception. ) ); - $this->expectException( Exception::class ); - $this->expectExceptionMessage( 'Invalid or missing payment token fields.' ); - ReepayTokens::add_payment_token_to_customer( 0, '' ); + + $this->assertSame( + array( + 'token' => false, + 'card_info' => '', + ), + ReepayTokens::add_payment_token_to_customer( 0, '' ) + ); + ; } public function test_add_payment_token_ms() { From d23aac48162fd0a2f8a5749e7d7ed70377a235ca Mon Sep 17 00:00:00 2001 From: daniel21703 Date: Fri, 17 Nov 2023 14:51:21 +0300 Subject: [PATCH 37/37] phpcs autofix --- includes/Actions/ReepayCustomer.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/includes/Actions/ReepayCustomer.php b/includes/Actions/ReepayCustomer.php index 0512057e..a5f5ee90 100644 --- a/includes/Actions/ReepayCustomer.php +++ b/includes/Actions/ReepayCustomer.php @@ -45,7 +45,7 @@ public static function set_reepay_handle( int $user_id ): string { $email = $_POST['billing_email']; } - if( empty( $email ) ){ + if ( empty( $email ) ) { $email = $customer->get_email(); }