From 99ca470d3f493d3334a038dff669eb53b6e8c969 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20H=C3=BCsken?= Date: Fri, 31 Jan 2025 08:25:03 +0100 Subject: [PATCH] Moved code for payment process order to subscriptions module by adding a new filter --- modules/ppcp-applepay/src/ApplePayGateway.php | 15 +++++++- modules/ppcp-axo/src/Gateway/AxoGateway.php | 13 ++++++- .../ppcp-googlepay/src/GooglePayGateway.php | 15 +++++++- .../src/PayPalSubscriptionsModule.php | 38 +++++++++++++++++++ .../src/Gateway/CardButtonGateway.php | 13 ++++++- .../src/Gateway/CreditCardGateway.php | 13 ++++++- .../src/Gateway/PayPalGateway.php | 35 ++++++----------- .../src/Processor/OrderMetaTrait.php | 2 +- .../Processor/TransactionIdHandlingTrait.php | 4 +- .../src/Handler/CheckoutOrderApproved.php | 13 ++++++- 10 files changed, 127 insertions(+), 34 deletions(-) diff --git a/modules/ppcp-applepay/src/ApplePayGateway.php b/modules/ppcp-applepay/src/ApplePayGateway.php index fbbdac900..da80dd488 100644 --- a/modules/ppcp-applepay/src/ApplePayGateway.php +++ b/modules/ppcp-applepay/src/ApplePayGateway.php @@ -180,11 +180,22 @@ class ApplePayGateway extends WC_Payment_Gateway { ); } - do_action( 'woocommerce_paypal_payments_before_process_order', $wc_order ); + do_action_deprecated('woocommerce_paypal_payments_before_process_order', [ $wc_order ], '2.9.7', 'woocommerce_paypal_payments_before_order_process', __( 'Usage of this action is deprecated. Please use the filter woocommerce_paypal_payments_before_order_process instead. ', 'woocommerce-paypal-payments' ) ); try { try { - $this->order_processor->process( $wc_order ); + /** + * This filter controls if the method 'precess()' from OrderProcessor will be called. + * So you can implement your own for example on subscriptions + * + * - true bool controls execution of 'OrderProcessor::precess()' + * @var $this \WC_Payment_Gateway + * @var $wc_order \WC_Order + */ + $process = apply_filters( 'woocommerce_paypal_payments_before_order_process', true, $this, $wc_order ); + if ( $process ) { + $this->order_processor->process( $wc_order ); + } do_action( 'woocommerce_paypal_payments_before_handle_payment_success', $wc_order ); diff --git a/modules/ppcp-axo/src/Gateway/AxoGateway.php b/modules/ppcp-axo/src/Gateway/AxoGateway.php index cd0ec8579..7390df485 100644 --- a/modules/ppcp-axo/src/Gateway/AxoGateway.php +++ b/modules/ppcp-axo/src/Gateway/AxoGateway.php @@ -253,7 +253,18 @@ class AxoGateway extends WC_Payment_Gateway { $order = $this->create_paypal_order( $wc_order, $token ); - $this->order_processor->process_captured_and_authorized( $wc_order, $order ); + /** + * This filter controls if the method 'precess()' from OrderProcessor will be called. + * So you can implement your own for example on subscriptions + * + * - true bool controls execution of 'OrderProcessor::precess()' + * @var $this \WC_Payment_Gateway + * @var $wc_order \WC_Order + */ + $process = apply_filters( 'woocommerce_paypal_payments_before_order_process', true, $this, $wc_order ); + if ( $process ) { + $this->order_processor->process_captured_and_authorized( $wc_order, $order ); + } } catch ( Exception $exception ) { return $this->handle_payment_failure( $wc_order, $exception ); } diff --git a/modules/ppcp-googlepay/src/GooglePayGateway.php b/modules/ppcp-googlepay/src/GooglePayGateway.php index 16fe5f690..29e8fae0b 100644 --- a/modules/ppcp-googlepay/src/GooglePayGateway.php +++ b/modules/ppcp-googlepay/src/GooglePayGateway.php @@ -189,11 +189,22 @@ class GooglePayGateway extends WC_Payment_Gateway { } //phpcs:enable WordPress.Security.NonceVerification.Recommended - do_action( 'woocommerce_paypal_payments_before_process_order', $wc_order ); + do_action_deprecated('woocommerce_paypal_payments_before_process_order', [ $wc_order ], '2.9.7', 'woocommerce_paypal_payments_before_order_process', __( 'Usage of this action is deprecated. Please use the filter woocommerce_paypal_payments_before_order_process instead. ', 'woocommerce-paypal-payments' ) ); try { try { - $this->order_processor->process( $wc_order ); + /** + * This filter controls if the method 'precess()' from OrderProcessor will be called. + * So you can implement your own for example on subscriptions + * + * - true bool controls execution of 'OrderProcessor::precess()' + * @var $this \WC_Payment_Gateway + * @var $wc_order \WC_Order + */ + $process = apply_filters( 'woocommerce_paypal_payments_before_order_process', true, $this, $wc_order ); + if ( $process ) { + $this->order_processor->process( $wc_order ); + } do_action( 'woocommerce_paypal_payments_before_handle_payment_success', $wc_order ); diff --git a/modules/ppcp-paypal-subscriptions/src/PayPalSubscriptionsModule.php b/modules/ppcp-paypal-subscriptions/src/PayPalSubscriptionsModule.php index 48c3a71af..09148543b 100644 --- a/modules/ppcp-paypal-subscriptions/src/PayPalSubscriptionsModule.php +++ b/modules/ppcp-paypal-subscriptions/src/PayPalSubscriptionsModule.php @@ -28,6 +28,7 @@ use WooCommerce\PayPalCommerce\Vendor\Inpsyde\Modularity\Module\ModuleClassNameI use WooCommerce\PayPalCommerce\Vendor\Inpsyde\Modularity\Module\ServiceModule; use WooCommerce\PayPalCommerce\Vendor\Psr\Container\ContainerInterface; use WooCommerce\PayPalCommerce\WcGateway\Exception\NotFoundException; +use WooCommerce\PayPalCommerce\WcGateway\Gateway\PayPalGateway; use WooCommerce\PayPalCommerce\WcGateway\Settings\Settings; use WooCommerce\PayPalCommerce\WcSubscriptions\Helper\SubscriptionHelper; use WP_Post; @@ -56,6 +57,43 @@ class PayPalSubscriptionsModule implements ServiceModule, ExtendingModule, Execu * {@inheritDoc} */ public function run( ContainerInterface $c ): bool { + + add_filter( + 'woocommerce_paypal_payments_before_order_process', + function ( bool $process, \WC_Payment_Gateway $gateway, \WC_Order $wc_order ) use ( $c ) { + if ( ! $gateway instanceof PayPalGateway || $gateway::ID !== 'ppcp-gateway' ) { + return $process; + } + + $paypal_subscription_id = \WC()->session->get( 'ppcp_subscription_id' ) ?? ''; + if ( ! $paypal_subscription_id ) { + return $process; + } + + $order = $c->get( 'session.handler' )->order(); + $gateway->add_paypal_meta( $wc_order, $order, $c->get( 'onboarding.environment' ) ); + + $subscriptions = function_exists( 'wcs_get_subscriptions_for_order' ) ? wcs_get_subscriptions_for_order( $wc_order ) : array(); + foreach ( $subscriptions as $subscription ) { + $subscription->update_meta_data( 'ppcp_subscription', $paypal_subscription_id ); + $subscription->save(); + + $subscription->add_order_note( "PayPal subscription {$paypal_subscription_id} added." ); + } + + $transaction_id = $gateway->get_paypal_order_transaction_id( $order ); + if ( $transaction_id ) { + $gateway->update_transaction_id( $transaction_id, $wc_order, $c->get( 'woocommerce.logger.woocommerce' ) ); + } + + $wc_order->payment_complete(); + + return false; + }, + 10, + 3 + ); + add_action( 'save_post', /** diff --git a/modules/ppcp-wc-gateway/src/Gateway/CardButtonGateway.php b/modules/ppcp-wc-gateway/src/Gateway/CardButtonGateway.php index ffb0fe55c..feec7db5b 100644 --- a/modules/ppcp-wc-gateway/src/Gateway/CardButtonGateway.php +++ b/modules/ppcp-wc-gateway/src/Gateway/CardButtonGateway.php @@ -295,7 +295,18 @@ class CardButtonGateway extends \WC_Payment_Gateway { try { try { - $this->order_processor->process( $wc_order ); + /** + * This filter controls if the method 'precess()' from OrderProcessor will be called. + * So you can implement your own for example on subscriptions + * + * - true bool controls execution of 'OrderProcessor::precess()' + * @var $this \WC_Payment_Gateway + * @var $wc_order \WC_Order + */ + $process = apply_filters( 'woocommerce_paypal_payments_before_order_process', true, $this, $wc_order ); + if ( $process ) { + $this->order_processor->process( $wc_order ); + } do_action( 'woocommerce_paypal_payments_before_handle_payment_success', $wc_order ); diff --git a/modules/ppcp-wc-gateway/src/Gateway/CreditCardGateway.php b/modules/ppcp-wc-gateway/src/Gateway/CreditCardGateway.php index a5e897548..e5420a65b 100644 --- a/modules/ppcp-wc-gateway/src/Gateway/CreditCardGateway.php +++ b/modules/ppcp-wc-gateway/src/Gateway/CreditCardGateway.php @@ -523,7 +523,18 @@ class CreditCardGateway extends \WC_Payment_Gateway_CC { //phpcs:enable WordPress.Security.NonceVerification.Recommended try { - $this->order_processor->process( $wc_order ); + /** + * This filter controls if the method 'precess()' from OrderProcessor will be called. + * So you can implement your own for example on subscriptions + * + * - true bool controls execution of 'OrderProcessor::precess()' + * @var $this \WC_Payment_Gateway + * @var $wc_order \WC_Order + */ + $process = apply_filters( 'woocommerce_paypal_payments_before_order_process', true, $this, $wc_order ); + if ( $process ) { + $this->order_processor->process( $wc_order ); + } do_action( 'woocommerce_paypal_payments_before_handle_payment_success', $wc_order ); diff --git a/modules/ppcp-wc-gateway/src/Gateway/PayPalGateway.php b/modules/ppcp-wc-gateway/src/Gateway/PayPalGateway.php index 5ffbeec9d..fc7a06c67 100644 --- a/modules/ppcp-wc-gateway/src/Gateway/PayPalGateway.php +++ b/modules/ppcp-wc-gateway/src/Gateway/PayPalGateway.php @@ -625,30 +625,19 @@ class PayPalGateway extends \WC_Payment_Gateway { //phpcs:enable WordPress.Security.NonceVerification.Recommended try { - $paypal_subscription_id = WC()->session->get( 'ppcp_subscription_id' ) ?? ''; - if ( $paypal_subscription_id ) { - $order = $this->session_handler->order(); - $this->add_paypal_meta( $wc_order, $order, $this->environment ); - - $subscriptions = function_exists( 'wcs_get_subscriptions_for_order' ) ? wcs_get_subscriptions_for_order( $order_id ) : array(); - foreach ( $subscriptions as $subscription ) { - $subscription->update_meta_data( 'ppcp_subscription', $paypal_subscription_id ); - $subscription->save(); - - $subscription->add_order_note( "PayPal subscription {$paypal_subscription_id} added." ); - } - - $transaction_id = $this->get_paypal_order_transaction_id( $order ); - if ( $transaction_id ) { - $this->update_transaction_id( $transaction_id, $wc_order ); - } - - $wc_order->payment_complete(); - - return $this->handle_payment_success( $wc_order ); - } try { - $this->order_processor->process( $wc_order ); + /** + * This filter controls if the method 'precess()' from OrderProcessor will be called. + * So you can implement your own for example on subscriptions + * + * - true bool controls execution of 'OrderProcessor::precess()' + * @var $this \WC_Payment_Gateway + * @var $wc_order \WC_Order + */ + $process = apply_filters( 'woocommerce_paypal_payments_before_order_process', true, $this, $wc_order ); + if ( $process ) { + $this->order_processor->process( $wc_order ); + } do_action( 'woocommerce_paypal_payments_before_handle_payment_success', $wc_order ); diff --git a/modules/ppcp-wc-gateway/src/Processor/OrderMetaTrait.php b/modules/ppcp-wc-gateway/src/Processor/OrderMetaTrait.php index 62a80456a..7af20ce16 100644 --- a/modules/ppcp-wc-gateway/src/Processor/OrderMetaTrait.php +++ b/modules/ppcp-wc-gateway/src/Processor/OrderMetaTrait.php @@ -28,7 +28,7 @@ trait OrderMetaTrait { * @param Environment $environment The environment. * @param OrderTransient|null $order_transient The order transient helper. */ - protected function add_paypal_meta( + public function add_paypal_meta( WC_Order $wc_order, Order $order, Environment $environment, diff --git a/modules/ppcp-wc-gateway/src/Processor/TransactionIdHandlingTrait.php b/modules/ppcp-wc-gateway/src/Processor/TransactionIdHandlingTrait.php index c6e666176..1b0b4c0f0 100644 --- a/modules/ppcp-wc-gateway/src/Processor/TransactionIdHandlingTrait.php +++ b/modules/ppcp-wc-gateway/src/Processor/TransactionIdHandlingTrait.php @@ -28,7 +28,7 @@ trait TransactionIdHandlingTrait { * * @return bool */ - protected function update_transaction_id( + public function update_transaction_id( string $transaction_id, WC_Order $wc_order, LoggerInterface $logger = null @@ -67,7 +67,7 @@ trait TransactionIdHandlingTrait { * * @return string|null */ - protected function get_paypal_order_transaction_id( Order $order ): ?string { + public function get_paypal_order_transaction_id( Order $order ): ?string { $purchase_unit = $order->purchase_units()[0] ?? null; if ( ! $purchase_unit ) { return null; diff --git a/modules/ppcp-webhooks/src/Handler/CheckoutOrderApproved.php b/modules/ppcp-webhooks/src/Handler/CheckoutOrderApproved.php index d93ca5b4c..4bb80c524 100644 --- a/modules/ppcp-webhooks/src/Handler/CheckoutOrderApproved.php +++ b/modules/ppcp-webhooks/src/Handler/CheckoutOrderApproved.php @@ -230,7 +230,18 @@ class CheckoutOrderApproved implements RequestHandler { } try { - $this->order_processor->process( $wc_order ); + /** + * This filter controls if the method 'precess()' from OrderProcessor will be called. + * So you can implement your own for example on subscriptions + * + * - true bool controls execution of 'OrderProcessor::precess()' + * @var $this \WC_Payment_Gateway + * @var $wc_order \WC_Order + */ + $process = apply_filters( 'woocommerce_paypal_payments_before_order_process', true, $this, $wc_order ); + if ( $process ) { + $this->order_processor->process( $wc_order ); + } } catch ( RuntimeException $exception ) { return $this->failure_response( sprintf(