This commit is contained in:
Rachit Bhargava
2024-01-10 11:53:33 -05:00
parent 83d223b0df
commit 054b4fffc9
16481 changed files with 0 additions and 3473867 deletions

View File

@@ -1,25 +0,0 @@
<?php
/**
* WooCommerce Onboarding
*/
namespace Automattic\WooCommerce\Internal\Admin\Onboarding;
/**
* Initializes backend logic for the onboarding process.
*/
class Onboarding {
/**
* Initialize onboarding functionality.
*/
public static function init() {
OnboardingHelper::instance()->init();
OnboardingIndustries::init();
OnboardingJetpack::instance()->init();
OnboardingMailchimp::instance()->init();
OnboardingProfile::init();
OnboardingSetupWizard::instance()->init();
OnboardingSync::instance()->init();
OnboardingThemes::init();
}
}

View File

@@ -1,169 +0,0 @@
<?php
/**
* WooCommerce Onboarding Helper
*/
namespace Automattic\WooCommerce\Internal\Admin\Onboarding;
use Automattic\WooCommerce\Admin\PageController;
use Automattic\WooCommerce\Admin\Features\OnboardingTasks\TaskLists;
/**
* Contains backend logic for the onboarding profile and checklist feature.
*/
class OnboardingHelper {
/**
* Class instance.
*
* @var OnboardingHelper instance
*/
private static $instance = null;
/**
* Get class instance.
*/
final public static function instance() {
if ( ! static::$instance ) {
static::$instance = new static();
}
return static::$instance;
}
/**
* Init.
*/
public function init() {
if ( ! is_admin() ) {
return;
}
add_action( 'current_screen', array( $this, 'add_help_tab' ), 60 );
add_action( 'current_screen', array( $this, 'reset_task_list' ) );
add_action( 'current_screen', array( $this, 'reset_extended_task_list' ) );
}
/**
* Update the help tab setup link to reset the onboarding profiler.
*/
public function add_help_tab() {
if ( ! function_exists( 'wc_get_screen_ids' ) ) {
return;
}
$screen = get_current_screen();
if ( ! $screen || ! in_array( $screen->id, wc_get_screen_ids(), true ) ) {
return;
}
// Remove the old help tab if it exists.
$help_tabs = $screen->get_help_tabs();
foreach ( $help_tabs as $help_tab ) {
if ( 'woocommerce_onboard_tab' !== $help_tab['id'] ) {
continue;
}
$screen->remove_help_tab( 'woocommerce_onboard_tab' );
}
// Add the new help tab.
$help_tab = array(
'title' => __( 'Setup wizard', 'woocommerce' ),
'id' => 'woocommerce_onboard_tab',
);
$setup_list = TaskLists::get_list( 'setup' );
$extended_list = TaskLists::get_list( 'extended' );
if ( $setup_list ) {
$help_tab['content'] = '<h2>' . __( 'WooCommerce Onboarding', 'woocommerce' ) . '</h2>';
$help_tab['content'] .= '<h3>' . __( 'Profile Setup Wizard', 'woocommerce' ) . '</h3>';
$help_tab['content'] .= '<p>' . __( 'If you need to access the setup wizard again, please click on the button below.', 'woocommerce' ) . '</p>' .
'<p><a href="' . wc_admin_url( '&path=/setup-wizard' ) . '" class="button button-primary">' . __( 'Setup wizard', 'woocommerce' ) . '</a></p>';
$help_tab['content'] .= '<h3>' . __( 'Task List', 'woocommerce' ) . '</h3>';
$help_tab['content'] .= '<p>' . __( 'If you need to enable or disable the task lists, please click on the button below.', 'woocommerce' ) . '</p>' .
( $setup_list->is_hidden()
? '<p><a href="' . wc_admin_url( '&reset_task_list=1' ) . '" class="button button-primary">' . __( 'Enable', 'woocommerce' ) . '</a></p>'
: '<p><a href="' . wc_admin_url( '&reset_task_list=0' ) . '" class="button button-primary">' . __( 'Disable', 'woocommerce' ) . '</a></p>'
);
}
if ( $extended_list ) {
$help_tab['content'] .= '<h3>' . __( 'Extended task List', 'woocommerce' ) . '</h3>';
$help_tab['content'] .= '<p>' . __( 'If you need to enable or disable the extended task lists, please click on the button below.', 'woocommerce' ) . '</p>' .
( $extended_list->is_hidden()
? '<p><a href="' . wc_admin_url( '&reset_extended_task_list=1' ) . '" class="button button-primary">' . __( 'Enable', 'woocommerce' ) . '</a></p>'
: '<p><a href="' . wc_admin_url( '&reset_extended_task_list=0' ) . '" class="button button-primary">' . __( 'Disable', 'woocommerce' ) . '</a></p>'
);
}
$screen->add_help_tab( $help_tab );
}
/**
* Reset the onboarding task list and redirect to the dashboard.
*/
public function reset_task_list() {
if (
! PageController::is_admin_page() ||
! isset( $_GET['reset_task_list'] ) // phpcs:ignore CSRF ok.
) {
return;
}
$task_list = TaskLists::get_list( 'setup' );
if ( ! $task_list ) {
return;
}
$show = 1 === absint( $_GET['reset_task_list'] ); // phpcs:ignore CSRF ok.
$update = $show ? $task_list->unhide() : $task_list->hide(); // phpcs:ignore CSRF ok.
if ( $update ) {
wc_admin_record_tracks_event(
'tasklist_toggled',
array(
'status' => $show ? 'enabled' : 'disabled',
)
);
}
wp_safe_redirect( wc_admin_url() );
exit;
}
/**
* Reset the extended task list and redirect to the dashboard.
*/
public function reset_extended_task_list() {
if (
! PageController::is_admin_page() ||
! isset( $_GET['reset_extended_task_list'] ) // phpcs:ignore CSRF ok.
) {
return;
}
$task_list = TaskLists::get_list( 'extended' );
if ( ! $task_list ) {
return;
}
$show = 1 === absint( $_GET['reset_extended_task_list'] ); // phpcs:ignore CSRF ok.
$update = $show ? $task_list->unhide() : $task_list->hide(); // phpcs:ignore CSRF ok.
if ( $update ) {
wc_admin_record_tracks_event(
'extended_tasklist_toggled',
array(
'status' => $show ? 'disabled' : 'enabled',
)
);
}
wp_safe_redirect( wc_admin_url() );
exit;
}
}

