Commit 203c546b78 for woocommerce
commit 203c546b7841e54b1298e21361ef192308f3546a
Author: Mayisha <33387139+Mayisha@users.noreply.github.com>
Date: Sat Dec 27 00:45:36 2025 +0600
PayPal Standard Refactor 2: Move helper file under src folder (#62596)
* create paypal standard helper class under includes
* deprecate old helper class
* use the new helper class in gateway
* move test file
* add tests for update_addresses_in_order
* Add changefile(s) from automation for the following project(s): woocommerce
* fix lint
* fix phpstan
* update baseline
* address backward compatibility suggestion
* address bc comment about return type
* remove duplicate test
diff --git a/plugins/woocommerce/changelog/62596-refactor-paypal-standard-2-helper b/plugins/woocommerce/changelog/62596-refactor-paypal-standard-2-helper
new file mode 100644
index 0000000000..9d7583b405
--- /dev/null
+++ b/plugins/woocommerce/changelog/62596-refactor-paypal-standard-2-helper
@@ -0,0 +1,4 @@
+Significance: patch
+Type: dev
+
+Deprecate WC_Gateway_Paypal_Helper class in favor of Automattic\WooCommerce\Gateways\PayPal\Helper.
\ No newline at end of file
diff --git a/plugins/woocommerce/includes/gateways/paypal/class-wc-gateway-paypal.php b/plugins/woocommerce/includes/gateways/paypal/class-wc-gateway-paypal.php
index ca222b51d5..456b5dbc47 100644
--- a/plugins/woocommerce/includes/gateways/paypal/class-wc-gateway-paypal.php
+++ b/plugins/woocommerce/includes/gateways/paypal/class-wc-gateway-paypal.php
@@ -14,15 +14,12 @@ use Automattic\Jetpack\Constants;
use Automattic\WooCommerce\Enums\PaymentGatewayFeature;
use Automattic\Jetpack\Connection\Manager as Jetpack_Connection_Manager;
use Automattic\WooCommerce\Gateways\PayPal\Constants as PayPalConstants;
+use Automattic\WooCommerce\Gateways\PayPal\Helper as PayPalHelper;
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
-if ( ! class_exists( 'WC_Gateway_Paypal_Helper' ) ) {
- require_once __DIR__ . '/includes/class-wc-gateway-paypal-helper.php';
-}
-
if ( ! class_exists( 'WC_Gateway_Paypal_Buttons' ) ) {
require_once __DIR__ . '/class-wc-gateway-paypal-buttons.php';
}
@@ -278,7 +275,7 @@ class WC_Gateway_Paypal extends WC_Payment_Gateway {
$paypal_order_details = $paypal_request->get_paypal_order_details( $paypal_order_id );
// Update the addresses in the order with the addresses from the PayPal order details.
- WC_Gateway_Paypal_Helper::update_addresses_in_order( $order, $paypal_order_details );
+ PayPalHelper::update_addresses_in_order( $order, $paypal_order_details );
} catch ( Exception $e ) {
self::log( 'Error updating addresses for order #' . $order_id . ': ' . $e->getMessage(), 'error' );
$order->update_meta_data( '_paypal_addresses_updated', 'no' );
@@ -310,7 +307,7 @@ class WC_Gateway_Paypal extends WC_Payment_Gateway {
*/
$use_orders_v2 = apply_filters(
'woocommerce_paypal_use_orders_v2',
- WC_Gateway_Paypal_Helper::is_orders_v2_migration_eligible()
+ PayPalHelper::is_orders_v2_migration_eligible()
);
// If the conditions are met, but there is an override to not use Orders v2,
@@ -933,7 +930,7 @@ class WC_Gateway_Paypal extends WC_Payment_Gateway {
*/
$use_orders_v2 = apply_filters(
'woocommerce_paypal_use_orders_v2',
- WC_Gateway_Paypal_Helper::is_orders_v2_migration_eligible()
+ PayPalHelper::is_orders_v2_migration_eligible()
);
// If the conditions are met, but there is an override to not use Orders v2,
diff --git a/plugins/woocommerce/includes/gateways/paypal/includes/class-wc-gateway-paypal-helper.php b/plugins/woocommerce/includes/gateways/paypal/includes/class-wc-gateway-paypal-helper.php
index 58212c0fc3..4ca777f86b 100644
--- a/plugins/woocommerce/includes/gateways/paypal/includes/class-wc-gateway-paypal-helper.php
+++ b/plugins/woocommerce/includes/gateways/paypal/includes/class-wc-gateway-paypal-helper.php
@@ -2,6 +2,7 @@
/**
* PayPal Helper Class
*
+ * @deprecated 10.5.0 Use Automattic\WooCommerce\Gateways\PayPal\Helper instead. This class will be removed in 11.0.0.
* @package WooCommerce\Gateways
*/
@@ -11,47 +12,42 @@ if ( ! defined( 'ABSPATH' ) ) {
exit;
}
+use Automattic\WooCommerce\Gateways\PayPal\Helper as PayPalHelper;
+
if ( ! class_exists( 'WC_Gateway_Paypal_Constants' ) ) {
require_once __DIR__ . '/class-wc-gateway-paypal-constants.php';
}
/**
* Helper for PayPal gateway.
+ *
+ * @deprecated 10.5.0 Use Automattic\WooCommerce\Gateways\PayPal\Helper instead. This class will be removed in 11.0.0.
*/
class WC_Gateway_Paypal_Helper {
/**
* Check if the PayPal gateway is enabled.
*
+ * @deprecated 10.5.0 Use Automattic\WooCommerce\Gateways\PayPal\Helper::is_paypal_gateway_available() instead.
* @return bool
*/
public static function is_paypal_gateway_available() {
- $settings = get_option( 'woocommerce_paypal_settings', array() );
- $enabled = isset( $settings['enabled'] ) && 'yes' === $settings['enabled'];
- $should_load = isset( $settings['_should_load'] ) && 'yes' === $settings['_should_load'];
- return $enabled && $should_load;
+ return PayPalHelper::is_paypal_gateway_available();
}
/**
* Check if the merchant is eligible for migration from WPS to PPCP.
*
+ * @deprecated 10.5.0 Use Automattic\WooCommerce\Gateways\PayPal\Helper::is_orders_v2_migration_eligible() instead.
* @return bool
*/
public static function is_orders_v2_migration_eligible() {
- $settings = get_option( 'woocommerce_paypal_settings', array() );
-
- // If API keys are set, the merchant is not eligible for migration
- // as they may be using features that cannot be seamlessly migrated.
- $is_test_mode = isset( $settings['testmode'] ) && 'yes' === $settings['testmode'];
- $api_username = $is_test_mode ? ( $settings['sandbox_api_username'] ?? null ) : ( $settings['api_username'] ?? null );
- $api_password = $is_test_mode ? ( $settings['sandbox_api_password'] ?? null ) : ( $settings['api_password'] ?? null );
- $api_signature = $is_test_mode ? ( $settings['sandbox_api_signature'] ?? null ) : ( $settings['api_signature'] ?? null );
-
- return empty( $api_username ) && empty( $api_password ) && empty( $api_signature );
+ return PayPalHelper::is_orders_v2_migration_eligible();
}
/**
* Get the WC order from the PayPal custom ID.
*
+ * @deprecated 10.5.0 Use Automattic\WooCommerce\Gateways\PayPal\Helper::get_wc_order_from_paypal_custom_id() instead.
* @param string $custom_id The custom ID string from the PayPal order.
* @return WC_Order|null
*/
@@ -60,28 +56,7 @@ class WC_Gateway_Paypal_Helper {
return null;
}
- $data = json_decode( $custom_id, true );
- if ( ! is_array( $data ) ) {
- return null;
- }
-
- $order_id = $data['order_id'] ?? null;
- if ( ! $order_id ) {
- return null;
- }
-
- $order = wc_get_order( $order_id );
- if ( ! $order ) {
- return null;
- }
-
- // Validate the order key.
- $order_key = $data['order_key'] ?? null;
- if ( $order_key !== $order->get_order_key() ) {
- return null;
- }
-
- return $order;
+ return PayPalHelper::get_wc_order_from_paypal_custom_id( (string) $custom_id );
}
/**
@@ -90,126 +65,34 @@ class WC_Gateway_Paypal_Helper {
* This function recursively traverses the data array and redacts sensitive information
* while preserving the structure for debugging purposes.
*
+ * @deprecated 10.5.0 Use Automattic\WooCommerce\Gateways\PayPal\Helper::redact_data() instead.
* @param mixed $data The data to remove PII from (array, string, or other types).
* @return mixed The data with PII redacted.
*/
public static function redact_data( $data ) {
- if ( ! is_array( $data ) ) {
- return $data;
- }
-
- $redacted_data = array();
-
- foreach ( $data as $key => $value ) {
- // Skip redacting the payee information as it belongs to the store merchant.
- if ( 'payee' === $key ) {
- $redacted_data[ $key ] = $value;
- continue;
- }
- // Mask the email address.
- if ( 'email_address' === $key || 'email' === $key ) {
- $redacted_data[ $key ] = self::mask_email( $value );
- continue;
- }
-
- if ( is_array( $value ) ) {
- $redacted_data[ $key ] = self::redact_data( $value );
- } elseif ( in_array( $key, WC_Gateway_Paypal_Constants::FIELDS_TO_REDACT, true ) ) {
- $redacted_data[ $key ] = '[redacted]';
- } else {
- // Keep non-PII data as is.
- $redacted_data[ $key ] = $value;
- }
- }
-
- return $redacted_data;
+ return PayPalHelper::redact_data( $data );
}
/**
* Mask email address before @ keeping the full domain.
*
+ * @deprecated 10.5.0 Use Automattic\WooCommerce\Gateways\PayPal\Helper::mask_email() instead.
* @param string $email The email address to mask.
* @return string The masked email address or original input if invalid.
*/
public static function mask_email( $email ) {
- if ( ! is_string( $email ) || empty( $email ) ) {
- return $email;
- }
-
- $parts = explode( '@', $email, 2 );
- if ( count( $parts ) !== 2 || empty( $parts[0] ) || empty( $parts[1] ) ) {
- return $email;
- }
- list( $local, $domain ) = $parts;
-
- if ( strlen( $local ) <= 3 ) {
- $masked_local = str_repeat( '*', strlen( $local ) );
- } else {
- $masked_local = substr( $local, 0, 2 )
- . str_repeat( '*', max( 1, strlen( $local ) - 3 ) )
- . substr( $local, -1 );
- }
-
- return $masked_local . '@' . $domain;
+ return PayPalHelper::mask_email( (string) $email );
}
/**
* Update the addresses in the order.
*
+ * @deprecated 10.5.0 Use Automattic\WooCommerce\Gateways\PayPal\Helper::update_addresses_in_order() instead.
* @param WC_Order|null $order The order object.
* @param array $paypal_order_details The PayPal order details.
* @return void
*/
public static function update_addresses_in_order( ?WC_Order $order, array $paypal_order_details ): void {
- if ( empty( $order ) || empty( $paypal_order_details ) ) {
- return;
- }
-
- // Bail early if '_paypal_addresses_updated' is 'yes', meaning the addresses update already have been successful.
- if ( 'yes' === $order->get_meta( '_paypal_addresses_updated', true ) ) {
- return;
- }
-
- // Update the shipping information.
- $full_name = $paypal_order_details['purchase_units'][0]['shipping']['name']['full_name'] ?? '';
- if ( ! empty( $full_name ) ) {
- $name_parts = explode( ' ', $full_name, 2 );
- $approximate_first_name = $name_parts[0] ?? '';
- $approximate_last_name = isset( $name_parts[1] ) ? $name_parts[1] : '';
- $order->set_shipping_first_name( $approximate_first_name );
- $order->set_shipping_last_name( $approximate_last_name );
- }
-
- $shipping_address = $paypal_order_details['purchase_units'][0]['shipping']['address'] ?? array();
- if ( ! empty( $shipping_address ) ) {
- $order->set_shipping_country( $shipping_address['country_code'] ?? '' );
- $order->set_shipping_postcode( $shipping_address['postal_code'] ?? '' );
- $order->set_shipping_state( $shipping_address['admin_area_1'] ?? '' );
- $order->set_shipping_city( $shipping_address['admin_area_2'] ?? '' );
- $order->set_shipping_address_1( $shipping_address['address_line_1'] ?? '' );
- $order->set_shipping_address_2( $shipping_address['address_line_2'] ?? '' );
- }
-
- // Update the billing information.
- $full_name = $paypal_order_details['payer']['name'] ?? array();
- $email = $paypal_order_details['payer']['email_address'] ?? '';
- if ( ! empty( $full_name ) ) {
- $order->set_billing_first_name( $full_name['given_name'] ?? '' );
- $order->set_billing_last_name( $full_name['surname'] ?? '' );
- $order->set_billing_email( $email );
- }
-
- $billing_address = $paypal_order_details['payer']['address'] ?? array();
- if ( ! empty( $billing_address ) ) {
- $order->set_billing_country( $billing_address['country_code'] ?? '' );
- $order->set_billing_postcode( $billing_address['postal_code'] ?? '' );
- $order->set_billing_state( $billing_address['admin_area_1'] ?? '' );
- $order->set_billing_city( $billing_address['admin_area_2'] ?? '' );
- $order->set_billing_address_1( $billing_address['address_line_1'] ?? '' );
- $order->set_billing_address_2( $billing_address['address_line_2'] ?? '' );
- }
-
- $order->update_meta_data( '_paypal_addresses_updated', 'yes' );
- $order->save();
+ PayPalHelper::update_addresses_in_order( $order, $paypal_order_details );
}
}
diff --git a/plugins/woocommerce/phpstan-baseline.neon b/plugins/woocommerce/phpstan-baseline.neon
index bd66679524..7fe8aaa897 100644
--- a/plugins/woocommerce/phpstan-baseline.neon
+++ b/plugins/woocommerce/phpstan-baseline.neon
@@ -24900,18 +24900,6 @@ parameters:
count: 1
path: includes/gateways/paypal/includes/class-wc-gateway-paypal-api-handler.php
- -
- message: '#^Cannot call method get_order_key\(\) on WC_Order\|WC_Order_Refund\|true\.$#'
- identifier: method.nonObject
- count: 1
- path: includes/gateways/paypal/includes/class-wc-gateway-paypal-helper.php
-
- -
- message: '#^Method WC_Gateway_Paypal_Helper\:\:get_wc_order_from_paypal_custom_id\(\) should return WC_Order\|null but returns WC_Order\|WC_Order_Refund\|true\.$#'
- identifier: return.type
- count: 1
- path: includes/gateways/paypal/includes/class-wc-gateway-paypal-helper.php
-
-
message: '#^Cannot call method get_id\(\) on WC_Order\|true\.$#'
identifier: method.nonObject
diff --git a/plugins/woocommerce/src/Gateways/PayPal/Helper.php b/plugins/woocommerce/src/Gateways/PayPal/Helper.php
new file mode 100644
index 0000000000..ab55429203
--- /dev/null
+++ b/plugins/woocommerce/src/Gateways/PayPal/Helper.php
@@ -0,0 +1,213 @@
+<?php
+
+declare( strict_types=1 );
+
+namespace Automattic\WooCommerce\Gateways\PayPal;
+
+use WC_Order;
+
+defined( 'ABSPATH' ) || exit;
+
+/**
+ * PayPal Helper Class
+ *
+ * Helper methods for PayPal gateway operations including order validation,
+ * data redaction, and address updates.
+ *
+ * @since 10.5.0
+ */
+class Helper {
+ /**
+ * Check if the PayPal gateway is enabled.
+ *
+ * @return bool
+ */
+ public static function is_paypal_gateway_available(): bool {
+ $settings = get_option( 'woocommerce_paypal_settings', array() );
+ $enabled = isset( $settings['enabled'] ) && 'yes' === $settings['enabled'];
+ $should_load = isset( $settings['_should_load'] ) && 'yes' === $settings['_should_load'];
+ return $enabled && $should_load;
+ }
+
+ /**
+ * Check if the merchant is eligible for migration from WPS to PPCP.
+ *
+ * @return bool
+ */
+ public static function is_orders_v2_migration_eligible(): bool {
+ $settings = get_option( 'woocommerce_paypal_settings', array() );
+
+ // If API keys are set, the merchant is not eligible for migration
+ // as they may be using features that cannot be seamlessly migrated.
+ $is_test_mode = isset( $settings['testmode'] ) && 'yes' === $settings['testmode'];
+ $api_username = $is_test_mode ? ( $settings['sandbox_api_username'] ?? null ) : ( $settings['api_username'] ?? null );
+ $api_password = $is_test_mode ? ( $settings['sandbox_api_password'] ?? null ) : ( $settings['api_password'] ?? null );
+ $api_signature = $is_test_mode ? ( $settings['sandbox_api_signature'] ?? null ) : ( $settings['api_signature'] ?? null );
+
+ return empty( $api_username ) && empty( $api_password ) && empty( $api_signature );
+ }
+
+ /**
+ * Get the WC order from the PayPal custom ID.
+ *
+ * @param string $custom_id The custom ID string from the PayPal order.
+ * @return WC_Order|null
+ */
+ public static function get_wc_order_from_paypal_custom_id( string $custom_id ): ?WC_Order {
+ if ( '' === $custom_id ) {
+ return null;
+ }
+
+ $data = json_decode( $custom_id, true );
+ if ( ! is_array( $data ) ) {
+ return null;
+ }
+
+ $order_id = $data['order_id'] ?? null;
+ if ( ! $order_id ) {
+ return null;
+ }
+
+ $order = wc_get_order( $order_id );
+ if ( ! $order instanceof \WC_Order ) {
+ return null;
+ }
+
+ // Validate the order key.
+ $order_key = $data['order_key'] ?? null;
+ if ( $order_key !== $order->get_order_key() ) {
+ return null;
+ }
+
+ return $order;
+ }
+
+ /**
+ * Remove PII (Personally Identifiable Information) from data for logging.
+ *
+ * This function recursively traverses the data array and redacts sensitive information
+ * while preserving the structure for debugging purposes.
+ *
+ * @param mixed $data The data to remove PII from (array, string, or other types).
+ * @return mixed The data with PII redacted.
+ */
+ public static function redact_data( $data ) {
+ if ( ! is_array( $data ) ) {
+ return $data;
+ }
+
+ $redacted_data = array();
+
+ foreach ( $data as $key => $value ) {
+ // Skip redacting the payee information as it belongs to the store merchant.
+ if ( 'payee' === $key ) {
+ $redacted_data[ $key ] = $value;
+ continue;
+ }
+ // Mask the email address.
+ if ( 'email_address' === $key || 'email' === $key ) {
+ $redacted_data[ $key ] = self::mask_email( (string) $value );
+ continue;
+ }
+
+ if ( is_array( $value ) ) {
+ $redacted_data[ $key ] = self::redact_data( $value );
+ } elseif ( in_array( $key, Constants::FIELDS_TO_REDACT, true ) ) {
+ $redacted_data[ $key ] = '[redacted]';
+ } else {
+ // Keep non-PII data as is.
+ $redacted_data[ $key ] = $value;
+ }
+ }
+
+ return $redacted_data;
+ }
+
+ /**
+ * Mask email address before @ keeping the full domain.
+ *
+ * @param string $email The email address to mask.
+ * @return string The masked email address or original input if invalid.
+ */
+ public static function mask_email( string $email ): string {
+ if ( empty( $email ) ) {
+ return $email;
+ }
+
+ $parts = explode( '@', $email, 2 );
+ if ( count( $parts ) !== 2 || empty( $parts[0] ) || empty( $parts[1] ) ) {
+ return $email;
+ }
+ list( $local, $domain ) = $parts;
+
+ if ( strlen( $local ) <= 3 ) {
+ $masked_local = str_repeat( '*', strlen( $local ) );
+ } else {
+ $masked_local = substr( $local, 0, 2 )
+ . str_repeat( '*', max( 1, strlen( $local ) - 3 ) )
+ . substr( $local, -1 );
+ }
+
+ return $masked_local . '@' . $domain;
+ }
+
+ /**
+ * Update the addresses in the order.
+ *
+ * @param WC_Order|null $order The order object.
+ * @param array $paypal_order_details The PayPal order details.
+ * @return void
+ */
+ public static function update_addresses_in_order( ?WC_Order $order, array $paypal_order_details ): void {
+ if ( empty( $order ) || empty( $paypal_order_details ) ) {
+ return;
+ }
+
+ // Bail early if '_paypal_addresses_updated' is 'yes', meaning the addresses update already have been successful.
+ if ( 'yes' === $order->get_meta( '_paypal_addresses_updated', true ) ) {
+ return;
+ }
+
+ // Update the shipping information.
+ $full_name = $paypal_order_details['purchase_units'][0]['shipping']['name']['full_name'] ?? '';
+ if ( ! empty( $full_name ) ) {
+ $name_parts = explode( ' ', $full_name, 2 );
+ $approximate_first_name = $name_parts[0] ?? '';
+ $approximate_last_name = isset( $name_parts[1] ) ? $name_parts[1] : '';
+ $order->set_shipping_first_name( $approximate_first_name );
+ $order->set_shipping_last_name( $approximate_last_name );
+ }
+
+ $shipping_address = $paypal_order_details['purchase_units'][0]['shipping']['address'] ?? array();
+ if ( ! empty( $shipping_address ) ) {
+ $order->set_shipping_country( $shipping_address['country_code'] ?? '' );
+ $order->set_shipping_postcode( $shipping_address['postal_code'] ?? '' );
+ $order->set_shipping_state( $shipping_address['admin_area_1'] ?? '' );
+ $order->set_shipping_city( $shipping_address['admin_area_2'] ?? '' );
+ $order->set_shipping_address_1( $shipping_address['address_line_1'] ?? '' );
+ $order->set_shipping_address_2( $shipping_address['address_line_2'] ?? '' );
+ }
+
+ // Update the billing information.
+ $full_name = $paypal_order_details['payer']['name'] ?? array();
+ $email = $paypal_order_details['payer']['email_address'] ?? '';
+ if ( ! empty( $full_name ) ) {
+ $order->set_billing_first_name( $full_name['given_name'] ?? '' );
+ $order->set_billing_last_name( $full_name['surname'] ?? '' );
+ $order->set_billing_email( $email );
+ }
+
+ $billing_address = $paypal_order_details['payer']['address'] ?? array();
+ if ( ! empty( $billing_address ) ) {
+ $order->set_billing_country( $billing_address['country_code'] ?? '' );
+ $order->set_billing_postcode( $billing_address['postal_code'] ?? '' );
+ $order->set_billing_state( $billing_address['admin_area_1'] ?? '' );
+ $order->set_billing_city( $billing_address['admin_area_2'] ?? '' );
+ $order->set_billing_address_1( $billing_address['address_line_1'] ?? '' );
+ $order->set_billing_address_2( $billing_address['address_line_2'] ?? '' );
+ }
+
+ $order->update_meta_data( '_paypal_addresses_updated', 'yes' );
+ $order->save();
+ }
+}
diff --git a/plugins/woocommerce/tests/php/includes/gateways/paypal/class-wc-gateway-paypal-helper-test.php b/plugins/woocommerce/tests/php/src/Gateways/PayPal/HelperTest.php
similarity index 58%
rename from plugins/woocommerce/tests/php/includes/gateways/paypal/class-wc-gateway-paypal-helper-test.php
rename to plugins/woocommerce/tests/php/src/Gateways/PayPal/HelperTest.php
index b124b2bb56..00e2575c31 100644
--- a/plugins/woocommerce/tests/php/includes/gateways/paypal/class-wc-gateway-paypal-helper-test.php
+++ b/plugins/woocommerce/tests/php/src/Gateways/PayPal/HelperTest.php
@@ -1,18 +1,20 @@
<?php
/**
- * Unit tests for WC_Gateway_Paypal_Helper class.
+ * Unit tests for Automattic\WooCommerce\Gateways\PayPal\Helper class.
*
- * @package WooCommerce\Tests\Paypal.
+ * @package WooCommerce\Tests\Gateways\PayPal
*/
declare(strict_types=1);
-require_once WC_ABSPATH . 'includes/gateways/paypal/includes/class-wc-gateway-paypal-helper.php';
+namespace Automattic\WooCommerce\Tests\Gateways\PayPal;
+
+use Automattic\WooCommerce\Gateways\PayPal\Helper;
/**
- * Class WC_Gateway_Paypal_Helper_Test.
+ * Class HelperTest.
*/
-class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
+class HelperTest extends \WC_Unit_Test_Case {
/**
* Tear down the test environment.
@@ -84,7 +86,7 @@ class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
public function test_is_paypal_gateway_available_scenarios( $settings, $expected ) {
update_option( 'woocommerce_paypal_settings', $settings );
- $result = WC_Gateway_Paypal_Helper::is_paypal_gateway_available();
+ $result = Helper::is_paypal_gateway_available();
$this->assertEquals( $expected, $result );
}
@@ -168,7 +170,7 @@ class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
public function test_is_orders_v2_migration_eligible_scenarios( $settings, $expected ) {
update_option( 'woocommerce_paypal_settings', $settings );
- $result = WC_Gateway_Paypal_Helper::is_orders_v2_migration_eligible();
+ $result = Helper::is_orders_v2_migration_eligible();
$this->assertEquals( $expected, $result );
}
@@ -178,7 +180,7 @@ class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
*/
public function test_get_wc_order_from_paypal_custom_id_returns_order_when_valid() {
// Create a test order.
- $order = WC_Helper_Order::create_order();
+ $order = \WC_Helper_Order::create_order();
$order->save();
$custom_id = wp_json_encode(
@@ -190,9 +192,9 @@ class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
)
);
- $result = WC_Gateway_Paypal_Helper::get_wc_order_from_paypal_custom_id( $custom_id );
+ $result = Helper::get_wc_order_from_paypal_custom_id( $custom_id );
- $this->assertInstanceOf( WC_Order::class, $result );
+ $this->assertInstanceOf( \WC_Order::class, $result );
$this->assertEquals( $order->get_id(), $result->get_id() );
// Clean up.
@@ -210,7 +212,7 @@ class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
)
);
- $result = WC_Gateway_Paypal_Helper::get_wc_order_from_paypal_custom_id( $custom_id );
+ $result = Helper::get_wc_order_from_paypal_custom_id( $custom_id );
$this->assertNull( $result );
}
@@ -227,7 +229,7 @@ class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
)
);
- $result = WC_Gateway_Paypal_Helper::get_wc_order_from_paypal_custom_id( $custom_id );
+ $result = Helper::get_wc_order_from_paypal_custom_id( $custom_id );
$this->assertNull( $result );
}
@@ -237,7 +239,7 @@ class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
*/
public function test_get_wc_order_from_paypal_custom_id_returns_null_when_order_key_mismatch() {
// Create a test order.
- $order = WC_Helper_Order::create_order();
+ $order = \WC_Helper_Order::create_order();
$order->save();
$custom_id = wp_json_encode(
@@ -248,7 +250,7 @@ class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
)
);
- $result = WC_Gateway_Paypal_Helper::get_wc_order_from_paypal_custom_id( $custom_id );
+ $result = Helper::get_wc_order_from_paypal_custom_id( $custom_id );
$this->assertNull( $result );
@@ -263,22 +265,10 @@ class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
*/
public function provider_custom_id_scenarios() {
return array(
- 'null_input' => array(
- 'custom_id' => null,
- 'expected' => null,
- ),
'empty_string' => array(
'custom_id' => '',
'expected' => null,
),
- 'integer_input' => array(
- 'custom_id' => 123,
- 'expected' => null,
- ),
- 'array_input' => array(
- 'custom_id' => array( 'test' ),
- 'expected' => null,
- ),
'invalid_json' => array(
'custom_id' => 'not-json',
'expected' => null,
@@ -295,11 +285,11 @@ class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
*
* @dataProvider provider_custom_id_scenarios
*
- * @param mixed $custom_id The custom ID to test.
- * @param mixed $expected The expected result.
+ * @param string $custom_id The custom ID to test.
+ * @param mixed $expected The expected result.
*/
public function test_get_wc_order_from_paypal_custom_id_invalid_inputs( $custom_id, $expected ) {
- $result = WC_Gateway_Paypal_Helper::get_wc_order_from_paypal_custom_id( $custom_id );
+ $result = Helper::get_wc_order_from_paypal_custom_id( $custom_id );
$this->assertEquals( $expected, $result );
}
@@ -313,7 +303,7 @@ class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
* @param string $expected The expected masked result.
*/
public function test_mask_email( $email, $expected ) {
- $result = WC_Gateway_Paypal_Helper::mask_email( $email );
+ $result = Helper::mask_email( $email );
$this->assertEquals( $expected, $result );
}
@@ -345,10 +335,6 @@ class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
'email' => '',
'expected' => '',
),
- 'not_string' => array(
- 'email' => 123,
- 'expected' => 123,
- ),
'invalid_email_string' => array(
'email' => 'notanemail',
'expected' => 'notanemail',
@@ -392,7 +378,7 @@ class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
),
);
- $result = WC_Gateway_Paypal_Helper::redact_data( $data );
+ $result = Helper::redact_data( $data );
// PII fields should be redacted.
$this->assertEquals( '[redacted]', $result['given_name'] );
@@ -420,19 +406,213 @@ class WC_Gateway_Paypal_Helper_Test extends \WC_Unit_Test_Case {
* Test redact_data handles non-array inputs.
*/
public function test_redact_data_handles_non_array_inputs() {
- $this->assertEquals( 'string', WC_Gateway_Paypal_Helper::redact_data( 'string' ) );
- $this->assertEquals( 123, WC_Gateway_Paypal_Helper::redact_data( 123 ) );
- $this->assertEquals( null, WC_Gateway_Paypal_Helper::redact_data( null ) );
- $this->assertEquals( true, WC_Gateway_Paypal_Helper::redact_data( true ) );
+ $this->assertEquals( 'string', Helper::redact_data( 'string' ) );
+ $this->assertEquals( 123, Helper::redact_data( 123 ) );
+ $this->assertEquals( null, Helper::redact_data( null ) );
+ $this->assertEquals( true, Helper::redact_data( true ) );
}
/**
* Test redact_data handles empty arrays.
*/
public function test_redact_data_handles_empty_array() {
- $result = WC_Gateway_Paypal_Helper::redact_data( array() );
+ $result = Helper::redact_data( array() );
$this->assertIsArray( $result );
$this->assertEmpty( $result );
}
+
+ /**
+ * Test update_addresses_in_order updates both shipping and billing addresses.
+ */
+ public function test_update_addresses_in_order_updates_addresses() {
+ $order = \WC_Helper_Order::create_order();
+ $order->save();
+
+ $paypal_order_details = array(
+ 'purchase_units' => array(
+ array(
+ 'shipping' => array(
+ 'name' => array(
+ 'full_name' => 'John Doe',
+ ),
+ 'address' => array(
+ 'country_code' => 'US',
+ 'postal_code' => '12345',
+ 'admin_area_1' => 'CA',
+ 'admin_area_2' => 'San Francisco',
+ 'address_line_1' => '123 Main St',
+ 'address_line_2' => 'Apt 4B',
+ ),
+ ),
+ ),
+ ),
+ 'payer' => array(
+ 'name' => array(
+ 'given_name' => 'Jane',
+ 'surname' => 'Smith',
+ ),
+ 'email_address' => 'jane.smith@example.com',
+ 'address' => array(
+ 'country_code' => 'US',
+ 'postal_code' => '54321',
+ 'admin_area_1' => 'NY',
+ 'admin_area_2' => 'New York',
+ 'address_line_1' => '456 Broadway',
+ 'address_line_2' => 'Suite 100',
+ ),
+ ),
+ );
+
+ Helper::update_addresses_in_order( $order, $paypal_order_details );
+
+ // Verify shipping address was updated.
+ $this->assertEquals( 'John', $order->get_shipping_first_name() );
+ $this->assertEquals( 'Doe', $order->get_shipping_last_name() );
+ $this->assertEquals( 'US', $order->get_shipping_country() );
+ $this->assertEquals( '12345', $order->get_shipping_postcode() );
+ $this->assertEquals( 'CA', $order->get_shipping_state() );
+ $this->assertEquals( 'San Francisco', $order->get_shipping_city() );
+ $this->assertEquals( '123 Main St', $order->get_shipping_address_1() );
+ $this->assertEquals( 'Apt 4B', $order->get_shipping_address_2() );
+
+ // Verify billing address was updated.
+ $this->assertEquals( 'Jane', $order->get_billing_first_name() );
+ $this->assertEquals( 'Smith', $order->get_billing_last_name() );
+ $this->assertEquals( 'jane.smith@example.com', $order->get_billing_email() );
+ $this->assertEquals( 'US', $order->get_billing_country() );
+ $this->assertEquals( '54321', $order->get_billing_postcode() );
+ $this->assertEquals( 'NY', $order->get_billing_state() );
+ $this->assertEquals( 'New York', $order->get_billing_city() );
+ $this->assertEquals( '456 Broadway', $order->get_billing_address_1() );
+ $this->assertEquals( 'Suite 100', $order->get_billing_address_2() );
+
+ // Verify meta flag was set.
+ $this->assertEquals( 'yes', $order->get_meta( '_paypal_addresses_updated', true ) );
+
+ // Clean up.
+ $order->delete( true );
+ }
+
+ /**
+ * Test update_addresses_in_order does not update when order is null.
+ */
+ public function test_update_addresses_in_order_skips_null_order() {
+ $paypal_order_details = array(
+ 'purchase_units' => array(
+ array(
+ 'shipping' => array(
+ 'name' => array( 'full_name' => 'John Doe' ),
+ ),
+ ),
+ ),
+ );
+
+ // Should not throw an error.
+ Helper::update_addresses_in_order( null, $paypal_order_details );
+
+ // No assertions, just ensuring no exception is thrown.
+ $this->assertTrue( true );
+ }
+
+ /**
+ * Test update_addresses_in_order does not update when paypal_order_details is empty.
+ */
+ public function test_update_addresses_in_order_skips_empty_details() {
+ $order = \WC_Helper_Order::create_order();
+ $order->save();
+
+ $original_shipping_first_name = $order->get_shipping_first_name();
+ $original_billing_first_name = $order->get_billing_first_name();
+
+ Helper::update_addresses_in_order( $order, array() );
+
+ // Order should not be modified.
+ $this->assertEquals( $original_shipping_first_name, $order->get_shipping_first_name() );
+ $this->assertEquals( $original_billing_first_name, $order->get_billing_first_name() );
+ $this->assertEmpty( $order->get_meta( '_paypal_addresses_updated', true ) );
+
+ // Clean up.
+ $order->delete( true );
+ }
+
+ /**
+ * Test update_addresses_in_order does not update when already updated.
+ */
+ public function test_update_addresses_in_order_skips_already_updated() {
+ $order = \WC_Helper_Order::create_order();
+ $order->update_meta_data( '_paypal_addresses_updated', 'yes' );
+ $order->save();
+
+ $original_shipping_first_name = $order->get_shipping_first_name();
+
+ $paypal_order_details = array(
+ 'purchase_units' => array(
+ array(
+ 'shipping' => array(
+ 'name' => array(
+ 'full_name' => 'Different Name',
+ ),
+ ),
+ ),
+ ),
+ );
+
+ Helper::update_addresses_in_order( $order, $paypal_order_details );
+
+ // Order should not be modified.
+ $this->assertEquals( $original_shipping_first_name, $order->get_shipping_first_name() );
+
+ // Clean up.
+ $order->delete( true );
+ }
+
+ /**
+ * Test update_addresses_in_order handles partial address data.
+ */
+ public function test_update_addresses_in_order_handles_partial_address_data() {
+ $order = \WC_Helper_Order::create_order();
+ $order->save();
+
+ $paypal_order_details = array(
+ 'purchase_units' => array(
+ array(
+ 'shipping' => array(
+ 'name' => array(
+ 'full_name' => 'John Doe',
+ ),
+ 'address' => array(
+ 'country_code' => 'US',
+ // Only country code, missing other fields.
+ ),
+ ),
+ ),
+ ),
+ 'payer' => array(
+ 'name' => array(
+ 'given_name' => 'Jane',
+ // Missing surname.
+ ),
+ 'address' => array(
+ 'postal_code' => '12345',
+ // Only postal code.
+ ),
+ ),
+ );
+
+ Helper::update_addresses_in_order( $order, $paypal_order_details );
+
+ // Shipping country should be set, other fields should be empty strings.
+ $this->assertEquals( 'US', $order->get_shipping_country() );
+ $this->assertEquals( '', $order->get_shipping_postcode() );
+ $this->assertEquals( '', $order->get_shipping_state() );
+
+ // Billing should have given name and postal code.
+ $this->assertEquals( 'Jane', $order->get_billing_first_name() );
+ $this->assertEquals( '', $order->get_billing_last_name() );
+ $this->assertEquals( '12345', $order->get_billing_postcode() );
+
+ // Clean up.
+ $order->delete( true );
+ }
}