Merge pull request #22904 from woocommerce/update/20577

Updates - Docs and ActionScheduler implementation
This commit is contained in:
Mike Jolley 2019-03-12 13:21:48 +00:00 committed by GitHub
commit 638812cdd3
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 110 additions and 70 deletions

View File

@ -207,14 +207,16 @@ class WC_Admin_Notices {
* If we need to update, include a message with the update button. * If we need to update, include a message with the update button.
*/ */
public static function update_notice() { public static function update_notice() {
if ( version_compare( get_option( 'woocommerce_db_version' ), WC_VERSION, '<' ) ) { if ( WC_Install::needs_db_update() ) {
$updater = new WC_Background_Updater(); $next_scheduled_date = WC()->queue()->get_next( 'woocommerce_run_update_callback', null, 'woocommerce-db-updates' );
if ( $updater->is_updating() || ! empty( $_GET['do_update_woocommerce'] ) ) { // WPCS: input var ok, CSRF ok.
if ( $next_scheduled_date || ! empty( $_GET['do_update_woocommerce'] ) ) { // WPCS: input var ok, CSRF ok.
include dirname( __FILE__ ) . '/views/html-notice-updating.php'; include dirname( __FILE__ ) . '/views/html-notice-updating.php';
} else { } else {
include dirname( __FILE__ ) . '/views/html-notice-update.php'; include dirname( __FILE__ ) . '/views/html-notice-update.php';
} }
} else { } else {
WC_Install::update_db_version();
include dirname( __FILE__ ) . '/views/html-notice-updated.php'; include dirname( __FILE__ ) . '/views/html-notice-updated.php';
} }
} }

View File

@ -18,16 +18,22 @@ $update_url = wp_nonce_url(
?> ?>
<div id="message" class="updated woocommerce-message wc-connect"> <div id="message" class="updated woocommerce-message wc-connect">
<p> <p>
<strong><?php esc_html_e( 'WooCommerce data update', 'woocommerce' ); ?></strong> &#8211; <?php esc_html_e( 'We need to update your store database to the latest version.', 'woocommerce' ); ?> <strong><?php esc_html_e( 'WooCommerce database update required', 'woocommerce' ); ?></strong>
</p>
<p>
<?php
esc_html_e( 'WooCommerce has been updated! To keep things running smoothly, we have to update your database to the newest version.', 'woocommerce' );
/* translators: 1: Link to docs 2: Close link. */
printf( ' ' . esc_html__( 'The database update process runs in the background and may take a little while, so please be patient. Advanced users can alternatively update via %1$sWP CLI%2$s.', 'woocommerce' ), '<a href="https://github.com/woocommerce/woocommerce/wiki/Upgrading-the-database-using-WP-CLI">', '</a>' );
?>
</p> </p>
<p class="submit"> <p class="submit">
<a href="<?php echo esc_url( $update_url ); ?>" class="wc-update-now button-primary"> <a href="<?php echo esc_url( $update_url ); ?>" class="wc-update-now button-primary">
<?php esc_html_e( 'Run the updater', 'woocommerce' ); ?> <?php esc_html_e( 'Update WooCommerce Database', 'woocommerce' ); ?>
</a>
<a href="https://docs.woocommerce.com/document/how-to-update-woocommerce/" class="button-secondary">
<?php esc_html_e( 'Learn more about updates', 'woocommerce' ); ?>
</a> </a>
</p> </p>
</div> </div>
<script type="text/javascript">
jQuery( '.wc-update-now' ).click( 'click', function() {
return window.confirm( '<?php echo esc_js( __( 'It is strongly recommended that you backup your database before proceeding. Are you sure you wish to run the updater now?', 'woocommerce' ) ); ?>' ); // jshint ignore:line
});
</script>

View File

@ -1,6 +1,8 @@
<?php <?php
/** /**
* Admin View: Notice - Updated * Admin View: Notice - Updated.
*
* @package WooCommerce\Admin
*/ */
if ( ! defined( 'ABSPATH' ) ) { if ( ! defined( 'ABSPATH' ) ) {
@ -9,7 +11,7 @@ if ( ! defined( 'ABSPATH' ) ) {
?> ?>
<div id="message" class="updated woocommerce-message wc-connect woocommerce-message--success"> <div id="message" class="updated woocommerce-message wc-connect woocommerce-message--success">
<a class="woocommerce-message-close notice-dismiss" href="<?php echo esc_url( wp_nonce_url( add_query_arg( 'wc-hide-notice', 'update', remove_query_arg( 'do_update_woocommerce' ) ), 'woocommerce_hide_notices_nonce', '_wc_notice_nonce' ) ); ?>"><?php _e( 'Dismiss', 'woocommerce' ); ?></a> <a class="woocommerce-message-close notice-dismiss" href="<?php echo esc_url( wp_nonce_url( add_query_arg( 'wc-hide-notice', 'update', remove_query_arg( 'do_update_woocommerce' ) ), 'woocommerce_hide_notices_nonce', '_wc_notice_nonce' ) ); ?>"><?php esc_html_e( 'Dismiss', 'woocommerce' ); ?></a>
<p><?php _e( 'WooCommerce data update complete. Thank you for updating to the latest version!', 'woocommerce' ); ?></p> <p><?php esc_html_e( 'WooCommerce database update complete. Thank you for updating to the latest version!', 'woocommerce' ); ?></p>
</div> </div>

View File

@ -8,19 +8,9 @@
if ( ! defined( 'ABSPATH' ) ) { if ( ! defined( 'ABSPATH' ) ) {
exit; exit;
} }
$force_update_url = wp_nonce_url(
add_query_arg( 'force_update_woocommerce', 'true', admin_url( 'admin.php?page=wc-settings' ) ),
'wc_force_db_update',
'wc_force_db_update_nonce'
);
?> ?>
<div id="message" class="updated woocommerce-message wc-connect"> <div id="message" class="updated woocommerce-message wc-connect">
<p> <p>
<strong><?php esc_html_e( 'WooCommerce data update', 'woocommerce' ); ?></strong> &#8211; <?php esc_html_e( 'Your database is being updated in the background.', 'woocommerce' ); ?> <strong><?php esc_html_e( 'WooCommerce database update', 'woocommerce' ); ?></strong> &#8211; <?php esc_html_e( 'WooCommerce is updating the database in the background. The database update process may take a little while, so please be patient.', 'woocommerce' ); ?>
<a href="<?php echo esc_url( $force_update_url ); ?>">
<?php esc_html_e( 'Taking a while? Click here to run it now.', 'woocommerce' ); ?>
</a>
</p> </p>
</div> </div>

View File

@ -3,6 +3,7 @@
* Background Updater * Background Updater
* *
* @version 2.6.0 * @version 2.6.0
* @deprecated 3.6.0 Replaced with queue.
* @package WooCommerce/Classes * @package WooCommerce/Classes
*/ */

View File

@ -132,19 +132,12 @@ class WC_Install {
), ),
); );
/**
* Background update class.
*
* @var object
*/
private static $background_updater;
/** /**
* Hook in tabs. * Hook in tabs.
*/ */
public static function init() { public static function init() {
add_action( 'init', array( __CLASS__, 'check_version' ), 5 ); add_action( 'init', array( __CLASS__, 'check_version' ), 5 );
add_action( 'init', array( __CLASS__, 'init_background_updater' ), 5 ); add_action( 'woocommerce_run_update_callback', array( __CLASS__, 'run_update_callback' ) );
add_action( 'admin_init', array( __CLASS__, 'install_actions' ) ); add_action( 'admin_init', array( __CLASS__, 'install_actions' ) );
add_filter( 'plugin_action_links_' . WC_PLUGIN_BASENAME, array( __CLASS__, 'plugin_action_links' ) ); add_filter( 'plugin_action_links_' . WC_PLUGIN_BASENAME, array( __CLASS__, 'plugin_action_links' ) );
add_filter( 'plugin_row_meta', array( __CLASS__, 'plugin_row_meta' ), 10, 2 ); add_filter( 'plugin_row_meta', array( __CLASS__, 'plugin_row_meta' ), 10, 2 );
@ -152,14 +145,6 @@ class WC_Install {
add_filter( 'cron_schedules', array( __CLASS__, 'cron_schedules' ) ); add_filter( 'cron_schedules', array( __CLASS__, 'cron_schedules' ) );
} }
/**
* Init background updates
*/
public static function init_background_updater() {
include_once dirname( __FILE__ ) . '/class-wc-background-updater.php';
self::$background_updater = new WC_Background_Updater();
}
/** /**
* Check WooCommerce version and run the updater is required. * Check WooCommerce version and run the updater is required.
* *
@ -172,6 +157,51 @@ class WC_Install {
} }
} }
/**
* Run an update callback when triggered by ActionScheduler.
*
* @since 3.6.0
* @param string $callback Callback name.
*/
public static function run_update_callback( $callback ) {
include_once dirname( __FILE__ ) . '/wc-update-functions.php';
if ( is_callable( $callback ) ) {
self::run_update_callback_start( $callback );
$result = (bool) call_user_func( $callback );
self::run_update_callback_end( $callback, $result );
}
}
/**
* Triggered when a callback will run.
*
* @since 3.6.0
* @param string $callback Callback name.
*/
protected static function run_update_callback_start( $callback ) {
wc_maybe_define_constant( 'WC_UPDATING', true );
}
/**
* Triggered when a callback has ran.
*
* @since 3.6.0
* @param string $callback Callback name.
* @param bool $result Return value from callback. Non-false need to run again.
*/
protected static function run_update_callback_end( $callback, $result ) {
if ( $result ) {
WC()->queue()->add(
'woocommerce_run_update_callback',
array(
'update_callback' => $callback,
),
'woocommerce-db-updates'
);
}
}
/** /**
* Install actions when a update button is clicked within the admin area. * Install actions when a update button is clicked within the admin area.
* *
@ -183,17 +213,6 @@ class WC_Install {
self::update(); self::update();
WC_Admin_Notices::add_notice( 'update' ); WC_Admin_Notices::add_notice( 'update' );
} }
if ( ! empty( $_GET['force_update_woocommerce'] ) ) { // WPCS: input var ok.
check_admin_referer( 'wc_force_db_update', 'wc_force_db_update_nonce' );
$blog_id = get_current_blog_id();
// Used to fire an action added in WP_Background_Process::_construct() that calls WP_Background_Process::handle_cron_healthcheck().
// This method will make sure the database updates are executed even if cron is disabled. Nothing will happen if the updates are already running.
do_action( 'wp_' . $blog_id . '_wc_updater_cron' );
wp_safe_redirect( admin_url( 'admin.php?page=wc-settings' ) );
exit;
}
} }
/** /**
@ -271,7 +290,7 @@ class WC_Install {
* @since 3.2.0 * @since 3.2.0
* @return boolean * @return boolean
*/ */
private static function needs_db_update() { public static function needs_db_update() {
$current_db_version = get_option( 'woocommerce_db_version', null ); $current_db_version = get_option( 'woocommerce_db_version', null );
$updates = self::get_db_update_callbacks(); $updates = self::get_db_update_callbacks();
@ -298,7 +317,6 @@ class WC_Install {
private static function maybe_update_db_version() { private static function maybe_update_db_version() {
if ( self::needs_db_update() ) { if ( self::needs_db_update() ) {
if ( apply_filters( 'woocommerce_enable_auto_update_db', false ) ) { if ( apply_filters( 'woocommerce_enable_auto_update_db', false ) ) {
self::init_background_updater();
self::update(); self::update();
} else { } else {
WC_Admin_Notices::add_notice( 'update' ); WC_Admin_Notices::add_notice( 'update' );
@ -331,25 +349,23 @@ class WC_Install {
*/ */
private static function update() { private static function update() {
$current_db_version = get_option( 'woocommerce_db_version' ); $current_db_version = get_option( 'woocommerce_db_version' );
$logger = wc_get_logger(); $loop = 0;
$update_queued = false;
foreach ( self::get_db_update_callbacks() as $version => $update_callbacks ) { foreach ( self::get_db_update_callbacks() as $version => $update_callbacks ) {
if ( version_compare( $current_db_version, $version, '<' ) ) { if ( version_compare( $current_db_version, $version, '<' ) ) {
foreach ( $update_callbacks as $update_callback ) { foreach ( $update_callbacks as $update_callback ) {
$logger->info( WC()->queue()->schedule_single(
sprintf( 'Queuing %s - %s', $version, $update_callback ), time() + $loop,
array( 'source' => 'wc_db_updates' ) 'woocommerce_run_update_callback',
array(
'update_callback' => $update_callback,
),
'woocommerce-db-updates'
); );
self::$background_updater->push_to_queue( $update_callback ); $loop++;
$update_queued = true;
} }
} }
} }
if ( $update_queued ) {
self::$background_updater->save()->dispatch();
}
} }
/** /**

View File

@ -37,20 +37,43 @@ class WC_CLI_Update_Command {
$current_db_version = get_option( 'woocommerce_db_version' ); $current_db_version = get_option( 'woocommerce_db_version' );
$update_count = 0; $update_count = 0;
$callbacks = WC_Install::get_db_update_callbacks();
$callbacks_to_run = array();
foreach ( WC_Install::get_db_update_callbacks() as $version => $update_callbacks ) { foreach ( $callbacks as $version => $update_callbacks ) {
if ( version_compare( $current_db_version, $version, '<' ) ) { if ( version_compare( $current_db_version, $version, '<' ) ) {
foreach ( $update_callbacks as $update_callback ) { foreach ( $update_callbacks as $update_callback ) {
/* translators: %s: DB update callback key */ $callbacks_to_run[] = $update_callback;
WP_CLI::log( sprintf( __( 'Calling update function: %s', 'woocommerce' ), $update_callback ) );
call_user_func( $update_callback );
$update_count ++;
} }
} }
} }
if ( empty( $callbacks_to_run ) ) {
/* translators: %s Database version number */
WP_CLI::success( sprintf( __( 'No updates required. Database version is %s', 'woocommerce' ), get_option( 'woocommerce_db_version' ) ) );
return;
}
/* translators: 1: Number of database updates 2: List of update callbacks */
WP_CLI::log( sprintf( __( 'Found %1$d updates (%2$s)', 'woocommerce' ), count( $callbacks_to_run ), implode( ', ', $callbacks_to_run ) ) );
$progress = \WP_CLI\Utils\make_progress_bar( __( 'Updating database', 'woocommerce' ), count( $callbacks_to_run ) ); // phpcs:ignore PHPCompatibility.LanguageConstructs.NewLanguageConstructs.t_ns_separatorFound
foreach ( $callbacks_to_run as $update_callback ) {
call_user_func( $update_callback );
$result = false;
while ( $result ) {
$result = (bool) call_user_func( $update_callback );
}
$update_count ++;
$progress->tick();
}
$progress->finish();
WC_Admin_Notices::remove_notice( 'update' ); WC_Admin_Notices::remove_notice( 'update' );
/* translators: 1: Number of database updates performed 2: Database version number */ /* translators: 1: Number of database updates performed 2: Database version number */
WP_CLI::success( sprintf( __( '%1$d updates complete. Database version is %2$s', 'woocommerce' ), absint( $update_count ), get_option( 'woocommerce_db_version' ) ) ); WP_CLI::success( sprintf( __( '%1$d update functions completed. Database version is %2$s', 'woocommerce' ), absint( $update_count ), get_option( 'woocommerce_db_version' ) ) );
} }
} }