View File

@@ -1,83 +0,0 @@
<?php
/**
* WooCommerce Onboarding Industries
*/
namespace Automattic\WooCommerce\Internal\Admin\Onboarding;
/**
* Logic around onboarding industries.
*/
class OnboardingIndustries {
/**
* Init.
*/
public static function init() {
add_filter( 'woocommerce_admin_onboarding_preloaded_data', array( __CLASS__, 'preload_data' ) );
}
/**
* Get a list of allowed industries for the onboarding wizard.
*
* @return array
*/
public static function get_allowed_industries() {
/* With "use_description" we turn the description input on. With "description_label" we set the input label */
return apply_filters(
'woocommerce_admin_onboarding_industries',
array(
'fashion-apparel-accessories' => array(
'label' => __( 'Fashion, apparel, and accessories', 'woocommerce' ),
'use_description' => false,
'description_label' => '',
),
'health-beauty' => array(
'label' => __( 'Health and beauty', 'woocommerce' ),
'use_description' => false,
'description_label' => '',
),
'electronics-computers' => array(
'label' => __( 'Electronics and computers', 'woocommerce' ),
'use_description' => false,
'description_label' => '',
),
'food-drink' => array(
'label' => __( 'Food and drink', 'woocommerce' ),
'use_description' => false,
'description_label' => '',
),
'home-furniture-garden' => array(
'label' => __( 'Home, furniture, and garden', 'woocommerce' ),
'use_description' => false,
'description_label' => '',
),
'cbd-other-hemp-derived-products' => array(
'label' => __( 'CBD and other hemp-derived products', 'woocommerce' ),
'use_description' => false,
'description_label' => '',
),
'education-and-learning' => array(
'label' => __( 'Education and learning', 'woocommerce' ),
'use_description' => false,
'description_label' => '',
),
'other' => array(
'label' => __( 'Other', 'woocommerce' ),
'use_description' => true,
'description_label' => __( 'Description', 'woocommerce' ),
),
)
);
}
/**
* Add preloaded data to onboarding.
*
* @param array $settings Component settings.
* @return array
*/
public static function preload_data( $settings ) {
$settings['onboarding']['industries'] = self::get_allowed_industries();
return $settings;
}
}

View File

@@ -1,66 +0,0 @@
<?php
/**
* WooCommerce Onboarding Jetpack
*/
namespace Automattic\WooCommerce\Internal\Admin\Onboarding;
/**
* Contains logic around Jetpack setup during onboarding.
*/
class OnboardingJetpack {
/**
* Class instance.
*
* @var OnboardingJetpack instance
*/
private static $instance = null;
/**
* Get class instance.
*/
final public static function instance() {
if ( ! static::$instance ) {
static::$instance = new static();
}
return static::$instance;
}
/**
* Init.
*/
public function init() {
add_action( 'woocommerce_admin_plugins_pre_activate', array( $this, 'activate_and_install_jetpack_ahead_of_wcpay' ) );
add_action( 'woocommerce_admin_plugins_pre_install', array( $this, 'activate_and_install_jetpack_ahead_of_wcpay' ) );
// Always hook into Jetpack connection even if outside of admin.
add_action( 'jetpack_site_registered', array( $this, 'set_woocommerce_setup_jetpack_opted_in' ) );
}
/**
* Sets the woocommerce_setup_jetpack_opted_in to true when Jetpack connects to WPCOM.
*/
public function set_woocommerce_setup_jetpack_opted_in() {
update_option( 'woocommerce_setup_jetpack_opted_in', true );
}
/**
* Ensure that Jetpack gets installed and activated ahead of WooCommerce Payments
* if both are being installed/activated at the same time.
*
* See: https://github.com/Automattic/woocommerce-payments/issues/1663
* See: https://github.com/Automattic/jetpack/issues/19624
*
* @param array $plugins A list of plugins to install or activate.
*
* @return array
*/
public function activate_and_install_jetpack_ahead_of_wcpay( $plugins ) {
if ( in_array( 'jetpack', $plugins, true ) && in_array( 'woocommerce-payments', $plugins, true ) ) {
array_unshift( $plugins, 'jetpack' );
$plugins = array_unique( $plugins );
}
return $plugins;
}
}

View File

@@ -1,53 +0,0 @@
<?php
/**
* WooCommerce Onboarding Mailchimp
*/
namespace Automattic\WooCommerce\Internal\Admin\Onboarding;
use Automattic\WooCommerce\Internal\Admin\Schedulers\MailchimpScheduler;
/**
* Logic around updating Mailchimp during onboarding.
*/
class OnboardingMailchimp {
/**
* Class instance.
*
* @var OnboardingMailchimp instance
*/
private static $instance = null;
/**
* Get class instance.
*/
final public static function instance() {
if ( ! static::$instance ) {
static::$instance = new static();
}
return static::$instance;
}
/**
* Init.
*/
public function init() {
add_action( 'woocommerce_onboarding_profile_data_updated', array( $this, 'on_profile_data_updated' ), 10, 2 );
}
/**
* Reset MailchimpScheduler if profile data is being updated with a new email.
*
* @param array $existing_data Existing option data.
* @param array $updating_data Updating option data.
*/
public function on_profile_data_updated( $existing_data, $updating_data ) {
if (
isset( $existing_data['store_email'] ) &&
isset( $updating_data['store_email'] ) &&
$existing_data['store_email'] !== $updating_data['store_email']
) {
MailchimpScheduler::reset();
}
}
}

View File

@@ -1,175 +0,0 @@
<?php
/**
* WooCommerce Onboarding Products
*/
namespace Automattic\WooCommerce\Internal\Admin\Onboarding;
use Automattic\WooCommerce\Admin\Features\Features;
use Automattic\WooCommerce\Internal\Admin\Onboarding\OnboardingProfile;
use Automattic\WooCommerce\Admin\Loader;
use Automattic\WooCommerce\Admin\PluginsHelper;
/**
* Class for handling product types and data around product types.
*/
class OnboardingProducts {
/**
* Name of product data transient.
*
* @var string
*/
const PRODUCT_DATA_TRANSIENT = 'wc_onboarding_product_data';
/**
* Get a list of allowed product types for the onboarding wizard.
*
* @return array
*/
public static function get_allowed_product_types() {
$products = array(
'physical' => array(
'label' => __( 'Physical products', 'woocommerce' ),
'default' => true,
),
'downloads' => array(
'label' => __( 'Downloads', 'woocommerce' ),
),
'subscriptions' => array(
'label' => __( 'Subscriptions', 'woocommerce' ),
),
'memberships' => array(
'label' => __( 'Memberships', 'woocommerce' ),
'product' => 958589,
),
'bookings' => array(
'label' => __( 'Bookings', 'woocommerce' ),
'product' => 390890,
),
'product-bundles' => array(
'label' => __( 'Bundles', 'woocommerce' ),
'product' => 18716,
),
'product-add-ons' => array(
'label' => __( 'Customizable products', 'woocommerce' ),
'product' => 18618,
),
);
$base_location = wc_get_base_location();
$has_cbd_industry = false;
if ( 'US' === $base_location['country'] ) {
$profile = get_option( OnboardingProfile::DATA_OPTION, array() );
if ( ! empty( $profile['industry'] ) ) {
$has_cbd_industry = in_array( 'cbd-other-hemp-derived-products', array_column( $profile['industry'], 'slug' ), true );
}
}
if ( ! Features::is_enabled( 'subscriptions' ) || 'US' !== $base_location['country'] || $has_cbd_industry ) {
$products['subscriptions']['product'] = 27147;
}
return apply_filters( 'woocommerce_admin_onboarding_product_types', $products );
}
/**
* Get dynamic product data from API.
*
* @param array $product_types Array of product types.
* @return array
*/
public static function get_product_data( $product_types ) {
$locale = get_user_locale();
// Transient value is an array of product data keyed by locale.
$transient_value = get_transient( self::PRODUCT_DATA_TRANSIENT );
$transient_value = is_array( $transient_value ) ? $transient_value : array();
$woocommerce_products = $transient_value[ $locale ] ?? false;
if ( false === $woocommerce_products ) {
$woocommerce_products = wp_remote_get(
add_query_arg(
array(
'locale' => $locale,
),
'https://woocommerce.com/wp-json/wccom-extensions/1.0/search'
),
array(
'user-agent' => 'WooCommerce/' . WC()->version . '; ' . get_bloginfo( 'url' ),
)
);
if ( is_wp_error( $woocommerce_products ) ) {
return $product_types;
}
$transient_value[ $locale ] = $woocommerce_products;
set_transient( self::PRODUCT_DATA_TRANSIENT, $transient_value, DAY_IN_SECONDS );
}
$data = json_decode( $woocommerce_products['body'] );
$products = array();
$product_data = array();
// Map product data by ID.
if ( isset( $data ) && isset( $data->products ) ) {
foreach ( $data->products as $product_datum ) {
if ( isset( $product_datum->id ) ) {
$products[ $product_datum->id ] = $product_datum;
}
}
}
// Loop over product types and append data.
foreach ( $product_types as $key => $product_type ) {
$product_data[ $key ] = $product_types[ $key ];
if ( isset( $product_type['product'] ) && isset( $products[ $product_type['product'] ] ) ) {
$price = html_entity_decode( $products[ $product_type['product'] ]->price );
$yearly_price = (float) str_replace( '$', '', $price );
$product_data[ $key ]['yearly_price'] = $yearly_price;
$product_data[ $key ]['description'] = $products[ $product_type['product'] ]->excerpt;
$product_data[ $key ]['more_url'] = $products[ $product_type['product'] ]->link;
$product_data[ $key ]['slug'] = strtolower( preg_replace( '~[^\pL\d]+~u', '-', $products[ $product_type['product'] ]->slug ) );
}
}
return $product_data;
}
/**
* Get the allowed product types with the polled data.
*
* @return array
*/
public static function get_product_types_with_data() {
return self::get_product_data( self::get_allowed_product_types() );
}
/**
* Get relevant purchaseable products for the site.
*
* @return array
*/
public static function get_relevant_products() {
$profiler_data = get_option( OnboardingProfile::DATA_OPTION, array() );
$installed = PluginsHelper::get_installed_plugin_slugs();
$product_types = isset( $profiler_data['product_types'] ) ? $profiler_data['product_types'] : array();
$product_data = self::get_product_types_with_data();
$purchaseable = array();
$remaining = array();
foreach ( $product_types as $type ) {
if ( ! isset( $product_data[ $type ]['slug'] ) ) {
continue;
}
$purchaseable[] = $product_data[ $type ];
if ( ! in_array( $product_data[ $type ]['slug'], $installed, true ) ) {
$remaining[] = $product_data[ $type ]['label'];
}
}
return array(
'purchaseable' => $purchaseable,
'remaining' => $remaining,
);
}
}

