mirror of
https://github.com/woocommerce/woocommerce-paypal-payments.git
synced 2025-08-30 05:00:51 +08:00
Merge pull request #3601 from woocommerce/trunk
Merge trunk into develop
This commit is contained in:
commit
0535faad10
12 changed files with 226 additions and 46 deletions
|
@ -170,6 +170,10 @@ return array(
|
|||
$matrix['GB'] = array( 'GBP' );
|
||||
}
|
||||
|
||||
if ( $container->get( 'axo.au.enabled' ) ) {
|
||||
$matrix['AU'] = array( 'AUD' );
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns which countries and currency combinations can be used for AXO.
|
||||
*/
|
||||
|
@ -206,6 +210,14 @@ return array(
|
|||
);
|
||||
}
|
||||
|
||||
if ( $container->get( 'axo.au.enabled' ) ) {
|
||||
$matrix['AU'] = array(
|
||||
'VISA',
|
||||
'MASTERCARD',
|
||||
'AMEX',
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns which countries and card type combinations can be used for AXO.
|
||||
*/
|
||||
|
@ -417,4 +429,17 @@ return array(
|
|||
);
|
||||
// phpcs:enable WordPress.NamingConventions.ValidHookName.UseUnderscores
|
||||
},
|
||||
'axo.au.enabled' => static function ( ContainerInterface $container ): bool {
|
||||
// phpcs:disable WordPress.NamingConventions.ValidHookName.UseUnderscores
|
||||
/**
|
||||
* Filter to determine if Fastlane AU should be enabled.
|
||||
*
|
||||
* @param bool $enabled Whether Fastlane AU is enabled.
|
||||
*/
|
||||
return apply_filters(
|
||||
'woocommerce.feature-flags.woocommerce_paypal_payments.axo_au_enabled',
|
||||
getenv( 'PCP_AXO_AU_ENABLED' ) !== '0'
|
||||
);
|
||||
// phpcs:enable WordPress.NamingConventions.ValidHookName.UseUnderscores
|
||||
},
|
||||
);
|
||||
|
|
|
@ -13,6 +13,9 @@ use Exception;
|
|||
use WC_Cart;
|
||||
use WC_Order;
|
||||
use WC_Order_Item_Product;
|
||||
use WooCommerce\PayPalCommerce\Button\Helper\MessagesApply;
|
||||
use WooCommerce\PayPalCommerce\Settings\Data\SettingsModel;
|
||||
use WooCommerce\PayPalCommerce\Settings\SettingsModule;
|
||||
use WooCommerce\PayPalCommerce\Vendor\Inpsyde\Modularity\Module\ExecutableModule;
|
||||
use WooCommerce\PayPalCommerce\Vendor\Inpsyde\Modularity\Module\ExtendingModule;
|
||||
use WooCommerce\PayPalCommerce\Vendor\Inpsyde\Modularity\Module\ModuleClassNameIdTrait;
|
||||
|
@ -91,6 +94,67 @@ class CompatModule implements ServiceModule, ExtendingModule, ExecutableModule {
|
|||
|
||||
$this->legacy_ui_card_payment_mapping( $c );
|
||||
|
||||
/**
|
||||
* Automatically enable Pay Later messaging for eligible stores during plugin update.
|
||||
*
|
||||
* This action runs during plugin updates to automatically enable Pay Later messaging for stores
|
||||
* that meet the following criteria:
|
||||
* - Feature flag 'paylater_messaging_force_enabled' is enabled (default: true, can be disabled via filter)
|
||||
* - Pay Later messaging is available for the store's country
|
||||
* - The "Stay updated" checkbox is enabled (checked in either old or new UI)
|
||||
*
|
||||
* The "Stay updated" setting is retrieved differently based on the UI version:
|
||||
* - Legacy UI: Retrieved from wcgateway.settings
|
||||
* - New UI: Retrieved from settings.data.settings model
|
||||
*
|
||||
* When all conditions are met, this will:
|
||||
* - Enable Pay Later messaging
|
||||
* - Add default messaging locations (product, cart, checkout) to existing selections
|
||||
*
|
||||
* @todo Remove this auto-enablement logic after the next release
|
||||
*
|
||||
* @hook woocommerce_paypal_payments_gateway_migrate_on_update
|
||||
*/
|
||||
add_action(
|
||||
'woocommerce_paypal_payments_gateway_migrate_on_update',
|
||||
static function() use ( $c ) {
|
||||
if ( ! apply_filters(
|
||||
// phpcs:ignore WordPress.NamingConventions.ValidHookName.UseUnderscores
|
||||
'woocommerce.feature-flags.woocommerce_paypal_payments.paylater_messaging_force_enabled',
|
||||
true
|
||||
) ) {
|
||||
return;
|
||||
}
|
||||
|
||||
$messages_apply = $c->get( 'button.helper.messages-apply' );
|
||||
assert( $messages_apply instanceof MessagesApply );
|
||||
|
||||
$settings_model = $c->get( 'settings.data.settings' );
|
||||
assert( $settings_model instanceof SettingsModel );
|
||||
|
||||
$settings = $c->get( 'wcgateway.settings' );
|
||||
assert( $settings instanceof Settings );
|
||||
|
||||
$stay_updated = SettingsModule::should_use_the_old_ui()
|
||||
? $settings->has( 'stay_updated' ) && $settings->get( 'stay_updated' )
|
||||
: $settings_model->get_stay_updated();
|
||||
|
||||
if ( ! $messages_apply->for_country() || ! $stay_updated ) {
|
||||
return;
|
||||
}
|
||||
|
||||
$selected_locations = $settings->has( 'pay_later_messaging_locations' ) ? $settings->get( 'pay_later_messaging_locations' ) : array();
|
||||
|
||||
$settings->set( 'pay_later_messaging_enabled', true );
|
||||
$settings->set(
|
||||
'pay_later_messaging_locations',
|
||||
array_unique( array_merge( $selected_locations, array( 'product', 'cart', 'checkout' ) ) )
|
||||
);
|
||||
|
||||
$settings->persist();
|
||||
}
|
||||
);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
@ -10,6 +10,7 @@ const StayUpdated = () => {
|
|||
return (
|
||||
<SettingsBlock className="ppcp--pay-now-experience">
|
||||
<ControlToggleButton
|
||||
id="ppcp-stay-updated"
|
||||
label={ __( 'Stay Updated', 'woocommerce-paypal-payments' ) }
|
||||
description={ __(
|
||||
'Get the latest PayPal features and capabilities as they are released. When the extension is updated, new features, payment methods, styling options, and more will automatically update.',
|
||||
|
|
|
@ -1,13 +1,7 @@
|
|||
document.addEventListener( 'DOMContentLoaded', () => {
|
||||
const config = ppcpSwitchSettingsUi;
|
||||
const button = document.querySelector(
|
||||
'.button.button-settings-switch-ui'
|
||||
);
|
||||
const link = document.querySelector(
|
||||
'.ppcp-notice-wrapper:not(.inline) a.settings-switch-ui'
|
||||
);
|
||||
|
||||
if ( typeof config === 'undefined' || ( ! button && ! link ) ) {
|
||||
if ( typeof config === 'undefined' ) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -36,20 +30,24 @@ document.addEventListener( 'DOMContentLoaded', () => {
|
|||
return response.json();
|
||||
} )
|
||||
.then( ( data ) => {
|
||||
window.location.reload();
|
||||
window.location.href = config.settingsUrl;
|
||||
} )
|
||||
.catch( ( error ) => {
|
||||
console.error( 'Error:', error );
|
||||
} );
|
||||
};
|
||||
|
||||
if ( button ) {
|
||||
button.addEventListener( 'click', handleClick );
|
||||
}
|
||||
|
||||
document.addEventListener( 'click', ( event ) => {
|
||||
const linkElement = event.target.closest( 'a.settings-switch-ui' );
|
||||
if ( linkElement ) {
|
||||
if (
|
||||
event.target.closest( '.button.button-settings-switch-ui' ) ||
|
||||
event.target.closest(
|
||||
'.ppcp-notice-wrapper:not(.inline) a.settings-switch-ui'
|
||||
) ||
|
||||
event.target.closest( 'a[name="settings-switch-ui"]' ) ||
|
||||
event.target
|
||||
.closest( '.woocommerce-inbox-note__action-button' )
|
||||
?.textContent.includes( 'Switch to New Settings' )
|
||||
) {
|
||||
handleClick( event );
|
||||
}
|
||||
} );
|
||||
|
|
|
@ -165,6 +165,7 @@ class SettingsModule implements ServiceModule, ExecutableModule {
|
|||
'Are you sure you want to switch to the new settings interface?This action cannot be undone.',
|
||||
'woocommerce-paypal-payments'
|
||||
),
|
||||
'settingsUrl' => admin_url( 'admin.php?page=wc-settings&tab=checkout§ion=ppcp-gateway' ),
|
||||
)
|
||||
);
|
||||
|
||||
|
|
|
@ -21,11 +21,13 @@ use WooCommerce\PayPalCommerce\ApiClient\Helper\DccApplies;
|
|||
use WooCommerce\PayPalCommerce\Applepay\ApplePayGateway;
|
||||
use WooCommerce\PayPalCommerce\Axo\Gateway\AxoGateway;
|
||||
use WooCommerce\PayPalCommerce\Axo\Helper\PropertiesDictionary;
|
||||
use WooCommerce\PayPalCommerce\Button\Helper\MessagesApply;
|
||||
use WooCommerce\PayPalCommerce\Button\Helper\MessagesDisclaimers;
|
||||
use WooCommerce\PayPalCommerce\Common\Pattern\SingletonDecorator;
|
||||
use WooCommerce\PayPalCommerce\Googlepay\GooglePayGateway;
|
||||
use WooCommerce\PayPalCommerce\Onboarding\Render\OnboardingOptionsRenderer;
|
||||
use WooCommerce\PayPalCommerce\Onboarding\State;
|
||||
use WooCommerce\PayPalCommerce\Settings\Data\SettingsModel;
|
||||
use WooCommerce\PayPalCommerce\Settings\SettingsModule;
|
||||
use WooCommerce\PayPalCommerce\Vendor\Psr\Container\ContainerInterface;
|
||||
use WooCommerce\PayPalCommerce\WcGateway\Admin\FeesRenderer;
|
||||
|
@ -2161,10 +2163,52 @@ return array(
|
|||
*
|
||||
* @returns InboxNoteInterface[]
|
||||
*/
|
||||
'wcgateway.settings.inbox-notes' => static function( ContainerInterface $container ): array {
|
||||
'wcgateway.settings.inbox-notes' => static function( ContainerInterface $container ): array {
|
||||
$inbox_note_factory = $container->get( 'wcgateway.settings.inbox-note-factory' );
|
||||
assert( $inbox_note_factory instanceof InboxNoteFactory );
|
||||
|
||||
$settings = $container->get( 'wcgateway.settings' );
|
||||
assert( $settings instanceof Settings );
|
||||
|
||||
$settings_model = $container->get( 'settings.data.settings' );
|
||||
assert( $settings_model instanceof SettingsModel );
|
||||
|
||||
$messages_apply = $container->get( 'button.helper.messages-apply' );
|
||||
assert( $messages_apply instanceof MessagesApply );
|
||||
|
||||
$is_working_capital_feature_flag_enabled = apply_filters(
|
||||
// phpcs:ignore WordPress.NamingConventions.ValidHookName.UseUnderscores -- feature flags use this convention
|
||||
'woocommerce.feature-flags.woocommerce_paypal_payments.working_capital_enabled',
|
||||
getenv( 'PCP_WORKING_CAPITAL_ENABLED' ) === '1'
|
||||
);
|
||||
|
||||
$is_paylater_messaging_force_enabled_feature_flag_enabled = apply_filters(
|
||||
// phpcs:ignore WordPress.NamingConventions.ValidHookName.UseUnderscores -- feature flags use this convention
|
||||
'woocommerce.feature-flags.woocommerce_paypal_payments.paylater_messaging_force_enabled',
|
||||
true
|
||||
);
|
||||
|
||||
$stay_updated = SettingsModule::should_use_the_old_ui()
|
||||
? $settings->has( 'stay_updated' ) && $settings->get( 'stay_updated' )
|
||||
: $settings_model->get_stay_updated();
|
||||
|
||||
$stay_updated_field_link = SettingsModule::should_use_the_old_ui()
|
||||
? admin_url( 'admin.php?page=wc-settings&tab=checkout§ion=ppcp-gateway&ppcp-tab=ppcp-connection#ppcp-stay_updated_field' )
|
||||
: admin_url( 'admin.php?page=wc-settings&tab=checkout§ion=ppcp-gateway&panel=settings#ppcp-stay-updated' );
|
||||
|
||||
$paylater_messaging_tab_link = SettingsModule::should_use_the_old_ui()
|
||||
? admin_url( 'admin.php?page=wc-settings&tab=checkout§ion=ppcp-gateway&ppcp-tab=ppcp-pay-later' )
|
||||
: admin_url( 'admin.php?page=wc-settings&tab=checkout§ion=ppcp-gateway&panel=pay-later-messaging' );
|
||||
|
||||
$message = sprintf(
|
||||
// translators: %1$s is the URL for the startup guide.
|
||||
__(
|
||||
'We\'ve redesigned the settings for better performance and usability. Starting late October, this improved design will be the default for all WooCommerce installations to enjoy faster navigation, cleaner organization, and improved performance. Check out the <a href="%1$s" target="_blank">Startup Guide</a>, then click <a href="#" name="settings-switch-ui"><strong>Switch to New Settings</strong></a> to activate it.',
|
||||
'woocommerce-paypal-payments'
|
||||
),
|
||||
'https://woocommerce.com/document/woocommerce-paypal-payments/paypal-payments-startup-guide/'
|
||||
);
|
||||
|
||||
return array(
|
||||
$inbox_note_factory->create_note(
|
||||
__( 'PayPal Working Capital', 'woocommerce-paypal-payments' ),
|
||||
|
@ -2172,6 +2216,7 @@ return array(
|
|||
Note::E_WC_ADMIN_NOTE_INFORMATIONAL,
|
||||
'ppcp-working-capital-inbox-note',
|
||||
Note::E_WC_ADMIN_NOTE_UNACTIONED,
|
||||
$is_working_capital_feature_flag_enabled && $container->get( 'api.shop.country' ) === 'US' && $stay_updated,
|
||||
new InboxNoteAction(
|
||||
'apply_now',
|
||||
__( 'Apply now', 'woocommerce-paypal-payments' ),
|
||||
|
@ -2180,6 +2225,43 @@ return array(
|
|||
true
|
||||
)
|
||||
),
|
||||
$inbox_note_factory->create_note(
|
||||
__( '📢 Important: New PayPal Payments settings UI becoming default in October!', 'woocommerce-paypal-payments' ),
|
||||
$message,
|
||||
Note::E_WC_ADMIN_NOTE_INFORMATIONAL,
|
||||
'ppcp-settings-migration-inbox-note',
|
||||
Note::E_WC_ADMIN_NOTE_UNACTIONED,
|
||||
SettingsModule::should_use_the_old_ui(),
|
||||
new InboxNoteAction(
|
||||
'switch_to_new_settings',
|
||||
__( 'Switch to New Settings', 'woocommerce-paypal-payments' ),
|
||||
admin_url( 'admin.php?page=wc-settings&tab=checkout§ion=ppcp-gateway' ),
|
||||
Note::E_WC_ADMIN_NOTE_UNACTIONED,
|
||||
true
|
||||
)
|
||||
),
|
||||
$inbox_note_factory->create_note(
|
||||
__( 'Pay Later messaging now optimizing conversions', 'woocommerce-paypal-payments' ),
|
||||
sprintf(
|
||||
// translators: %1$s is the URL for Pay Later messaging documentation.
|
||||
__(
|
||||
'PayPal Pay Later messages are now displaying on your store through your <a href="%1$s">Stay Updated</a> preference, helping customers see flexible payment options. Merchants typically see 20-40% higher conversion rates with these purchase incentives. The messages appear contextually near prices, not as ads. You control this completely—disable anytime if your conversion metrics don\'t improve.',
|
||||
'woocommerce-paypal-payments'
|
||||
),
|
||||
$stay_updated_field_link
|
||||
),
|
||||
Note::E_WC_ADMIN_NOTE_INFORMATIONAL,
|
||||
'ppcp-settings-paylater-messaging-force-enabled-inbox-note',
|
||||
Note::E_WC_ADMIN_NOTE_UNACTIONED,
|
||||
$is_paylater_messaging_force_enabled_feature_flag_enabled && $messages_apply->for_country() && $stay_updated,
|
||||
new InboxNoteAction(
|
||||
'review_pay_later_settings',
|
||||
__( 'Review Pay Later settings', 'woocommerce-paypal-payments' ),
|
||||
$paylater_messaging_tab_link,
|
||||
Note::E_WC_ADMIN_NOTE_UNACTIONED,
|
||||
true
|
||||
)
|
||||
),
|
||||
);
|
||||
},
|
||||
|
||||
|
|
|
@ -221,12 +221,16 @@ class OrderProcessor {
|
|||
throw new Exception( __( 'Could not retrieve PayPal order.', 'woocommerce-paypal-payments' ) );
|
||||
}
|
||||
} else {
|
||||
$this->logger->warning(
|
||||
sprintf(
|
||||
'No PayPal order ID found in order #%d meta.',
|
||||
$wc_order->get_id()
|
||||
)
|
||||
);
|
||||
$is_paypal_return = isset( $_GET['wc-ajax'] ) && wc_clean( wp_unslash( $_GET['wc-ajax'] ) ) === 'ppc-return-url'; // phpcs:ignore WordPress.Security.NonceVerification.Recommended
|
||||
|
||||
if ( $is_paypal_return ) {
|
||||
$this->logger->warning(
|
||||
sprintf(
|
||||
'No PayPal order ID found for WooCommerce order #%d.',
|
||||
$wc_order->get_id()
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
throw new PayPalOrderMissingException(
|
||||
esc_attr__(
|
||||
|
|
|
@ -17,6 +17,7 @@ class InboxNote implements InboxNoteInterface {
|
|||
protected string $type;
|
||||
protected string $name;
|
||||
protected string $status;
|
||||
protected bool $is_enabled;
|
||||
protected InboxNoteActionInterface $action;
|
||||
|
||||
public function __construct(
|
||||
|
@ -25,14 +26,16 @@ class InboxNote implements InboxNoteInterface {
|
|||
string $type,
|
||||
string $name,
|
||||
string $status,
|
||||
bool $is_enabled,
|
||||
InboxNoteActionInterface $action
|
||||
) {
|
||||
$this->title = $title;
|
||||
$this->content = $content;
|
||||
$this->type = $type;
|
||||
$this->name = $name;
|
||||
$this->status = $status;
|
||||
$this->action = $action;
|
||||
$this->title = $title;
|
||||
$this->content = $content;
|
||||
$this->type = $type;
|
||||
$this->name = $name;
|
||||
$this->status = $status;
|
||||
$this->is_enabled = $is_enabled;
|
||||
$this->action = $action;
|
||||
}
|
||||
|
||||
public function title(): string {
|
||||
|
@ -55,6 +58,10 @@ class InboxNote implements InboxNoteInterface {
|
|||
return $this->status;
|
||||
}
|
||||
|
||||
public function is_enabled(): bool {
|
||||
return $this->is_enabled;
|
||||
}
|
||||
|
||||
public function action(): InboxNoteActionInterface {
|
||||
return $this->action;
|
||||
}
|
||||
|
|
|
@ -18,8 +18,9 @@ class InboxNoteFactory {
|
|||
string $type,
|
||||
string $name,
|
||||
string $status,
|
||||
bool $is_enabled,
|
||||
InboxNoteActionInterface $action
|
||||
): InboxNoteInterface {
|
||||
return new InboxNote( $title, $content, $type, $name, $status, $action );
|
||||
return new InboxNote( $title, $content, $type, $name, $status, $is_enabled, $action );
|
||||
}
|
||||
}
|
||||
|
|
|
@ -16,5 +16,6 @@ interface InboxNoteInterface {
|
|||
public function type(): string;
|
||||
public function name(): string;
|
||||
public function status(): string;
|
||||
public function is_enabled(): bool;
|
||||
public function action(): InboxNoteActionInterface;
|
||||
}
|
||||
|
|
|
@ -30,8 +30,17 @@ class InboxNoteRegistrar {
|
|||
public function register(): void {
|
||||
foreach ( $this->inbox_notes as $inbox_note ) {
|
||||
$inbox_note_name = $inbox_note->name();
|
||||
$existing_note = Notes::get_note_by_name( $inbox_note_name );
|
||||
|
||||
if ( Notes::get_note_by_name( $inbox_note_name ) ) {
|
||||
if ( ! $inbox_note->is_enabled() ) {
|
||||
if ( $existing_note instanceof Note ) {
|
||||
$data_store = Notes::load_data_store();
|
||||
$data_store->delete( $existing_note );
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
if ( $existing_note ) {
|
||||
continue;
|
||||
}
|
||||
|
||||
|
|
|
@ -966,26 +966,13 @@ class WCGatewayModule implements ServiceModule, ExtendingModule, ExecutableModul
|
|||
add_action(
|
||||
'admin_init',
|
||||
static function () use ( $container ): void {
|
||||
$settings = $container->get( 'wcgateway.settings' );
|
||||
assert( $settings instanceof Settings );
|
||||
|
||||
$is_working_capital_feature_flag_enabled = apply_filters(
|
||||
// phpcs:ignore WordPress.NamingConventions.ValidHookName.UseUnderscores -- feature flags use this convention
|
||||
'woocommerce.feature-flags.woocommerce_paypal_payments.working_capital_enabled',
|
||||
getenv( 'PCP_WORKING_CAPITAL_ENABLED' ) === '1'
|
||||
);
|
||||
|
||||
$is_working_capital_eligible = $container->get( 'api.shop.country' ) === 'US' && $settings->has( 'stay_updated' ) && $settings->get( 'stay_updated' );
|
||||
|
||||
if ( ! $is_working_capital_feature_flag_enabled || ! $is_working_capital_eligible ) {
|
||||
return;
|
||||
}
|
||||
|
||||
$logger = $container->get( 'woocommerce.logger.woocommerce' );
|
||||
assert( $logger instanceof LoggerInterface );
|
||||
|
||||
$inbox_note_registrar = $container->get( 'wcgateway.settings.inbox-note-registrar' );
|
||||
assert( $inbox_note_registrar instanceof InboxNoteRegistrar );
|
||||
|
||||
try {
|
||||
$inbox_note_registrar = $container->get( 'wcgateway.settings.inbox-note-registrar' );
|
||||
assert( $inbox_note_registrar instanceof InboxNoteRegistrar );
|
||||
$inbox_note_registrar->register();
|
||||
} catch ( Exception $exception ) {
|
||||
$logger->error( 'Failed to add note to the WooCommerce inbox section. ' . $exception->getMessage() );
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue