diff --git a/bulk-edit-cron-offload.php b/bulk-edit-cron-offload.php index 334f8a10fd98c965cab222625d5818de45dd536c..ccfb942f93e8729e001dbb3b0ee1e64da7bb147d 100644 --- a/bulk-edit-cron-offload.php +++ b/bulk-edit-cron-offload.php @@ -5,7 +5,7 @@ * Description: Process Bulk Edit requests using Cron * Author: Erick Hitter, Automattic * Author URI: https://automattic.com/ - * Text Domain: automattic-bulk-edit-cron-offload + * Text Domain: bulk-edit-cron-offload * Domain Path: /languages * Version: 1.0 * diff --git a/includes/class-delete-all.php b/includes/class-delete-all.php index 2472f38aa8f9767c9f0a2602e25f879fc44e2b7b..3f683f4ff424c7a86cd2ab8fae0fe5483a6dedef 100644 --- a/includes/class-delete-all.php +++ b/includes/class-delete-all.php @@ -1,7 +1,15 @@ <?php +/** + * Offload "Empty Trash" + * + * @package Bulk_Edit_Cron_Offload + */ namespace Automattic\WP\Bulk_Edit_Cron_Offload; +/** + * Class Delete_All + */ class Delete_All { /** * Class constants @@ -20,7 +28,7 @@ class Delete_All { add_action( 'admin_notices', array( __CLASS__, 'admin_notices' ) ); add_filter( 'posts_where', array( __CLASS__, 'hide_posts_pending_delete' ), 999, 2 ); - // Limit when caps are intercepted, given frequent execution of the `map_meta_cap` filter + // Limit when caps are intercepted, given frequent execution of the `map_meta_cap` filter. add_action( 'load-edit.php', function() { add_filter( 'map_meta_cap', array( __CLASS__, 'hide_empty_trash_pending_delete' ), 10, 2 ); } ); @@ -28,10 +36,12 @@ class Delete_All { /** * Handle a request to delete all trashed items for a given post type + * + * @param object $vars Bulk-request variables. */ public static function process( $vars ) { - // Special keys are used to trigger this request, and we need to remove them on redirect - $extra_keys = array( 'delete_all', 'delete_all2', ); + // Special keys are used to trigger this request, and we need to remove them on redirect. + $extra_keys = array( 'delete_all', 'delete_all2' ); $action_scheduled = self::action_next_scheduled( self::CRON_EVENT, $vars->post_type ); @@ -46,6 +56,8 @@ class Delete_All { /** * Cron callback to delete trashed items in a given post type + * + * @param object $vars Bulk-request variables. */ public static function process_via_cron( $vars ) { global $wpdb; @@ -57,22 +69,25 @@ class Delete_All { if ( is_array( $post_ids ) && ! empty( $post_ids ) ) { require_once ABSPATH . '/wp-admin/includes/post.php'; - $deleted = $locked = $auth_error = $error = array(); + $deleted = array(); + $locked = array(); + $auth_error = array(); + $error = array(); foreach ( $post_ids as $post_id ) { - // Can the user delete this post + // Can the user delete this post? if ( ! user_can( $vars->user_id, 'delete_post', $post_id ) ) { $auth_error[] = $post_id; continue; } - // Post is locked by someone, so leave it alone + // Post is locked by someone, so leave it alone. if ( false !== wp_check_post_lock( $post_id ) ) { $locked[] = $post_id; continue; } - // Try deleting + // Try deleting. $post_deleted = wp_delete_post( $post_id ); if ( $post_deleted ) { $deleted[] = $post_id; @@ -80,18 +95,17 @@ class Delete_All { $error[] = $post_id; } - // Take a break periodically + // Take a break periodically. if ( 0 === $count++ % 50 ) { stop_the_insanity(); + sleep( 3 ); } } - // TODO: something meaningful with this data $results = compact( 'deleted', 'locked', 'auth_error', 'error' ); - return $results; + do_action( 'bulk_edit_cron_offload_delete_all_request_completed', $results, $vars ); } else { - // TODO: What to do here? - return false; + do_action( 'bulk_edit_cron_offload_delete_all_request_no_posts', $post_ids, $vars ); } } @@ -104,19 +118,19 @@ class Delete_All { if ( isset( $_REQUEST[ self::ADMIN_NOTICE_KEY ] ) ) { if ( 1 === (int) $_REQUEST[ self::ADMIN_NOTICE_KEY ] ) { $class = 'notice-success'; - $message = __( 'Success! The trash will be emptied soon.', 'automattic-bulk-edit-cron-offload' ); + $message = __( 'Success! The trash will be emptied soon.', 'bulk-edit-cron-offload' ); } else { $class = 'notice-error'; - $message = __( 'A request to empty the trash is already pending for this post type.', 'automattic-bulk-edit-cron-offload' ); + $message = __( 'A request to empty the trash is already pending for this post type.', 'bulk-edit-cron-offload' ); } } elseif ( 'edit' === $screen->base && isset( $_REQUEST['post_status'] ) && 'trash' === $_REQUEST['post_status'] ) { if ( self::action_next_scheduled( self::CRON_EVENT, $screen->post_type ) ) { $class = 'notice-warning'; - $message = __( 'A pending request to empty the trash will be processed soon.', 'automattic-bulk-edit-cron-offload' ); + $message = __( 'A pending request to empty the trash will be processed soon.', 'bulk-edit-cron-offload' ); } } - // Nothing to display + // Nothing to display. if ( ! isset( $class ) || ! isset( $message ) ) { return; } @@ -130,6 +144,10 @@ class Delete_All { /** * When a delete is pending for a given post type, hide those posts in the admin + * + * @param string $where Posts' WHERE clause. + * @param object $q WP_Query object. + * @return string */ public static function hide_posts_pending_delete( $where, $q ) { if ( ! is_admin() || ! $q->is_main_query() ) { @@ -156,33 +174,33 @@ class Delete_All { * * Core doesn't provide a filter specifically for this, but permissions are checked before showing the button * - * @param array $caps User's capabilities - * @param string $cap Cap currently being checked + * @param array $caps User's capabilities. + * @param string $cap Cap currently being checked. * @return array */ public static function hide_empty_trash_pending_delete( $caps, $cap ) { - // Button we're blocking only shows for the "trash" status, understandably + // Button we're blocking only shows for the "trash" status, understandably. if ( ! isset( $_REQUEST['post_status'] ) || 'trash' !== $_REQUEST['post_status'] ) { return $caps; } - // Get post type as Core envisions + // Get post type as Core envisions. $screen = get_current_screen(); - // Cap used to display button, per WP_Posts_List_Table::extra_tablenav() + // Cap used to display button, per WP_Posts_List_Table::extra_tablenav(). $cap_to_block = get_post_type_object( $screen->post_type )->cap->edit_others_posts; - // The current cap isn't the one we're looking for + // The current cap isn't the one we're looking for. if ( $cap !== $cap_to_block ) { return $caps; } - // There isn't a pending purge, so one should be permitted + // There isn't a pending purge, so one should be permitted. if ( ! self::action_next_scheduled( self::CRON_EVENT, $screen->post_type ) ) { return $caps; } - // Block the edit button by disallowing its cap + // Block the edit button by disallowing its cap. $caps[] = 'do_not_allow'; return $caps; @@ -191,8 +209,8 @@ class Delete_All { /** * Find the next scheduled instance of a given action, regardless of arguments * - * @param string $action_to_check Hook to search for - * @param string $post_type Post type hook is scheduled for + * @param string $action_to_check Hook to search for. + * @param string $post_type Post type hook is scheduled for. * @return array */ private static function action_next_scheduled( $action_to_check, $post_type ) { @@ -203,7 +221,7 @@ class Delete_All { } foreach ( $events as $timestamp => $timestamp_events ) { - // Skip non-event data that Core includes in the option + // Skip non-event data that Core includes in the option. if ( ! is_numeric( $timestamp ) ) { continue; } @@ -217,13 +235,16 @@ class Delete_All { $vars = array_shift( $instance_args['args'] ); if ( $post_type === $vars->post_type ) { - return array( 'timestamp' => $timestamp, 'args' => $vars, ); + return array( + 'timestamp' => $timestamp, + 'args' => $vars, + ); } } } } - // No matching event found + // No matching event found. return array(); } } diff --git a/includes/class-main.php b/includes/class-main.php index a34e9cdd64eaee08ca805aad6a2a74b2a27b1c33..aa0d618d084a96a8970b5bb3e8efe01b47a96614 100644 --- a/includes/class-main.php +++ b/includes/class-main.php @@ -7,6 +7,9 @@ namespace Automattic\WP\Bulk_Edit_Cron_Offload; +/** + * Class Main + */ class Main { /** * Prefix for bulk-process hook invoked by request-specific classes @@ -24,15 +27,15 @@ class Main { * Call appropriate handler */ public static function intercept() { - // Nothing to do + // Nothing to do. if ( ! self::should_intercept_request() ) { return; } - // Validate request + // Validate request. check_admin_referer( 'bulk-posts' ); - // Parse request to determine what to do + // Parse request to determine what to do. $vars = self::capture_vars(); $action = self::build_hook( $vars->action ); @@ -40,10 +43,10 @@ class Main { return; } - // Pass request to a class to handle offloading to cron, UX, etc + // Pass request to a class to handle offloading to cron, UX, etc. do_action( $action, $vars ); - // Only skip Core's default handling when action is offloaded + // Only skip Core's default handling when action is offloaded. if ( has_action( $action ) ) { self::skip_core_processing(); } @@ -68,7 +71,7 @@ class Main { * Capture relevant variables */ private static function capture_vars() { - $vars = (object) array_fill_keys( array( 'user_id', 'action', 'post_type', 'posts', 'tax_input', 'post_author', 'comment_status', 'ping_status', 'post_status', 'post_sticky', 'post_format', ), null ); + $vars = (object) array_fill_keys( array( 'user_id', 'action', 'post_type', 'posts', 'tax_input', 'post_author', 'comment_status', 'ping_status', 'post_status', 'post_sticky', 'post_format' ), null ); $vars->user_id = get_current_user_id(); @@ -118,14 +121,13 @@ class Main { $vars->post_format = $_REQUEST['post_format']; } - // Return captured variables return $vars; } /** * Validate action * - * @param string $action Action parsed from request vars + * @param string $action Action parsed from request vars. * @return bool */ public static function bulk_action_allowed( $action ) { @@ -143,7 +145,7 @@ class Main { /** * Build a WP hook specific to a bulk request * - * @param string $action Bulk action to offload + * @param string $action Bulk action to offload. * @return string */ public static function build_hook( $action ) { @@ -163,19 +165,19 @@ class Main { /** * Redirect, including a flag to indicate if the bulk process was scheduled successfully * - * @param string $return_key Key to include in redirect URL to flag request's origin, use for admin feedback, etc. - * @param bool $succeeded Whether or not the bulk-delete was scheduled - * @param array $extra_keys Array of additional action keys to remove from redirect URL. Optional. + * @param string $return_key Key to include in redirect URL to flag request's origin, use for admin feedback, etc. + * @param bool $succeeded Whether or not the bulk-delete was scheduled. + * @param array $extra_keys Optional. Array of additional action keys to remove from redirect URL. */ public static function do_admin_redirect( $return_key, $succeeded = false, $extra_keys = array() ) { $redirect = wp_unslash( $_SERVER['REQUEST_URI'] ); - // Remove arguments that could re-trigger this bulk-edit - $action_keys = array( '_wp_http_referer', '_wpnonce', 'action', 'action2', ); + // Remove arguments that could re-trigger this bulk-edit. + $action_keys = array( '_wp_http_referer', '_wpnonce', 'action', 'action2' ); $action_keys = array_merge( $action_keys, $extra_keys ); $redirect = remove_query_arg( $action_keys, $redirect ); - // Add a flag for the admin notice + // Add a flag for the admin notice. $redirect = add_query_arg( $return_key, $succeeded ? 1 : -1, $redirect ); $redirect = esc_url_raw( $redirect ); diff --git a/includes/utils.php b/includes/utils.php index d135c507c342a395cee56a6d4818669d11636a33..b2d3724c6df0cedf84681ebe2c5bc6af35737bc2 100644 --- a/includes/utils.php +++ b/includes/utils.php @@ -1,4 +1,9 @@ <?php +/** + * Plugin utilities + * + * @package Bulk_Edit_Cron_Offload + */ namespace Automattic\WP\Bulk_Edit_Cron_Offload; @@ -8,7 +13,7 @@ namespace Automattic\WP\Bulk_Edit_Cron_Offload; function stop_the_insanity() { global $wpdb, $wp_object_cache; - $wpdb->queries = array(); // or define( 'WP_IMPORTING', true ); + $wpdb->queries = array(); if ( ! is_object( $wp_object_cache ) ) { return; @@ -20,6 +25,6 @@ function stop_the_insanity() { $wp_object_cache->cache = array(); if ( is_callable( $wp_object_cache, '__remoteset' ) ) { - $wp_object_cache->__remoteset(); // important + $wp_object_cache->__remoteset(); // important! } } diff --git a/languages/bulk-edit-cron-offload.pot b/languages/bulk-edit-cron-offload.pot index c61a699cf66937b19ba5bdfccdd3bc2e02575ea3..ba8d037a21ee446652f324099a4d8509acb919b8 100644 --- a/languages/bulk-edit-cron-offload.pot +++ b/languages/bulk-edit-cron-offload.pot @@ -5,7 +5,7 @@ msgstr "" "Project-Id-Version: Bulk Edit Cron Offload 1.0\n" "Report-Msgid-Bugs-To: " "https://wordpress.org/support/plugin/bulk-edit-cron-offload\n" -"POT-Creation-Date: 2017-09-13 00:10:57+00:00\n" +"POT-Creation-Date: 2017-09-13 01:24:54+00:00\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=utf-8\n" "Content-Transfer-Encoding: 8bit\n" @@ -25,6 +25,18 @@ msgstr "" "X-Poedit-Bookmarks: \n" "X-Textdomain-Support: yes\n" +#: includes/class-delete-all.php:124 +msgid "Success! The trash will be emptied soon." +msgstr "" + +#: includes/class-delete-all.php:127 +msgid "A request to empty the trash is already pending for this post type." +msgstr "" + +#: includes/class-delete-all.php:132 +msgid "A pending request to empty the trash will be processed soon." +msgstr "" + #. Plugin Name of the plugin/theme msgid "Bulk Edit Cron Offload" msgstr ""