View File

@@ -1,67 +0,0 @@
<?php
/**
* WooCommerce Onboarding Setup Wizard
*/
namespace Automattic\WooCommerce\Internal\Admin\Onboarding;
use Automattic\WooCommerce\Admin\Features\OnboardingTasks\TaskLists;
use Automattic\WooCommerce\Admin\PageController;
use Automattic\WooCommerce\Admin\WCAdminHelper;
/**
* Contains backend logic for the onboarding profile and checklist feature.
*/
class OnboardingProfile {
/**
* Profile data option name.
*/
const DATA_OPTION = 'woocommerce_onboarding_profile';
/**
* Add onboarding actions.
*/
public static function init() {
add_action( 'update_option_' . self::DATA_OPTION, array( __CLASS__, 'trigger_complete' ), 10, 2 );
}
/**
* Trigger the woocommerce_onboarding_profile_completed action
*
* @param array $old_value Previous value.
* @param array $value Current value.
*/
public static function trigger_complete( $old_value, $value ) {
if ( isset( $old_value['completed'] ) && $old_value['completed'] ) {
return;
}
if ( ! isset( $value['completed'] ) || ! $value['completed'] ) {
return;
}
/**
* Action hook fired when the onboarding profile (or onboarding wizard,
* or profiler) is completed.
*
* @since 1.5.0
*/
do_action( 'woocommerce_onboarding_profile_completed' );
}
/**
* Check if the profiler still needs to be completed.
*
* @return bool
*/
public static function needs_completion() {
$onboarding_data = get_option( self::DATA_OPTION, array() );
$is_completed = isset( $onboarding_data['completed'] ) && true === $onboarding_data['completed'];
$is_skipped = isset( $onboarding_data['skipped'] ) && true === $onboarding_data['skipped'];
// @todo When merging to WooCommerce Core, we should set the `completed` flag to true during the upgrade progress.
// https://github.com/woocommerce/woocommerce-admin/pull/2300#discussion_r287237498.
return ! $is_completed && ! $is_skipped;
}
}

View File

@@ -1,285 +0,0 @@
<?php
/**
* WooCommerce Onboarding Setup Wizard
*/
namespace Automattic\WooCommerce\Internal\Admin\Onboarding;
use Automattic\WooCommerce\Admin\PageController;
use Automattic\WooCommerce\Admin\WCAdminHelper;
use Automattic\WooCommerce\Internal\Admin\Onboarding\OnboardingProfile;
use Automattic\WooCommerce\Admin\Features\OnboardingTasks\TaskLists;
/**
* Contains backend logic for the onboarding profile and checklist feature.
*/
class OnboardingSetupWizard {
/**
* Class instance.
*
* @var OnboardingSetupWizard instance
*/
private static $instance = null;
/**
* Get class instance.
*/
final public static function instance() {
if ( ! static::$instance ) {
static::$instance = new static();
}
return static::$instance;
}
/**
* Add onboarding actions.
*/
public function init() {
if ( ! is_admin() ) {
return;
}
// Old settings injection.
// Run after Automattic\WooCommerce\Internal\Admin\Loader.
add_filter( 'woocommerce_components_settings', array( $this, 'component_settings' ), 20 );
// New settings injection.
add_filter( 'woocommerce_admin_shared_settings', array( $this, 'component_settings' ), 20 );
add_filter( 'woocommerce_admin_preload_settings', array( $this, 'preload_settings' ) );
add_filter( 'admin_body_class', array( $this, 'add_loading_classes' ) );
add_action( 'admin_init', array( $this, 'do_admin_redirects' ) );
add_action( 'current_screen', array( $this, 'redirect_to_profiler' ) );
add_filter( 'woocommerce_show_admin_notice', array( $this, 'remove_old_install_notice' ), 10, 2 );
}
/**
* Test whether the context of execution comes from async action scheduler.
* Note: this is a polyfill for wc_is_running_from_async_action_scheduler()
* which was introduced in WC 4.0.
*
* @return bool
*/
private function is_running_from_async_action_scheduler() {
if ( function_exists( '\wc_is_running_from_async_action_scheduler' ) ) {
return \wc_is_running_from_async_action_scheduler();
}
// phpcs:ignore WordPress.Security.NonceVerification.Recommended
return isset( $_REQUEST['action'] ) && 'as_async_request_queue_runner' === $_REQUEST['action'];
}
/**
* Handle redirects to setup/welcome page after install and updates.
*
* For setup wizard, transient must be present, the user must have access rights, and we must ignore the network/bulk plugin updaters.
*/
public function do_admin_redirects() {
// Don't run this fn from Action Scheduler requests, as it would clear _wc_activation_redirect transient.
// That means OBW would never be shown.
if ( $this->is_running_from_async_action_scheduler() ) {
return;
}
// Setup wizard redirect.
if ( get_transient( '_wc_activation_redirect' ) && apply_filters( 'woocommerce_enable_setup_wizard', true ) ) {
$do_redirect = true;
$current_page = isset( $_GET['page'] ) ? wc_clean( wp_unslash( $_GET['page'] ) ) : false; // phpcs:ignore WordPress.Security.NonceVerification
$is_onboarding_path = ! isset( $_GET['path'] ) || '/setup-wizard' === wc_clean( wp_unslash( $_GET['page'] ) ); // phpcs:ignore WordPress.Security.NonceVerification
// On these pages, or during these events, postpone the redirect.
if ( wp_doing_ajax() || is_network_admin() || ! current_user_can( 'manage_woocommerce' ) ) {
$do_redirect = false;
}
// On these pages, or during these events, disable the redirect.
if (
( 'wc-admin' === $current_page && $is_onboarding_path ) ||
apply_filters( 'woocommerce_prevent_automatic_wizard_redirect', false ) ||
isset( $_GET['activate-multi'] ) // phpcs:ignore WordPress.Security.NonceVerification
) {
delete_transient( '_wc_activation_redirect' );
$do_redirect = false;
}
if ( $do_redirect ) {
delete_transient( '_wc_activation_redirect' );
wp_safe_redirect( wc_admin_url() );
exit;
}
}
}
/**
* Trigger the woocommerce_onboarding_profile_completed action
*
* @param array $old_value Previous value.
* @param array $value Current value.
*/
public function trigger_profile_completed_action( $old_value, $value ) {
if ( isset( $old_value['completed'] ) && $old_value['completed'] ) {
return;
}
if ( ! isset( $value['completed'] ) || ! $value['completed'] ) {
return;
}
/**
* Action hook fired when the onboarding profile (or onboarding wizard,
* or profiler) is completed.
*
* @since 1.5.0
*/
do_action( 'woocommerce_onboarding_profile_completed' );
}
/**
* Returns true if the profiler should be displayed (not completed and not skipped).
*
* @return bool
*/
private function should_show() {
if ( $this->is_setup_wizard() ) {
return true;
}
return OnboardingProfile::needs_completion();
}
/**
* Redirect to the profiler on homepage if completion is needed.
*/
public function redirect_to_profiler() {
if ( ! $this->is_homepage() || ! OnboardingProfile::needs_completion() ) {
return;
}
wp_safe_redirect( wc_admin_url( '&path=/setup-wizard' ) );
exit;
}
/**
* Check if the current page is the profile wizard.
*
* @return bool
*/
private function is_setup_wizard() {
/* phpcs:disable WordPress.Security.NonceVerification */
return isset( $_GET['page'] ) &&
'wc-admin' === $_GET['page'] &&
isset( $_GET['path'] ) &&
'/setup-wizard' === $_GET['path'];
/* phpcs: enable */
}
/**
* Check if the current page is the homepage.
*
* @return bool
*/
private function is_homepage() {
/* phpcs:disable WordPress.Security.NonceVerification */
return isset( $_GET['page'] ) &&
'wc-admin' === $_GET['page'] &&
! isset( $_GET['path'] );
/* phpcs: enable */
}
/**
* Determine if the current page is one of the WC Admin pages.
*
* @return bool
*/
private function is_woocommerce_page() {
$current_page = PageController::get_instance()->get_current_page();
if ( ! $current_page || ! isset( $current_page['path'] ) ) {
return false;
}
return 0 === strpos( $current_page['path'], 'wc-admin' );
}
/**
* Add profiler items to component settings.
*
* @param array $settings Component settings.
*
* @return array
*/
public function component_settings( $settings ) {
$profile = (array) get_option( OnboardingProfile::DATA_OPTION, array() );
$settings['onboarding'] = array(
'profile' => $profile,
);
// Only fetch if the onboarding wizard OR the task list is incomplete or currently shown
// or the current page is one of the WooCommerce Admin pages.
if (
( ! $this->should_show() && ! count( TaskLists::get_visible() )
||
! $this->is_woocommerce_page()
)
) {
return $settings;
}
include_once WC_ABSPATH . 'includes/admin/helper/class-wc-helper-options.php';
$wccom_auth = \WC_Helper_Options::get( 'auth' );
$profile['wccom_connected'] = empty( $wccom_auth['access_token'] ) ? false : true;
$settings['onboarding']['currencySymbols'] = get_woocommerce_currency_symbols();
$settings['onboarding']['euCountries'] = WC()->countries->get_european_union_countries();
$settings['onboarding']['localeInfo'] = include WC()->plugin_path() . '/i18n/locale-info.php';
$settings['onboarding']['profile'] = $profile;
if ( $this->is_setup_wizard() ) {
$settings['onboarding']['pageCount'] = (int) ( wp_count_posts( 'page' ) )->publish;
$settings['onboarding']['postCount'] = (int) ( wp_count_posts( 'post' ) )->publish;
$settings['onboarding']['isBlockTheme'] = wc_current_theme_is_fse_theme();
}
return apply_filters( 'woocommerce_admin_onboarding_preloaded_data', $settings );
}
/**
* Preload WC setting options to prime state of the application.
*
* @param array $options Array of options to preload.
* @return array
*/
public function preload_settings( $options ) {
$options[] = 'general';
return $options;
}
/**
* Set the admin full screen class when loading to prevent flashes of unstyled content.
*
* @param bool $classes Body classes.
* @return array
*/
public function add_loading_classes( $classes ) {
/* phpcs:disable WordPress.Security.NonceVerification */
if ( $this->is_setup_wizard() ) {
$classes .= ' woocommerce-admin-full-screen';
}
/* phpcs: enable */
return $classes;
}
/**
* Remove the install notice that prompts the user to visit the old onboarding setup wizard.
*
* @param bool $show Show or hide the notice.
* @param string $notice The slug of the notice.
* @return bool
*/
public function remove_old_install_notice( $show, $notice ) {
if ( 'install' === $notice ) {
return false;
}
return $show;
}
}

View File

@@ -1,152 +0,0 @@
<?php
/**
* WooCommerce Onboarding
*/
namespace Automattic\WooCommerce\Internal\Admin\Onboarding;
use Automattic\WooCommerce\Internal\Admin\Onboarding\OnboardingProfile;
use Automattic\WooCommerce\Admin\Features\OnboardingTasks\TaskLists;
/**
* Contains backend logic for the onboarding profile and checklist feature.
*/
class OnboardingSync {
/**
* Class instance.
*
* @var OnboardingSync instance
*/
private static $instance = null;
/**
* Get class instance.
*/
final public static function instance() {
if ( ! static::$instance ) {
static::$instance = new static();
}
return static::$instance;
}
/**
* Init.
*/
public function init() {
add_action( 'update_option_' . OnboardingProfile::DATA_OPTION, array( $this, 'send_profile_data_on_update' ), 10, 2 );
add_action( 'woocommerce_helper_connected', array( $this, 'send_profile_data_on_connect' ) );
if ( ! is_admin() ) {
return;
}
add_action( 'current_screen', array( $this, 'redirect_wccom_install' ) );
}
/**
* Send profile data to Woo.com.
*/
private function send_profile_data() {
if ( 'yes' !== get_option( 'woocommerce_allow_tracking', 'no' ) ) {
return;
}
if ( ! class_exists( '\WC_Helper_API' ) || ! method_exists( '\WC_Helper_API', 'put' ) ) {
return;
}
if ( ! class_exists( '\WC_Helper_Options' ) ) {
return;
}
$auth = \WC_Helper_Options::get( 'auth' );
if ( empty( $auth['access_token'] ) || empty( $auth['access_token_secret'] ) ) {
return false;
}
$profile = get_option( OnboardingProfile::DATA_OPTION, array() );
$base_location = wc_get_base_location();
$defaults = array(
'plugins' => 'skipped',
'industry' => array(),
'product_types' => array(),
'product_count' => '0',
'selling_venues' => 'no',
'number_employees' => '1',
'revenue' => 'none',
'other_platform' => 'none',
'business_extensions' => array(),
'theme' => get_stylesheet(),
'setup_client' => false,
'store_location' => $base_location['country'],
'default_currency' => get_woocommerce_currency(),
);
// Prepare industries as an array of slugs if they are in array format.
if ( isset( $profile['industry'] ) && is_array( $profile['industry'] ) ) {
$industry_slugs = array();
foreach ( $profile['industry'] as $industry ) {
$industry_slugs[] = is_array( $industry ) ? $industry['slug'] : $industry;
}
$profile['industry'] = $industry_slugs;
}
$body = wp_parse_args( $profile, $defaults );
\WC_Helper_API::put(
'profile',
array(
'authenticated' => true,
'body' => wp_json_encode( $body ),
'headers' => array(
'Content-Type' => 'application/json',
),
)
);
}
/**
* Send profiler data on profiler change to completion.
*
* @param array $old_value Previous value.
* @param array $value Current value.
*/
public function send_profile_data_on_update( $old_value, $value ) {
if ( ! isset( $value['completed'] ) || ! $value['completed'] ) {
return;
}
$this->send_profile_data();
}
/**
* Send profiler data after a site is connected.
*/
public function send_profile_data_on_connect() {
$profile = get_option( OnboardingProfile::DATA_OPTION, array() );
if ( ! isset( $profile['completed'] ) || ! $profile['completed'] ) {
return;
}
$this->send_profile_data();
}
/**
* Redirects the user to the task list if the task list is enabled and finishing a wccom checkout.
*
* @todo Once URL params are added to the redirect, we can check those instead of the referer.
*/
public function redirect_wccom_install() {
$task_list = TaskLists::get_list( 'setup' );
if (
! $task_list ||
$task_list->is_hidden() ||
! isset( $_SERVER['HTTP_REFERER'] ) ||
0 !== strpos( $_SERVER['HTTP_REFERER'], 'https://woo.com/checkout?utm_medium=product' ) // phpcs:ignore sanitization ok.
) {
return;
}
wp_safe_redirect( wc_admin_url() );
}
}

View File

@@ -1,233 +0,0 @@
<?php
/**
* WooCommerce Onboarding Themes
*/
namespace Automattic\WooCommerce\Internal\Admin\Onboarding;
use Automattic\WooCommerce\Admin\Loader;
use Automattic\WooCommerce\Admin\PageController;
use Automattic\WooCommerce\Admin\WCAdminHelper;
use Automattic\WooCommerce\Admin\Features\OnboardingTasks\Init as OnboardingTasks;
use Automattic\WooCommerce\Admin\Features\OnboardingTasks\TaskLists;
use Automattic\WooCommerce\Admin\Schedulers\MailchimpScheduler;
/**
* Logic around onboarding themes.
*/
class OnboardingThemes {
/**
* Name of themes transient.
*
* @var string
*/
const THEMES_TRANSIENT = 'wc_onboarding_themes';
/**
* Init.
*/
public static function init() {
add_action( 'woocommerce_theme_installed', array( __CLASS__, 'delete_themes_transient' ) );
add_action( 'after_switch_theme', array( __CLASS__, 'delete_themes_transient' ) );
add_filter( 'woocommerce_rest_prepare_themes', array( __CLASS__, 'add_uploaded_theme_data' ) );
add_filter( 'woocommerce_admin_onboarding_preloaded_data', array( __CLASS__, 'preload_data' ) );
}
/**
* Get puchasable theme by slug.
*
* @param string $price_string string of price.
* @return float|null
*/
private static function get_price_from_string( $price_string ) {
$price_match = null;
// Parse price from string as it includes the currency symbol.
preg_match( '/\\d+\.\d{2}\s*/', $price_string, $price_match );
if ( count( $price_match ) > 0 ) {
return (float) $price_match[0];
}
return null;
}
/**
* Get puchasable theme by slug.
*
* @param string $slug from theme.
* @return array|null
*/
public static function get_paid_theme_by_slug( $slug ) {
$themes = self::get_themes();
$theme_key = array_search( $slug, array_column( $themes, 'slug' ), true );
$theme = false !== $theme_key ? $themes[ $theme_key ] : null;
if ( $theme && isset( $theme['id'] ) && isset( $theme['price'] ) ) {
$price = self::get_price_from_string( $theme['price'] );
if ( $price && $price > 0 ) {
return $themes[ $theme_key ];
}
}
return null;
}
/**
* Sort themes returned from Woo.com
*
* @param array $themes Array of themes from Woo.com.
* @return array
*/
public static function sort_woocommerce_themes( $themes ) {
usort(
$themes,
function ( $product_1, $product_2 ) {
if ( ! property_exists( $product_1, 'id' ) || ! property_exists( $product_1, 'slug' ) ) {
return 1;
}
if ( ! property_exists( $product_2, 'id' ) || ! property_exists( $product_2, 'slug' ) ) {
return 1;
}
if ( in_array( 'Storefront', array( $product_1->slug, $product_2->slug ), true ) ) {
return 'Storefront' === $product_1->slug ? -1 : 1;
}
return $product_1->id < $product_2->id ? 1 : -1;
}
);
return $themes;
}
/**
* Get a list of themes for the onboarding wizard.
*
* @return array
*/
public static function get_themes() {
$themes = get_transient( self::THEMES_TRANSIENT );
if ( false === $themes ) {
$theme_data = wp_remote_get(
'https://woocommerce.com/wp-json/wccom-extensions/1.0/search?category=themes',
array(
'user-agent' => 'WooCommerce/' . WC()->version . '; ' . get_bloginfo( 'url' ),
)
);
$themes = array();
if ( ! is_wp_error( $theme_data ) ) {
$theme_data = json_decode( $theme_data['body'] );
$woo_themes = property_exists( $theme_data, 'products' ) ? $theme_data->products : array();
$sorted_themes = self::sort_woocommerce_themes( $woo_themes );
foreach ( $sorted_themes as $theme ) {
$slug = sanitize_title_with_dashes( $theme->slug );
$themes[ $slug ] = (array) $theme;
$themes[ $slug ]['is_installed'] = false;
$themes[ $slug ]['has_woocommerce_support'] = true;
$themes[ $slug ]['slug'] = $slug;
}
}
$installed_themes = wp_get_themes();
foreach ( $installed_themes as $slug => $theme ) {
$theme_data = self::get_theme_data( $theme );
if ( isset( $themes[ $slug ] ) ) {
$themes[ $slug ]['is_installed'] = true;
$themes[ $slug ]['image'] = $theme_data['image'];
} else {
$themes[ $slug ] = $theme_data;
}
}
$active_theme = get_option( 'stylesheet' );
/**
* The active theme may no be set if active_theme is not compatible with current version of WordPress.
* In this case, we should not add active theme to onboarding themes.
*/
if ( isset( $themes[ $active_theme ] ) ) {
// Add the WooCommerce support tag for default themes that don't explicitly declare support.
if ( function_exists( 'wc_is_wp_default_theme_active' ) && wc_is_wp_default_theme_active() ) {
$themes[ $active_theme ]['has_woocommerce_support'] = true;
}
$themes = array( $active_theme => $themes[ $active_theme ] ) + $themes;
}
set_transient( self::THEMES_TRANSIENT, $themes, DAY_IN_SECONDS );
}
$themes = apply_filters( 'woocommerce_admin_onboarding_themes', $themes );
return array_values( $themes );
}
/**
* Get theme data used in onboarding theme browser.
*
* @param WP_Theme $theme Theme to gather data from.
* @return array
*/
public static function get_theme_data( $theme ) {
return array(
'slug' => sanitize_text_field( $theme->stylesheet ),
'title' => $theme->get( 'Name' ),
'price' => '0.00',
'is_installed' => true,
'image' => $theme->get_screenshot(),
'has_woocommerce_support' => true,
);
}
/**
* Add theme data to response from themes controller.
*
* @param WP_REST_Response $response Rest response.
* @return WP_REST_Response
*/
public static function add_uploaded_theme_data( $response ) {
if ( ! isset( $response->data['theme'] ) ) {
return $response;
}
$theme = wp_get_theme( $response->data['theme'] );
$response->data['theme_data'] = self::get_theme_data( $theme );
return $response;
}
/**
* Delete the stored themes transient.
*/
public static function delete_themes_transient() {
delete_transient( self::THEMES_TRANSIENT );
}
/**
* Add preloaded data to onboarding.
*
* @param array $settings Component settings.
*
* @return array
*/
public static function preload_data( $settings ) {
$settings['onboarding']['activeTheme'] = get_option( 'stylesheet' );
$settings['onboarding']['themes'] = self::get_themes();
return $settings;
}
/**
* Gets an array of themes that can be installed & activated via the onboarding wizard.
*
* @return array
*/
public static function get_allowed_themes() {
$allowed_themes = array();
$themes = self::get_themes();
foreach ( $themes as $theme ) {
$price = preg_replace( '/&#?[a-z0-9]+;/i', '', $theme['price'] );
if ( $theme['is_installed'] || '0.00' === $price ) {
$allowed_themes[] = $theme['slug'];
}
}
return apply_filters( 'woocommerce_admin_onboarding_themes_whitelist', $allowed_themes );
}
}